From 92a14c10a6de9d639746bcfb66939d186cc60426 Mon Sep 17 00:00:00 2001 From: Joseph Callen Date: Thu, 21 Aug 2025 13:15:19 -0400 Subject: [PATCH] vSphere: bump capv for bug fixes This commit updates capv to the latest release-1.12 which resolves a race in vm-host zonal described here: https://github.com/kubernetes-sigs/cluster-api-provider-vsphere/issues/3575 ``` go get sigs.k8s.io/cluster-api-provider-vsphere@release-1.13 ``` --- cluster-api/providers/vsphere/go.mod | 139 +- cluster-api/providers/vsphere/go.sum | 195 +- .../asaskevich/govalidator/.gitignore | 15 - .../asaskevich/govalidator/.travis.yml | 20 +- .../asaskevich/govalidator/CODE_OF_CONDUCT.md | 43 - .../asaskevich/govalidator/CONTRIBUTING.md | 4 +- .../github.com/asaskevich/govalidator/LICENSE | 2 +- .../asaskevich/govalidator/README.md | 149 +- .../asaskevich/govalidator/arrays.go | 29 - .../asaskevich/govalidator/converter.go | 33 +- .../github.com/asaskevich/govalidator/doc.go | 3 - .../asaskevich/govalidator/error.go | 6 +- .../asaskevich/govalidator/numerics.go | 37 +- .../asaskevich/govalidator/patterns.go | 174 +- .../asaskevich/govalidator/types.go | 56 +- .../asaskevich/govalidator/utils.go | 46 +- .../asaskevich/govalidator/validator.go | 716 +-- .../asaskevich/govalidator/wercker.yml | 2 +- .../emicklei/go-restful/v3/CHANGES.md | 5 +- .../emicklei/go-restful/v3/README.md | 2 +- .../emicklei/go-restful/v3/jsr311.go | 19 +- .../emicklei/go-restful/v3/route.go | 2 + .../github.com/evanphx/json-patch/v5/merge.go | 26 +- .../github.com/evanphx/json-patch/v5/patch.go | 120 +- .../github.com/fsnotify/fsnotify/.cirrus.yml | 7 +- .../fsnotify/fsnotify/.gitattributes | 1 - .../github.com/fsnotify/fsnotify/.gitignore | 3 + .../github.com/fsnotify/fsnotify/CHANGELOG.md | 34 +- .../fsnotify/fsnotify/CONTRIBUTING.md | 120 +- .../fsnotify/fsnotify/backend_fen.go | 324 +- .../fsnotify/fsnotify/backend_inotify.go | 594 ++- .../fsnotify/fsnotify/backend_kqueue.go | 747 ++- .../fsnotify/fsnotify/backend_other.go | 204 +- .../fsnotify/fsnotify/backend_windows.go | 305 +- .../github.com/fsnotify/fsnotify/fsnotify.go | 368 +- .../fsnotify/fsnotify/internal/darwin.go | 39 + .../fsnotify/internal/debug_darwin.go | 57 + .../fsnotify/internal/debug_dragonfly.go | 33 + .../fsnotify/internal/debug_freebsd.go | 42 + .../fsnotify/internal/debug_kqueue.go | 32 + .../fsnotify/fsnotify/internal/debug_linux.go | 56 + .../fsnotify/internal/debug_netbsd.go | 25 + .../fsnotify/internal/debug_openbsd.go | 28 + .../fsnotify/internal/debug_solaris.go | 45 + .../fsnotify/internal/debug_windows.go | 40 + .../fsnotify/fsnotify/internal/freebsd.go | 31 + .../fsnotify/fsnotify/internal/internal.go | 2 + .../fsnotify/fsnotify/internal/unix.go | 31 + .../fsnotify/fsnotify/internal/unix2.go | 7 + .../fsnotify/fsnotify/internal/windows.go | 41 + .../github.com/fsnotify/fsnotify/mkdoc.zsh | 259 - .../fsnotify/fsnotify/system_bsd.go | 1 - .../fsnotify/fsnotify/system_darwin.go | 1 - .../go-cmp/cmp/internal/function/func.go | 7 + .../github.com/google/go-cmp/cmp/options.go | 10 +- .../github.com/onsi/gomega/CHANGELOG.md | 33 +- .../github.com/onsi/gomega/format/format.go | 10 +- .../github.com/onsi/gomega/gomega_dsl.go | 24 +- .../onsi/gomega/internal/assertion.go | 32 +- .../onsi/gomega/internal/async_assertion.go | 44 +- .../onsi/gomega/internal/duration_bundle.go | 2 +- .../github.com/onsi/gomega/internal/gomega.go | 20 +- .../gomega/internal/polling_signal_error.go | 2 +- .../onsi/gomega/internal/vetoptdesc.go | 2 +- .../vendor/github.com/onsi/gomega/matchers.go | 72 +- .../github.com/onsi/gomega/matchers/and.go | 8 +- .../matchers/assignable_to_type_of_matcher.go | 8 +- .../onsi/gomega/matchers/be_a_directory.go | 8 +- .../onsi/gomega/matchers/be_a_regular_file.go | 8 +- .../gomega/matchers/be_an_existing_file.go | 8 +- .../onsi/gomega/matchers/be_closed_matcher.go | 6 +- .../matchers/be_comparable_to_matcher.go | 8 +- .../gomega/matchers/be_element_of_matcher.go | 8 +- .../onsi/gomega/matchers/be_empty_matcher.go | 6 +- .../matchers/be_equivalent_to_matcher.go | 8 +- .../onsi/gomega/matchers/be_false_matcher.go | 6 +- .../onsi/gomega/matchers/be_identical_to.go | 8 +- .../onsi/gomega/matchers/be_key_of_matcher.go | 8 +- .../onsi/gomega/matchers/be_nil_matcher.go | 6 +- .../gomega/matchers/be_numerically_matcher.go | 10 +- .../onsi/gomega/matchers/be_sent_matcher.go | 10 +- .../gomega/matchers/be_temporally_matcher.go | 8 +- .../onsi/gomega/matchers/be_true_matcher.go | 6 +- .../onsi/gomega/matchers/be_zero_matcher.go | 6 +- .../onsi/gomega/matchers/consist_of.go | 34 +- .../matchers/contain_element_matcher.go | 18 +- .../matchers/contain_elements_matcher.go | 10 +- .../matchers/contain_substring_matcher.go | 8 +- .../onsi/gomega/matchers/equal_matcher.go | 8 +- .../onsi/gomega/matchers/have_cap_matcher.go | 6 +- .../onsi/gomega/matchers/have_each_matcher.go | 14 +- .../gomega/matchers/have_exact_elements.go | 8 +- .../matchers/have_existing_field_matcher.go | 6 +- .../onsi/gomega/matchers/have_field.go | 10 +- .../gomega/matchers/have_http_body_matcher.go | 12 +- .../have_http_header_with_value_matcher.go | 10 +- .../matchers/have_http_status_matcher.go | 10 +- .../onsi/gomega/matchers/have_key_matcher.go | 8 +- .../matchers/have_key_with_value_matcher.go | 12 +- .../onsi/gomega/matchers/have_len_matcher.go | 6 +- .../gomega/matchers/have_occurred_matcher.go | 6 +- .../gomega/matchers/have_prefix_matcher.go | 8 +- .../gomega/matchers/have_suffix_matcher.go | 8 +- .../onsi/gomega/matchers/have_value.go | 8 +- .../gomega/matchers/match_error_matcher.go | 4 +- .../gomega/matchers/match_json_matcher.go | 16 +- .../gomega/matchers/match_regexp_matcher.go | 8 +- .../onsi/gomega/matchers/match_xml_matcher.go | 10 +- .../gomega/matchers/match_yaml_matcher.go | 20 +- .../github.com/onsi/gomega/matchers/not.go | 8 +- .../github.com/onsi/gomega/matchers/or.go | 8 +- .../onsi/gomega/matchers/panic_matcher.go | 10 +- .../onsi/gomega/matchers/receive_matcher.go | 16 +- .../onsi/gomega/matchers/satisfy_matcher.go | 10 +- .../matchers/semi_structured_data_support.go | 32 +- .../onsi/gomega/matchers/succeed_matcher.go | 6 +- .../goraph/bipartitegraph/bipartitegraph.go | 4 +- .../matchers/support/goraph/node/node.go | 2 +- .../onsi/gomega/matchers/type_support.go | 40 +- .../onsi/gomega/matchers/with_transform.go | 14 +- .../github.com/onsi/gomega/types/types.go | 49 +- .../vendor/github.com/spf13/cobra/README.md | 5 +- .../github.com/spf13/cobra/active_help.go | 2 +- .../spf13/cobra/bash_completionsV2.go | 152 +- .../vendor/github.com/spf13/cobra/cobra.go | 16 +- .../vendor/github.com/spf13/cobra/command.go | 331 +- .../github.com/spf13/cobra/completions.go | 126 +- .../spf13/cobra/powershell_completions.go | 35 +- .../fsnotify => spf13/pflag}/.editorconfig | 12 +- .../github.com/spf13/pflag/.golangci.yaml | 4 + .../vendor/github.com/spf13/pflag/flag.go | 29 +- .../vendor/github.com/spf13/pflag/ip.go | 3 + .../github.com/spf13/pflag/ipnet_slice.go | 147 + .../github.com/spf13/pflag/string_array.go | 4 - .../apis/vpc/v1alpha1/addressbinding_types.go | 2 +- .../pkg/apis/vpc/v1alpha1/condition_types.go | 7 +- .../vpc/v1alpha1/ipaddressallocation_types.go | 2 +- .../apis/vpc/v1alpha1/ipblocksinfo_types.go | 2 +- .../pkg/apis/vpc/v1alpha1/subnet_types.go | 40 +- .../pkg/apis/vpc/v1alpha1/subnetset_types.go | 14 +- .../v1alpha1/vpcnetworkconfiguration_types.go | 12 +- .../vpc/v1alpha1/zz_generated.deepcopy.go | 34 +- .../github.com/vmware/govmomi/.goreleaser.yml | 43 - .../govmomi/internal/version/version.go | 2 +- .../vmware/govmomi/vim25/mo/registry.go | 36 +- .../vmware/govmomi/vim25/mo/retrieve.go | 23 +- .../vmware/govmomi/vim25/mo/type_info.go | 24 +- .../vmware/govmomi/vim25/soap/client.go | 21 +- .../net/http/otelhttp/common.go | 7 - .../net/http/otelhttp/config.go | 15 +- .../net/http/otelhttp/handler.go | 93 +- .../otelhttp/internal/request/body_wrapper.go | 75 + .../internal/request/resp_writer_wrapper.go | 112 + .../net/http/otelhttp/internal/semconv/env.go | 97 +- .../semconv/{v1.24.0.go => httpconv.go} | 153 +- .../http/otelhttp/internal/semconv/util.go | 11 +- .../http/otelhttp/internal/semconv/v1.20.0.go | 118 + .../otelhttp/internal/semconvutil/netconv.go | 2 +- .../net/http/otelhttp/transport.go | 64 +- .../net/http/otelhttp/version.go | 2 +- .../instrumentation/net/http/otelhttp/wrap.go | 99 - .../go.opentelemetry.io/otel/.golangci.yml | 2 + .../go.opentelemetry.io/otel/CHANGELOG.md | 67 +- .../go.opentelemetry.io/otel/CODEOWNERS | 2 +- .../go.opentelemetry.io/otel/CONTRIBUTING.md | 2 +- .../vendor/go.opentelemetry.io/otel/Makefile | 13 +- .../vendor/go.opentelemetry.io/otel/README.md | 37 +- .../go.opentelemetry.io/otel/RELEASING.md | 1 + .../otel/baggage/baggage.go | 150 +- .../go.opentelemetry.io/otel/codes/codes.go | 2 +- .../vendor/go.opentelemetry.io/otel/doc.go | 2 + .../otel/internal/rawhelpers.go | 9 +- .../go.opentelemetry.io/otel/metric/meter.go | 13 + .../otel/metric/noop/README.md | 3 + .../otel/metric/noop/noop.go | 281 ++ .../otel/sdk/instrumentation/library.go | 3 +- .../otel/sdk/trace/snapshot.go | 2 +- .../otel/sdk/trace/span.go | 4 +- .../go.opentelemetry.io/otel/sdk/version.go | 2 +- .../otel/semconv/v1.24.0/README.md | 3 - .../otel/semconv/v1.24.0/attribute_group.go | 4387 ----------------- .../otel/semconv/v1.24.0/doc.go | 9 - .../otel/semconv/v1.24.0/event.go | 200 - .../otel/semconv/v1.24.0/exception.go | 9 - .../otel/semconv/v1.24.0/metric.go | 1071 ---- .../otel/semconv/v1.24.0/resource.go | 2545 ---------- .../otel/semconv/v1.24.0/schema.go | 9 - .../otel/semconv/v1.24.0/trace.go | 1323 ----- .../otel/trace/provider.go | 59 + .../go.opentelemetry.io/otel/trace/span.go | 177 + .../go.opentelemetry.io/otel/trace/trace.go | 249 - .../go.opentelemetry.io/otel/trace/tracer.go | 37 + .../otel/trace/tracestate.go | 10 + .../otel/verify_released_changelog.sh | 42 + .../go.opentelemetry.io/otel/version.go | 2 +- .../go.opentelemetry.io/otel/versions.yaml | 8 +- .../golang.org/x/net/html/atom/table.go | 1256 ++--- .../vendor/golang.org/x/net/html/parse.go | 4 +- .../vendor/golang.org/x/net/html/token.go | 18 +- .../vendor/golang.org/x/net/http2/frame.go | 11 + .../vendor/golang.org/x/net/http2/http2.go | 39 +- .../vendor/golang.org/x/net/http2/server.go | 130 +- .../golang.org/x/net/http2/transport.go | 334 +- .../vendor/golang.org/x/net/http2/write.go | 3 +- .../x/net/internal/httpcommon/ascii.go | 53 + .../httpcommon}/headermap.go | 24 +- .../x/net/internal/httpcommon/request.go | 467 ++ .../golang.org/x/net/websocket/websocket.go | 5 +- .../vendor/golang.org/x/oauth2/oauth2.go | 8 +- .../vendor/golang.org/x/oauth2/pkce.go | 4 +- .../golang.org/x/sync/errgroup/errgroup.go | 3 +- .../golang.org/x/sync/errgroup/go120.go | 13 - .../golang.org/x/sync/errgroup/pre_go120.go | 14 - .../vendor/golang.org/x/sys/unix/auxv.go | 36 + .../golang.org/x/sys/unix/auxv_unsupported.go | 13 + .../golang.org/x/sys/unix/syscall_darwin.go | 149 +- .../golang.org/x/sys/unix/syscall_linux.go | 42 +- .../golang.org/x/sys/unix/syscall_solaris.go | 87 + .../golang.org/x/sys/unix/zerrors_linux.go | 20 +- .../x/sys/unix/zerrors_linux_386.go | 3 + .../x/sys/unix/zerrors_linux_amd64.go | 3 + .../x/sys/unix/zerrors_linux_arm.go | 3 + .../x/sys/unix/zerrors_linux_arm64.go | 4 + .../x/sys/unix/zerrors_linux_loong64.go | 3 + .../x/sys/unix/zerrors_linux_mips.go | 3 + .../x/sys/unix/zerrors_linux_mips64.go | 3 + .../x/sys/unix/zerrors_linux_mips64le.go | 3 + .../x/sys/unix/zerrors_linux_mipsle.go | 3 + .../x/sys/unix/zerrors_linux_ppc.go | 3 + .../x/sys/unix/zerrors_linux_ppc64.go | 3 + .../x/sys/unix/zerrors_linux_ppc64le.go | 3 + .../x/sys/unix/zerrors_linux_riscv64.go | 3 + .../x/sys/unix/zerrors_linux_s390x.go | 3 + .../x/sys/unix/zerrors_linux_sparc64.go | 3 + .../x/sys/unix/zsyscall_darwin_amd64.go | 84 + .../x/sys/unix/zsyscall_darwin_amd64.s | 20 + .../x/sys/unix/zsyscall_darwin_arm64.go | 84 + .../x/sys/unix/zsyscall_darwin_arm64.s | 20 + .../x/sys/unix/zsyscall_solaris_amd64.go | 114 + .../x/sys/unix/zsysnum_linux_386.go | 4 + .../x/sys/unix/zsysnum_linux_amd64.go | 4 + .../x/sys/unix/zsysnum_linux_arm.go | 4 + .../x/sys/unix/zsysnum_linux_arm64.go | 4 + .../x/sys/unix/zsysnum_linux_loong64.go | 4 + .../x/sys/unix/zsysnum_linux_mips.go | 4 + .../x/sys/unix/zsysnum_linux_mips64.go | 4 + .../x/sys/unix/zsysnum_linux_mips64le.go | 4 + .../x/sys/unix/zsysnum_linux_mipsle.go | 4 + .../x/sys/unix/zsysnum_linux_ppc.go | 4 + .../x/sys/unix/zsysnum_linux_ppc64.go | 4 + .../x/sys/unix/zsysnum_linux_ppc64le.go | 4 + .../x/sys/unix/zsysnum_linux_riscv64.go | 4 + .../x/sys/unix/zsysnum_linux_s390x.go | 4 + .../x/sys/unix/zsysnum_linux_sparc64.go | 4 + .../golang.org/x/sys/unix/ztypes_linux.go | 6 +- .../golang.org/x/sys/windows/registry/key.go | 13 +- .../x/sys/windows/registry/value.go | 6 +- .../golang.org/x/sys/windows/types_windows.go | 27 + .../x/text/internal/number/format.go | 2 - .../golang.org/x/text/language/parse.go | 2 +- .../gomodules.xyz/jsonpatch/v2/jsonpatch.go | 17 +- .../googleapis/api/httpbody/httpbody.pb.go | 6 +- .../rpc/errdetails/error_details.pb.go | 128 +- .../google.golang.org/grpc/MAINTAINERS.md | 33 +- .../vendor/google.golang.org/grpc/SECURITY.md | 2 +- .../google.golang.org/grpc/backoff/backoff.go | 2 +- .../grpc/balancer/balancer.go | 21 + .../grpc/balancer/base/balancer.go | 4 +- .../grpc/balancer/pickfirst/pickfirst.go | 4 +- .../grpc/balancer_wrapper.go | 50 +- .../grpc_binarylog_v1/binarylog.pb.go | 24 +- .../google.golang.org/grpc/clientconn.go | 114 +- .../vendor/google.golang.org/grpc/codec.go | 69 +- .../grpc/credentials/insecure/insecure.go | 2 +- .../google.golang.org/grpc/dialoptions.go | 29 +- .../vendor/google.golang.org/grpc/doc.go | 2 +- .../grpc/encoding/encoding.go | 5 +- .../grpc/encoding/encoding_v2.go | 81 + .../grpc/encoding/proto/proto.go | 44 +- .../grpc/experimental/stats/metricregistry.go | 269 + .../grpc/experimental/stats/metrics.go | 114 + .../grpc/grpclog/component.go | 10 +- .../google.golang.org/grpc/grpclog/grpclog.go | 104 +- .../grpc/grpclog/internal/grpclog.go | 26 + .../grpc/grpclog/internal/logger.go | 87 + .../internal/loggerv2.go} | 178 +- .../google.golang.org/grpc/grpclog/logger.go | 59 +- .../grpc/grpclog/loggerv2.go | 181 +- .../grpc/health/grpc_health_v1/health.pb.go | 10 +- .../health/grpc_health_v1/health_grpc.pb.go | 71 +- .../grpc/internal/binarylog/method_logger.go | 2 +- .../grpc/internal/channelz/channelmap.go | 9 +- .../grpc/internal/channelz/funcs.go | 2 +- .../internal/channelz/syscall_nonlinux.go | 4 +- .../grpc/internal/envconfig/envconfig.go | 6 +- .../grpc/internal/experimental.go | 8 +- .../{prefixLogger.go => prefix_logger.go} | 40 +- .../internal/grpcsync/callback_serializer.go | 24 +- .../grpc/internal/grpcsync/pubsub.go | 4 +- .../grpc/internal/internal.go | 24 +- .../internal/resolver/dns/dns_resolver.go | 4 +- .../resolver/passthrough/passthrough.go | 2 +- .../grpc/internal/stats/labels.go | 42 + .../internal/stats/metrics_recorder_list.go | 95 + .../grpc/internal/status/status.go | 4 +- .../grpc/internal/syscall/syscall_nonlinux.go | 6 +- .../grpc/internal/tcp_keepalive_unix.go | 2 +- .../grpc/internal/tcp_keepalive_windows.go | 2 +- .../grpc/internal/transport/controlbuf.go | 256 +- .../grpc/internal/transport/handler_server.go | 47 +- .../grpc/internal/transport/http2_client.go | 79 +- .../grpc/internal/transport/http2_server.go | 49 +- .../grpc/internal/transport/http_util.go | 24 +- .../grpc/internal/transport/proxy.go | 10 +- .../grpc/internal/transport/transport.go | 240 +- .../grpc/keepalive/keepalive.go | 20 +- .../google.golang.org/grpc/mem/buffer_pool.go | 194 + .../grpc/mem/buffer_slice.go | 226 + .../google.golang.org/grpc/mem/buffers.go | 252 + .../grpc/metadata/metadata.go | 7 +- .../google.golang.org/grpc/preloader.go | 28 +- .../google.golang.org/grpc/regenerate.sh | 123 - .../grpc/resolver_wrapper.go | 9 +- .../vendor/google.golang.org/grpc/rpc_util.go | 331 +- .../vendor/google.golang.org/grpc/server.go | 99 +- .../grpc/shared_buffer_pool.go | 154 - .../google.golang.org/grpc/stats/stats.go | 6 - .../vendor/google.golang.org/grpc/stream.go | 213 +- .../grpc/stream_interfaces.go | 86 + .../vendor/google.golang.org/grpc/version.go | 2 +- .../protobuf/encoding/protojson/decode.go | 5 - .../protobuf/encoding/prototext/decode.go | 5 - .../protobuf/internal/encoding/tag/tag.go | 8 +- .../protobuf/internal/filedesc/desc.go | 9 +- .../protobuf/internal/filedesc/desc_lazy.go | 9 - .../protobuf/internal/filetype/build.go | 2 +- .../protobuf/internal/flags/flags.go | 2 +- .../protobuf/internal/genid/goname.go | 5 - .../protobuf/internal/impl/codec_field.go | 75 - .../protobuf/internal/impl/codec_map.go | 14 +- .../protobuf/internal/impl/codec_map_go111.go | 38 - .../protobuf/internal/impl/codec_map_go112.go | 12 - .../protobuf/internal/impl/codec_message.go | 7 +- .../internal/impl/codec_message_opaque.go | 9 +- .../protobuf/internal/impl/convert_map.go | 2 +- .../protobuf/internal/impl/lazy.go | 2 +- .../protobuf/internal/impl/legacy_message.go | 5 +- .../protobuf/internal/impl/message.go | 23 +- .../protobuf/internal/impl/message_opaque.go | 41 +- .../protobuf/internal/impl/message_reflect.go | 5 - .../internal/impl/message_reflect_field.go | 130 +- .../protobuf/internal/impl/pointer_unsafe.go | 3 +- .../protobuf/internal/impl/validate.go | 24 +- .../protobuf/internal/impl/weak.go | 74 - .../protobuf/internal/version/version.go | 2 +- .../protobuf/proto/decode.go | 5 - .../protobuf/reflect/protodesc/desc.go | 8 +- .../protobuf/reflect/protodesc/desc_init.go | 1 - .../reflect/protodesc/desc_resolve.go | 26 +- .../reflect/protodesc/desc_validate.go | 12 - .../protobuf/reflect/protodesc/editions.go | 48 +- .../protobuf/reflect/protodesc/proto.go | 3 - .../protobuf/reflect/protoreflect/type.go | 12 +- .../types/descriptorpb/descriptor.pb.go | 12 +- .../protobuf/types/dynamicpb/types.go | 12 +- .../types/gofeaturespb/go_features.pb.go | 12 +- .../protobuf/types/known/anypb/any.pb.go | 12 +- .../types/known/durationpb/duration.pb.go | 12 +- .../protobuf/types/known/emptypb/empty.pb.go | 12 +- .../types/known/fieldmaskpb/field_mask.pb.go | 12 +- .../types/known/structpb/struct.pb.go | 12 +- .../types/known/timestamppb/timestamp.pb.go | 12 +- .../types/known/wrapperspb/wrappers.pb.go | 12 +- .../k8s.io/api/resource/v1alpha3/types.go | 4 + .../k8s.io/api/resource/v1beta1/types.go | 4 + .../vendor/k8s.io/client-go/util/retry/OWNERS | 4 + .../k8s.io/client-go/util/retry/util.go | 105 + .../providers/vsphere/vendor/modules.txt | 115 +- .../.golangci.yml | 17 +- .../cluster-api-provider-vsphere/Makefile | 37 +- .../apis/v1alpha3/conversion.go | 17 + .../v1alpha3/vspherecluster_conversion.go | 2 + .../vsphereclusteridentity_conversion.go | 18 + .../vspheredeploymentzone_conversion.go | 29 +- .../v1alpha3/vspheremachine_conversion.go | 1 + .../apis/v1alpha3/vspherevm_conversion.go | 1 + .../apis/v1alpha3/zz_generated.conversion.go | 98 +- .../apis/v1alpha4/conversion.go | 17 + .../v1alpha4/vspherecluster_conversion.go | 21 +- .../vsphereclusteridentity_conversion.go | 28 +- .../vspheredeploymentzone_conversion.go | 28 +- .../v1alpha4/vspheremachine_conversion.go | 1 + .../apis/v1alpha4/vspherevm_conversion.go | 1 + .../apis/v1alpha4/zz_generated.conversion.go | 98 +- .../apis/v1beta1/vspherecluster_types.go | 101 + .../v1beta1/vsphereclusteridentity_types.go | 53 + .../v1beta1/vspheredeploymentzone_types.go | 118 + .../apis/v1beta1/vspheremachine_types.go | 106 + .../apis/v1beta1/vspherevm_types.go | 170 + .../apis/v1beta1/zz_generated.deepcopy.go | 135 + .../vmware/v1beta1/vspherecluster_types.go | 122 + .../vmware/v1beta1/vspheremachine_types.go | 32 + .../vmware/v1beta1/zz_generated.deepcopy.go | 55 + .../controllers/clustermodule_reconciler.go | 21 +- .../vmware/serviceaccount_controller.go | 29 +- .../vmware/servicediscovery_controller.go | 37 +- .../vmware/vspherecluster_reconciler.go | 127 +- .../vspheremachinetemplate_controller.go | 5 + .../controllers/vspherecluster_controller.go | 4 +- .../controllers/vspherecluster_reconciler.go | 170 +- .../vsphereclusteridentity_controller.go | 60 +- .../vspheredeploymentzone_controller.go | 114 +- ...vspheredeploymentzone_controller_domain.go | 78 +- .../controllers/vspheremachine_controller.go | 109 +- .../controllers/vspherevm_controller.go | 131 +- .../vspherevm_ipaddress_reconciler.go | 42 +- .../webhooks/vmware/vspheremachine.go | 18 +- .../webhooks/vmware/vspheremachinetemplate.go | 16 +- .../webhooks/vsphereclustertemplate.go | 14 +- .../webhooks/vspheredeploymentzone.go | 10 +- .../internal/webhooks/vspherefailuredomain.go | 18 +- .../internal/webhooks/vspheremachine.go | 18 +- .../webhooks/vspheremachinetemplate.go | 14 +- .../internal/webhooks/vspherevm.go | 20 +- .../cluster-api-provider-vsphere/main.go | 72 +- .../pkg/context/cluster_context.go | 14 - .../pkg/context/interfaces.go | 3 + .../pkg/context/machine_context.go | 11 +- .../pkg/context/vm_context.go | 11 +- .../pkg/context/vmware/cluster_context.go | 15 - .../pkg/context/vmware/machine_context.go | 14 +- .../context/vspheredeploymentzone_context.go | 14 - .../pkg/manager/manager.go | 2 + .../pkg/services/govmomi/power.go | 21 + .../pkg/services/govmomi/service.go | 62 + .../pkg/services/govmomi/util.go | 26 +- .../pkg/services/govmomi/vcenter/clone.go | 25 +- .../pkg/services/network/dummy_provider.go | 10 +- .../pkg/services/network/netop_provider.go | 7 + .../pkg/services/network/nsxt_provider.go | 24 + .../pkg/services/network/nsxt_vpc_provider.go | 24 + .../pkg/services/vimmachine.go | 10 + .../vmoperator/control_plane_endpoint.go | 65 +- .../pkg/services/vmoperator/vmopmachine.go | 38 + .../pkg/session/error.go | 40 - .../pkg/session/session.go | 4 +- .../webhooks/alias.go | 71 + .../webhooks/doc.go | 18 + .../webhooks/vmware/alias.go | 39 + .../webhooks/vmware/doc.go | 18 + .../cluster-api/api/v1beta1/cluster_types.go | 163 +- .../api/v1beta1/clusterclass_types.go | 206 +- .../cluster-api/api/v1beta1/common_types.go | 44 +- .../api/v1beta1/condition_types.go | 16 +- .../cluster-api/api/v1beta1/index/cluster.go | 42 + .../cluster-api/api/v1beta1/index/index.go | 2 +- .../cluster-api/api/v1beta1/machine_types.go | 49 +- .../api/v1beta1/machinedeployment_types.go | 85 +- .../api/v1beta1/machinedrainrules_types.go | 21 +- .../api/v1beta1/machinehealthcheck_types.go | 47 +- .../api/v1beta1/machineset_types.go | 49 +- .../api/v1beta1/v1beta2_condition_consts.go | 22 +- .../api/v1beta1/zz_generated.deepcopy.go | 75 + .../api/v1beta1/zz_generated.openapi.go | 487 +- .../kubeadm/api/v1beta1/kubeadm_types.go | 140 +- .../api/v1beta1/kubeadmconfig_types.go | 140 +- .../v1beta1/kubeadmconfigtemplate_types.go | 19 +- .../api/v1beta1/zz_generated.deepcopy.go | 5 + .../clustercache/cluster_accessor.go | 26 +- .../clustercache/cluster_accessor_client.go | 34 +- .../controllers/clustercache/cluster_cache.go | 19 +- .../controllers/clustercache/metrics.go | 56 + .../controllers/crdmigrator/crd_migrator.go | 567 +++ .../remote/cluster_cache_tracker.go | 8 +- .../controllers/remote/stoppable_cache.go | 5 +- .../v1beta1/kubeadm_control_plane_types.go | 80 +- .../kubeadmcontrolplanetemplate_types.go | 28 +- .../api/v1beta1/zz_generated.deepcopy.go | 5 + .../exp/api/v1beta1/machinepool_types.go | 41 +- .../exp/ipam/api/v1beta1/ipaddress_types.go | 21 +- .../ipam/api/v1beta1/ipaddressclaim_types.go | 51 +- .../ipam/api/v1beta1/zz_generated.deepcopy.go | 28 + .../cluster-api/feature/feature.go | 12 +- .../cluster-api/util/annotations/helpers.go | 31 + .../cluster-api/util/cache/cache.go | 149 + .../sigs.k8s.io/cluster-api/util/cache/doc.go | 18 + .../util/collections/machine_collection.go | 10 + .../util/conditions/v1beta2/aggregate.go | 2 +- .../conditions/v1beta2/merge_strategies.go | 30 +- .../util/conditions/v1beta2/patch.go | 9 + .../util/conditions/v1beta2/summary.go | 2 +- .../cluster-api/util/finalizers/finalizers.go | 55 + .../cluster-api/util/labels/helpers.go | 33 + .../cluster-api/util/patch/patch.go | 17 +- .../cluster-api/util/paused/paused.go | 122 + .../util/predicates/cluster_predicates.go | 43 + .../util/predicates/generic_predicates.go | 45 +- .../sigs.k8s.io/cluster-api/util/util.go | 16 + .../sigs.k8s.io/controller-runtime/Makefile | 6 +- .../pkg/builder/controller.go | 8 +- .../pkg/cache/multi_namespace_cache.go | 3 + .../pkg/client/apiutil/restmapper.go | 20 +- .../pkg/client/fake/client.go | 24 +- .../controller-runtime/pkg/controller/name.go | 2 +- .../controller/priorityqueue/priorityqueue.go | 12 +- .../controller-runtime/pkg/handler/enqueue.go | 19 +- .../pkg/handler/enqueue_mapped.go | 45 +- .../pkg/handler/enqueue_owner.go | 2 +- .../pkg/handler/eventhandler.go | 132 +- .../pkg/internal/controller/controller.go | 44 +- 510 files changed, 16404 insertions(+), 17683 deletions(-) delete mode 100644 cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.gitignore delete mode 100644 cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CODE_OF_CONDUCT.md delete mode 100644 cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/doc.go delete mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitattributes create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/darwin.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_darwin.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_dragonfly.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_freebsd.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_kqueue.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_linux.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_netbsd.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_openbsd.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_solaris.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_windows.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/freebsd.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/internal.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix2.go create mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/windows.go delete mode 100644 cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/mkdoc.zsh rename cluster-api/providers/vsphere/vendor/github.com/{fsnotify/fsnotify => spf13/pflag}/.editorconfig (69%) create mode 100644 cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.golangci.yaml create mode 100644 cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ipnet_slice.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/body_wrapper.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/resp_writer_wrapper.go rename cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/{v1.24.0.go => httpconv.go} (57%) delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/wrap.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/README.md create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/noop.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/README.md delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/attribute_group.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/doc.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/event.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/exception.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/metric.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/resource.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/schema.go delete mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/trace.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/provider.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/span.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracer.go create mode 100644 cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/verify_released_changelog.sh create mode 100644 cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/ascii.go rename cluster-api/providers/vsphere/vendor/golang.org/x/net/{http2 => internal/httpcommon}/headermap.go (74%) create mode 100644 cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/request.go delete mode 100644 cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/go120.go delete mode 100644 cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/pre_go120.go create mode 100644 cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv.go create mode 100644 cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv_unsupported.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding_v2.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metricregistry.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metrics.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/grpclog.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/logger.go rename cluster-api/providers/vsphere/vendor/google.golang.org/grpc/{internal/grpclog/grpclog.go => grpclog/internal/loggerv2.go} (52%) rename cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/{prefixLogger.go => prefix_logger.go} (63%) create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/labels.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/metrics_recorder_list.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_pool.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_slice.go create mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffers.go delete mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/regenerate.sh delete mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/grpc/shared_buffer_pool.go delete mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go111.go delete mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go112.go delete mode 100644 cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/weak.go create mode 100644 cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/OWNERS create mode 100644 cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/util.go delete mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/error.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/alias.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/doc.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/alias.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/doc.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/metrics.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/crdmigrator/crd_migrator.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/cache.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/doc.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/finalizers/finalizers.go create mode 100644 cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/paused/paused.go diff --git a/cluster-api/providers/vsphere/go.mod b/cluster-api/providers/vsphere/go.mod index 80b84b266e5..44f7836e1a8 100644 --- a/cluster-api/providers/vsphere/go.mod +++ b/cluster-api/providers/vsphere/go.mod @@ -1,119 +1,120 @@ module openshift/installer/cluster-api/providers/vsphere -go 1.23.0 +go 1.24.0 -toolchain go1.23.5 +toolchain go1.24.6 -replace sigs.k8s.io/cluster-api => sigs.k8s.io/cluster-api v1.9.1 - -require sigs.k8s.io/cluster-api-provider-vsphere v1.12.0-rc.0.0.20250203113257-38f6b67f9b7d +replace sigs.k8s.io/cluster-api => sigs.k8s.io/cluster-api v1.10.1 replace github.com/vmware-tanzu/vm-operator/pkg/constants/testlabels => github.com/vmware-tanzu/vm-operator/pkg/constants/testlabels v0.0.0-20240404200847-de75746a9505 -replace github.com/vmware-tanzu/nsx-operator/pkg/apis => github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20240827061921-8f0982975508 - require ( github.com/vmware-tanzu/net-operator-api v0.0.0-20240326163340-1f32d6bf7f9d // indirect + github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20241112044858-9da8637c1b0d // indirect // The version of vm-operator should be kept in sync with the manifests at: config/deployments/integration-tests github.com/vmware-tanzu/vm-operator/api v1.8.6 // indirect github.com/vmware-tanzu/vm-operator/external/ncp v0.0.0-20240404200847-de75746a9505 // indirect - github.com/vmware/govmomi v0.47.1 // indirect + github.com/vmware/govmomi v0.49.0 // indirect ) +require sigs.k8s.io/cluster-api-provider-vsphere v1.13.1 + require ( cel.dev/expr v0.18.0 // indirect github.com/NYTimes/gziphandler v1.1.1 // indirect github.com/antlr4-go/antlr/v4 v4.13.0 // indirect - github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 // indirect - github.com/beorn7/perks v1.0.1 // indirect - github.com/blang/semver v3.5.1+incompatible // indirect + github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a // indirect github.com/blang/semver/v4 v4.0.0 // indirect github.com/cenkalti/backoff/v4 v4.3.0 // indirect - github.com/cespare/xxhash/v2 v2.3.0 // indirect - github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect - github.com/emicklei/go-restful/v3 v3.12.1 // indirect - github.com/evanphx/json-patch/v5 v5.9.0 // indirect + github.com/emicklei/go-restful/v3 v3.12.2 // indirect github.com/felixge/httpsnoop v1.0.4 // indirect - github.com/fsnotify/fsnotify v1.7.0 // indirect github.com/fxamacker/cbor/v2 v2.7.0 // indirect github.com/go-logr/logr v1.4.2 // indirect github.com/go-logr/stdr v1.2.2 // indirect github.com/go-logr/zapr v1.3.0 // indirect - github.com/go-openapi/jsonpointer v0.21.0 // indirect - github.com/go-openapi/jsonreference v0.20.2 // indirect - github.com/go-openapi/swag v0.23.0 // indirect github.com/go-task/slim-sprig/v3 v3.0.0 // indirect - github.com/gobuffalo/flect v1.0.3 // indirect - github.com/gogo/protobuf v1.3.2 // indirect - github.com/golang/protobuf v1.5.4 // indirect github.com/google/btree v1.1.3 // indirect - github.com/google/cel-go v0.22.0 // indirect github.com/google/gnostic-models v0.6.8 // indirect - github.com/google/go-cmp v0.6.0 // indirect github.com/google/gofuzz v1.2.0 // indirect github.com/google/uuid v1.6.0 // indirect github.com/grpc-ecosystem/grpc-gateway/v2 v2.20.0 // indirect - github.com/inconshreveable/mousetrap v1.1.0 // indirect - github.com/josharian/intern v1.0.0 // indirect - github.com/json-iterator/go v1.1.12 // indirect - github.com/mailru/easyjson v0.7.7 // indirect - github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect - github.com/modern-go/reflect2 v1.0.2 // indirect github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect - github.com/onsi/gomega v1.36.2 // indirect + github.com/onsi/gomega v1.37.0 // indirect github.com/pkg/errors v0.9.1 // indirect - github.com/prometheus/client_golang v1.19.1 // indirect - github.com/prometheus/client_model v0.6.1 // indirect - github.com/prometheus/common v0.55.0 // indirect - github.com/prometheus/procfs v0.15.1 // indirect - github.com/spf13/cobra v1.8.1 // indirect - github.com/spf13/pflag v1.0.5 // indirect - github.com/stoewer/go-strcase v1.3.0 // indirect - github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20241112044858-9da8637c1b0d // indirect + github.com/spf13/cobra v1.9.1 // indirect github.com/x448/float16 v0.8.4 // indirect - go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.53.0 // indirect - go.opentelemetry.io/otel v1.28.0 // indirect + go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.54.0 // indirect + go.opentelemetry.io/otel v1.29.0 // indirect go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.28.0 // indirect go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.27.0 // indirect - go.opentelemetry.io/otel/metric v1.28.0 // indirect - go.opentelemetry.io/otel/sdk v1.28.0 // indirect - go.opentelemetry.io/otel/trace v1.28.0 // indirect + go.opentelemetry.io/otel/metric v1.29.0 // indirect + go.opentelemetry.io/otel/sdk v1.29.0 // indirect + go.opentelemetry.io/otel/trace v1.29.0 // indirect go.opentelemetry.io/proto/otlp v1.3.1 // indirect go.uber.org/multierr v1.11.0 // indirect go.uber.org/zap v1.27.0 // indirect golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56 // indirect - golang.org/x/net v0.34.0 // indirect - golang.org/x/oauth2 v0.25.0 // indirect - golang.org/x/sync v0.10.0 // indirect - golang.org/x/sys v0.29.0 // indirect - golang.org/x/term v0.28.0 // indirect - golang.org/x/text v0.21.0 // indirect - golang.org/x/time v0.7.0 // indirect - gomodules.xyz/jsonpatch/v2 v2.4.0 // indirect - google.golang.org/genproto/googleapis/api v0.0.0-20240826202546-f6391c0de4c7 // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20240826202546-f6391c0de4c7 // indirect - google.golang.org/grpc v1.65.1 // indirect - google.golang.org/protobuf v1.36.1 // indirect + golang.org/x/net v0.38.0 // indirect + golang.org/x/oauth2 v0.28.0 // indirect + golang.org/x/sync v0.12.0 // indirect + golang.org/x/sys v0.32.0 // indirect + golang.org/x/term v0.30.0 // indirect + golang.org/x/text v0.23.0 // indirect + google.golang.org/genproto/googleapis/api v0.0.0-20241209162323-e6fa225c2576 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8 // indirect + google.golang.org/grpc v1.67.3 // indirect gopkg.in/evanphx/json-patch.v4 v4.12.0 // indirect - gopkg.in/fsnotify.v1 v1.4.7 // indirect gopkg.in/gcfg.v1 v1.2.3 // indirect - gopkg.in/inf.v0 v0.9.1 // indirect gopkg.in/warnings.v0 v0.1.2 // indirect - gopkg.in/yaml.v3 v3.0.1 // indirect - k8s.io/api v0.32.1 // indirect - k8s.io/apiextensions-apiserver v0.32.1 // indirect - k8s.io/apimachinery v0.32.1 // indirect - k8s.io/apiserver v0.32.1 // indirect - k8s.io/client-go v0.32.1 // indirect - k8s.io/cluster-bootstrap v0.32.1 // indirect - k8s.io/component-base v0.32.1 // indirect + k8s.io/api v0.32.3 // indirect + k8s.io/apiextensions-apiserver v0.32.3 // indirect + k8s.io/apimachinery v0.32.3 // indirect + k8s.io/client-go v0.32.3 // indirect + k8s.io/cluster-bootstrap v0.32.3 // indirect + k8s.io/component-base v0.32.3 // indirect k8s.io/klog/v2 v2.130.1 // indirect - k8s.io/kube-openapi v0.0.0-20241105132330-32ad38e42d3f // indirect k8s.io/utils v0.0.0-20241104100929-3ea5e8cea738 // indirect sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.31.0 // indirect sigs.k8s.io/cluster-api v0.0.0-00010101000000-000000000000 // indirect - sigs.k8s.io/controller-runtime v0.20.1 // indirect + sigs.k8s.io/controller-runtime v0.20.4 // indirect + sigs.k8s.io/yaml v1.4.0 // indirect +) + +require ( + github.com/beorn7/perks v1.0.1 // indirect + github.com/blang/semver v3.5.1+incompatible // indirect + github.com/cespare/xxhash/v2 v2.3.0 // indirect + github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect + github.com/evanphx/json-patch/v5 v5.9.11 // indirect + github.com/fsnotify/fsnotify v1.8.0 // indirect + github.com/go-openapi/jsonpointer v0.21.0 // indirect + github.com/go-openapi/jsonreference v0.20.2 // indirect + github.com/go-openapi/swag v0.23.0 // indirect + github.com/gobuffalo/flect v1.0.3 // indirect + github.com/gogo/protobuf v1.3.2 // indirect + github.com/golang/protobuf v1.5.4 // indirect + github.com/google/cel-go v0.22.0 // indirect + github.com/google/go-cmp v0.7.0 // indirect + github.com/inconshreveable/mousetrap v1.1.0 // indirect + github.com/josharian/intern v1.0.0 // indirect + github.com/json-iterator/go v1.1.12 // indirect + github.com/mailru/easyjson v0.7.7 // indirect + github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect + github.com/modern-go/reflect2 v1.0.2 // indirect + github.com/prometheus/client_golang v1.19.1 // indirect + github.com/prometheus/client_model v0.6.1 // indirect + github.com/prometheus/common v0.55.0 // indirect + github.com/prometheus/procfs v0.15.1 // indirect + github.com/spf13/pflag v1.0.6 // indirect + github.com/stoewer/go-strcase v1.3.0 // indirect + golang.org/x/time v0.8.0 // indirect + gomodules.xyz/jsonpatch/v2 v2.5.0 // indirect + google.golang.org/protobuf v1.36.5 // indirect + gopkg.in/fsnotify.v1 v1.4.7 // indirect + gopkg.in/inf.v0 v0.9.1 // indirect + gopkg.in/yaml.v3 v3.0.1 // indirect + k8s.io/apiserver v0.32.3 // indirect + k8s.io/kube-openapi v0.0.0-20241105132330-32ad38e42d3f // indirect sigs.k8s.io/json v0.0.0-20241010143419-9aa6b5e7a4b3 // indirect sigs.k8s.io/structured-merge-diff/v4 v4.4.2 // indirect - sigs.k8s.io/yaml v1.4.0 // indirect ) diff --git a/cluster-api/providers/vsphere/go.sum b/cluster-api/providers/vsphere/go.sum index 7ecf9ca6e95..510ea2c40c6 100644 --- a/cluster-api/providers/vsphere/go.sum +++ b/cluster-api/providers/vsphere/go.sum @@ -17,8 +17,8 @@ github.com/PuerkitoBio/purell v1.0.0/go.mod h1:c11w/QuzBsJSee3cPx9rAFu61PvFxuPbt github.com/PuerkitoBio/urlesc v0.0.0-20160726150825-5bd2802263f2/go.mod h1:uGdkoq3SwY9Y+13GIhn11/XLaGBb4BfwItxLd5jeuXE= github.com/antlr4-go/antlr/v4 v4.13.0 h1:lxCg3LAv+EUK6t1i0y1V6/SLeUi0eKEKdhQAlS8TVTI= github.com/antlr4-go/antlr/v4 v4.13.0/go.mod h1:pfChB/xh/Unjila75QW7+VU4TSnWnnk9UTnmpPaOR2g= -github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 h1:DklsrG3dyBCFEj5IhUbnKptjxatkF07cF2ak3yi77so= -github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2/go.mod h1:WaHUgvxTVq04UNunO+XhnAqY/wQc+bxr74GqbsZ/Jqw= +github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a h1:idn718Q4B6AGu/h5Sxe66HYVdqdGu2l9Iebqhi/AEoA= +github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a/go.mod h1:lB+ZfQJz7igIIfQNfa7Ml4HSf2uFQQRzpGGRXenZAgY= github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= github.com/blang/semver v3.5.1+incompatible h1:cQNTCjp13qL8KC3Nbxr/y2Bqb63oX6wdnnjpJbkM4JQ= @@ -31,14 +31,14 @@ github.com/cespare/xxhash/v2 v2.3.0 h1:UL815xU9SqsFlibzuggzjXhog7bL6oX9BbNZnL2UF github.com/cespare/xxhash/v2 v2.3.0/go.mod h1:VGX0DQ3Q6kWi7AoAeZDth3/j3BFtOZR5XLFGgcrjCOs= github.com/coredns/caddy v1.1.1 h1:2eYKZT7i6yxIfGP3qLJoJ7HAsDJqYB+X68g4NYjSrE0= github.com/coredns/caddy v1.1.1/go.mod h1:A6ntJQlAWuQfFlsd9hvigKbo2WS0VUs2l1e2F+BawD4= -github.com/coredns/corefile-migration v1.0.24 h1:NL/zRKijhJZLYlNnMr891DRv5jXgfd3Noons1M6oTpc= -github.com/coredns/corefile-migration v1.0.24/go.mod h1:56DPqONc3njpVPsdilEnfijCwNGC3/kTJLl7i7SPavY= +github.com/coredns/corefile-migration v1.0.26 h1:xiiEkVB1Dwolb24pkeDUDBfygV9/XsOSq79yFCrhptY= +github.com/coredns/corefile-migration v1.0.26/go.mod h1:56DPqONc3njpVPsdilEnfijCwNGC3/kTJLl7i7SPavY= github.com/coreos/go-semver v0.3.1 h1:yi21YpKnrx1gt5R+la8n5WgS0kCrsPp33dmEyHReZr4= github.com/coreos/go-semver v0.3.1/go.mod h1:irMmmIw/7yzSRPWryHsK7EYSg09caPQL03VsM8rvUec= github.com/coreos/go-systemd v0.0.0-20191104093116-d3cd4ed1dbcf h1:iW4rZ826su+pqaw19uhpSCzhj44qo35pNgKFGqzDKkU= github.com/coreos/go-systemd/v22 v22.5.0 h1:RrqgGjYQKalulkV8NGVIfkXQf6YYmOyiJKk8iXXhfZs= github.com/coreos/go-systemd/v22 v22.5.0/go.mod h1:Y58oyj3AT4RCenI/lSvhwexgC+NSVTIJ3seZv2GcEnc= -github.com/cpuguy83/go-md2man/v2 v2.0.4/go.mod h1:tgQtvFlXSQOSOSIRvRPT7W67SCa46tRHOmNcaadrF8o= +github.com/cpuguy83/go-md2man/v2 v2.0.6/go.mod h1:oOW0eioCTA6cOiMLiUPZOpcVxMig6NIQQ7OS05n1F4g= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v0.0.0-20151105211317-5215b55f46b2/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -52,18 +52,18 @@ github.com/dustin/go-humanize v1.0.1 h1:GzkhY7T5VNhEkwH0PVJgjz+fX1rhBrR7pRT3mDkp github.com/dustin/go-humanize v1.0.1/go.mod h1:Mu1zIs6XwVuF/gI1OepvI0qD18qycQx+mFykh5fBlto= github.com/elazarl/goproxy v0.0.0-20170405201442-c4fc26588b6e/go.mod h1:/Zj4wYkgs4iZTTu3o/KG3Itv/qCCa8VVMlb3i9OVuzc= github.com/emicklei/go-restful v0.0.0-20170410110728-ff4f55a20633/go.mod h1:otzb+WCGbkyDHkqmQmT5YD2WR4BBwUdeQoFo8l/7tVs= -github.com/emicklei/go-restful/v3 v3.12.1 h1:PJMDIM/ak7btuL8Ex0iYET9hxM3CI2sjZtzpL63nKAU= -github.com/emicklei/go-restful/v3 v3.12.1/go.mod h1:6n3XBCmQQb25CM2LCACGz8ukIrRry+4bhvbpWn3mrbc= +github.com/emicklei/go-restful/v3 v3.12.2 h1:DhwDP0vY3k8ZzE0RunuJy8GhNpPL6zqLkDf9B/a0/xU= +github.com/emicklei/go-restful/v3 v3.12.2/go.mod h1:6n3XBCmQQb25CM2LCACGz8ukIrRry+4bhvbpWn3mrbc= github.com/evanphx/json-patch v4.2.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= github.com/evanphx/json-patch v5.7.0+incompatible h1:vgGkfT/9f8zE6tvSCe74nfpAVDQ2tG6yudJd8LBksgI= github.com/evanphx/json-patch v5.7.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLiYLvXMP4fmwYFNcr97nuDLSk= -github.com/evanphx/json-patch/v5 v5.9.0 h1:kcBlZQbplgElYIlo/n1hJbls2z/1awpXxpRi0/FOJfg= -github.com/evanphx/json-patch/v5 v5.9.0/go.mod h1:VNkHZ/282BpEyt/tObQO8s5CMPmYYq14uClGH4abBuQ= +github.com/evanphx/json-patch/v5 v5.9.11 h1:/8HVnzMq13/3x9TPvjG08wUGqBTmZBsCWzjTM0wiaDU= +github.com/evanphx/json-patch/v5 v5.9.11/go.mod h1:3j+LviiESTElxA4p3EMKAB9HXj3/XEtnUf6OZxqIQTM= github.com/felixge/httpsnoop v1.0.4 h1:NFTV2Zj1bL4mc9sqWACXbQFVBBg2W3GPvqp8/ESS2Wg= github.com/felixge/httpsnoop v1.0.4/go.mod h1:m8KPJKqk1gH5J9DgRY2ASl2lWCfGKXixSwevea8zH2U= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= -github.com/fsnotify/fsnotify v1.7.0 h1:8JEhPFa5W2WU7YfeZzPNqzMP6Lwt7L2715Ggo0nosvA= -github.com/fsnotify/fsnotify v1.7.0/go.mod h1:40Bi/Hjc2AVfZrqy+aj+yEI+/bRxZnMJyTJwOpGvigM= +github.com/fsnotify/fsnotify v1.8.0 h1:dAwr6QBTBZIkG8roQaJjGof0pp0EeF+tNV7YBP3F/8M= +github.com/fsnotify/fsnotify v1.8.0/go.mod h1:8jBTzvmWwFyi3Pb8djgCCO5IBqzKJ/Jwo8TRcHyHii0= github.com/fxamacker/cbor/v2 v2.7.0 h1:iM5WgngdRBanHcxugY4JySA0nk1wZorNOpTgCMedv5E= github.com/fxamacker/cbor/v2 v2.7.0/go.mod h1:pxXPTn3joSm21Gbwsv0w9OSA2y1HFR9qXEeXQVeNoDQ= github.com/ghodss/yaml v0.0.0-20150909031657-73d445a93680/go.mod h1:4dBDuWmgqj2HViK6kFavaiC9ZROes6MMH2rRYeMEF04= @@ -110,20 +110,20 @@ github.com/google/gnostic-models v0.6.8 h1:yo/ABAfM5IMRsS1VnXjTBvUb61tFIHozhlYvR github.com/google/gnostic-models v0.6.8/go.mod h1:5n7qKqH0f5wFt+aWF8CW6pZLLNOfYuF5OpfBSENuI8U= github.com/google/go-cmp v0.3.0/go.mod h1:8QqcDgzrUqlUb/G2PQTWiueGozuR1884gddMywk6iLU= github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= -github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= -github.com/google/go-cmp v0.6.0/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/google/go-cmp v0.7.0 h1:wk8382ETsv4JYUZwIsn6YpYiWiBsYLSJiTsyBybVuN8= +github.com/google/go-cmp v0.7.0/go.mod h1:pXiqmnSA92OHEEa9HXL2W4E7lf9JzCmGVUdgjX3N/iU= github.com/google/gofuzz v0.0.0-20161122191042-44d81051d367/go.mod h1:HP5RmnzzSNb993RKQDq4+1A4ia9nllfqcQFTQJedwGI= github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= github.com/google/gofuzz v1.2.0 h1:xRy4A+RhZaiKjJ1bPfwQ8sedCA+YS2YcCHW6ec7JMi0= github.com/google/gofuzz v1.2.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= -github.com/google/pprof v0.0.0-20241210010833-40e02aabc2ad h1:a6HEuzUHeKH6hwfN/ZoQgRgVIWFJljSWa/zetS2WTvg= -github.com/google/pprof v0.0.0-20241210010833-40e02aabc2ad/go.mod h1:vavhavw2zAxS5dIdcRluK6cSGGPlZynqzFM8NdvU144= +github.com/google/pprof v0.0.0-20250403155104-27863c87afa6 h1:BHT72Gu3keYf3ZEu2J0b1vyeLSOYI8bm5wbJM/8yDe8= +github.com/google/pprof v0.0.0-20250403155104-27863c87afa6/go.mod h1:boTsfXsheKC2y+lKOCMpSfarhxDeIzfZG1jqGcPl3cA= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/gnostic v0.0.0-20170729233727-0c5108395e2d/go.mod h1:sJBsCZ4ayReDTBIg8b9dl28c5xFWyhBTVRp3pOg5EKY= -github.com/gorilla/websocket v1.5.0 h1:PPwGk2jz7EePpoHN/+ClbZu8SPxiqlu12wZP/3sWmnc= -github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= +github.com/gorilla/websocket v1.5.3 h1:saDtZ6Pbx/0u+bgYQ3q96pZgCzfhKXGPqt7kZ72aNNg= +github.com/gorilla/websocket v1.5.3/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= github.com/grpc-ecosystem/go-grpc-middleware v1.3.0 h1:+9834+KizmvFV7pXQGSXQTsaWhq2GjuNUt0aUU0YBYw= 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 h1:Ovs26xHkKqVztRpIrF/92BcuyuQ/YW4NSIpoGtfXNho= @@ -180,12 +180,12 @@ github.com/onsi/ginkgo v0.0.0-20170829012221-11459a886d9c/go.mod h1:lLunBs/Ym6LB github.com/onsi/ginkgo v1.6.0/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= github.com/onsi/ginkgo v1.10.1 h1:q/mM8GF/n0shIN8SaAZ0V+jnLPzen6WIVZdiwrRlMlo= github.com/onsi/ginkgo v1.10.1/go.mod h1:lLunBs/Ym6LB5Z9jYTR76FiuTmxDTDusOGeTQH+WWjE= -github.com/onsi/ginkgo/v2 v2.22.2 h1:/3X8Panh8/WwhU/3Ssa6rCKqPLuAkVY2I0RoyDLySlU= -github.com/onsi/ginkgo/v2 v2.22.2/go.mod h1:oeMosUL+8LtarXBHu/c0bx2D/K9zyQ6uX3cTyztHwsk= +github.com/onsi/ginkgo/v2 v2.23.4 h1:ktYTpKJAVZnDT4VjxSbiBenUjmlL/5QkBEocaWXiQus= +github.com/onsi/ginkgo/v2 v2.23.4/go.mod h1:Bt66ApGPBFzHyR+JO10Zbt0Gsp4uWxu5mIOTusL46e8= 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.36.2 h1:koNYke6TVk6ZmnyHrCXba/T/MoLBXFjeC1PtvYgw0A8= -github.com/onsi/gomega v1.36.2/go.mod h1:DdwyADRjrc825LhMEkD76cHR5+pUnjhUN8GlHlRPHzY= +github.com/onsi/gomega v1.37.0 h1:CdEG8g0S133B4OswTDC/5XPSzE1OeP29QOioj2PID2Y= +github.com/onsi/gomega v1.37.0/go.mod h1:8D9+Txp43QWKhM24yyOBEdpkzN8FvJyAwecBgsU4KU0= github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U= github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM= github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= @@ -211,13 +211,14 @@ github.com/sirupsen/logrus v1.9.3 h1:dueUQJ1C2q9oE3F7wvmSGAaVtTmUizReu6fjN8uqzbQ github.com/sirupsen/logrus v1.9.3/go.mod h1:naHLuLoDiP4jHNo9R0sCBMtWGeIprob74mVsIT4qYEQ= github.com/soheilhy/cmux v0.1.5 h1:jjzc5WVemNEDTLwv9tlmemhC73tI08BNOIGwBOo10Js= github.com/soheilhy/cmux v0.1.5/go.mod h1:T7TcVDs9LWfQgPlPsdngu6I6QIoyIFZDDC6sNE1GqG0= -github.com/spf13/cast v1.7.0 h1:ntdiHjuueXFgm5nzDRdOS4yfT43P5Fnud6DH50rz/7w= -github.com/spf13/cast v1.7.0/go.mod h1:ancEpBxwJDODSW/UG4rDrAqiKolqNNh2DX3mk86cAdo= -github.com/spf13/cobra v1.8.1 h1:e5/vxKd/rZsfSJMUX1agtjeTDf+qv1/JdBF8gg5k9ZM= -github.com/spf13/cobra v1.8.1/go.mod h1:wHxEcudfqmLYa8iTfL+OuZPbBZkmvliBWKIezN3kD9Y= +github.com/spf13/cast v1.7.1 h1:cuNEagBQEHWN1FnbGEjCXL2szYEXqfJPbP2HNUaca9Y= +github.com/spf13/cast v1.7.1/go.mod h1:ancEpBxwJDODSW/UG4rDrAqiKolqNNh2DX3mk86cAdo= +github.com/spf13/cobra v1.9.1 h1:CXSaggrXdbHK9CF+8ywj8Amf7PBRmPCOJugH954Nnlo= +github.com/spf13/cobra v1.9.1/go.mod h1:nDyEzZ8ogv936Cinf6g1RU9MRY64Ir93oCnqb9wxYW0= github.com/spf13/pflag v0.0.0-20170130214245-9ff6c6923cff/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/pflag v1.0.6 h1:jFzHGLGAlb3ruxLB8MhbI6A8+AQX/2eW4qeyNZXNp2o= +github.com/spf13/pflag v1.0.6/go.mod h1:McXfInJRrz4CZXVZOBLb0bTZqETkiAhM9Iw0y3An2Bg= github.com/stoewer/go-strcase v1.3.0 h1:g0eASXYtp+yvN9fK8sH94oCIk0fau9uV1/ZdJ0AVEzs= github.com/stoewer/go-strcase v1.3.0/go.mod h1:fAH5hQ5pehh+j3nZfvwdk2RgEgQjAoM8wodgtPmh1xo= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= @@ -237,14 +238,14 @@ github.com/tmc/grpc-websocket-proxy v0.0.0-20220101234140-673ab2c3ae75 h1:6fotK7 github.com/tmc/grpc-websocket-proxy v0.0.0-20220101234140-673ab2c3ae75/go.mod h1:KO6IkyS8Y3j8OdNO85qEYBsRPuteD+YciPomcXdrMnk= github.com/vmware-tanzu/net-operator-api v0.0.0-20240326163340-1f32d6bf7f9d h1:cgx9UH/r53bKU/Gbv8IPsUZ34bj5+ItijA2JCUS3kVk= github.com/vmware-tanzu/net-operator-api v0.0.0-20240326163340-1f32d6bf7f9d/go.mod h1:JbFOh22iDsT5BowJe0GgpMI5e2/S7cWaJlv9LdURVQM= -github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20240827061921-8f0982975508 h1:NBjcpxDcurBzM3uMfX7LpkDE6okU+x7XdDSqVdqXVO8= -github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20240827061921-8f0982975508/go.mod h1:Q4JzNkNMvjo7pXtlB5/R3oME4Nhah7fAObWgghVmtxk= +github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20241112044858-9da8637c1b0d h1:z9lrzKVtNlujduv9BilzPxuge/LE2F0N1ms3TP4JZvw= +github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20241112044858-9da8637c1b0d/go.mod h1:Q4JzNkNMvjo7pXtlB5/R3oME4Nhah7fAObWgghVmtxk= github.com/vmware-tanzu/vm-operator/api v1.8.6 h1:NIndORjcnSmIlQsCMIewpIwg/ocRVDh2lYjOroTVLrU= github.com/vmware-tanzu/vm-operator/api v1.8.6/go.mod h1:HHA2SNI9B5Yqtyp5t+Gt9WTWBi/fIkM6+MukDDSf11A= github.com/vmware-tanzu/vm-operator/external/ncp v0.0.0-20240404200847-de75746a9505 h1:y4wXx1FUFqqSgJ/xUOEM1DLS2Uu0KaeLADWpzpioGTU= github.com/vmware-tanzu/vm-operator/external/ncp v0.0.0-20240404200847-de75746a9505/go.mod h1:5rqRJ9zGR+KnKbkGx373WgN8xJpvAj99kHnfoDYRO5I= -github.com/vmware/govmomi v0.47.1 h1:6a2iNaqSS2/AFfvI8UMe0l787/TBKkK0KK9jCqCyYCE= -github.com/vmware/govmomi v0.47.1/go.mod h1:bYwUHpGpisE4AOlDl5eph90T+cjJMIcKx/kaa5v5rQM= +github.com/vmware/govmomi v0.49.0 h1:M80ExmFq3kOfeMvMJcHnXgA/4w5hUAFfYfc+Qm3lmPg= +github.com/vmware/govmomi v0.49.0/go.mod h1:+oZ0tYJw/pXKoeWHLR9Egq5KENVr2hLePRzisFhEWpA= github.com/x448/float16 v0.8.4 h1:qLwI1I70+NjRFUR3zs1JPUCgaCXSh3SW62uAKT1mSBM= github.com/x448/float16 v0.8.4/go.mod h1:14CWIYCyZA/cWjXOioeEpHeN/83MdbZDRQHoFcYsOfg= github.com/xiang90/probing v0.0.0-20221125231312-a49e3df8f510 h1:S2dVYn90KE98chqDkyE9Z4N61UnQd+KOfgp5Iu53llk= @@ -253,14 +254,14 @@ github.com/yuin/goldmark v1.1.27/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9de github.com/yuin/goldmark v1.2.1/go.mod h1:3hX8gzYuyVAZsxl0MRgGTJEmQBFcNTphYh9decYSb74= go.etcd.io/bbolt v1.3.11 h1:yGEzV1wPz2yVCLsD8ZAiGHhHVlczyC9d1rP43/VCRJ0= go.etcd.io/bbolt v1.3.11/go.mod h1:dksAq7YMXoljX0xu6VF5DMZGbhYYoLUalEiSySYAS4I= -go.etcd.io/etcd/api/v3 v3.5.17 h1:cQB8eb8bxwuxOilBpMJAEo8fAONyrdXTHUNcMd8yT1w= -go.etcd.io/etcd/api/v3 v3.5.17/go.mod h1:d1hvkRuXkts6PmaYk2Vrgqbv7H4ADfAKhyJqHNLJCB4= -go.etcd.io/etcd/client/pkg/v3 v3.5.17 h1:XxnDXAWq2pnxqx76ljWwiQ9jylbpC4rvkAeRVOUKKVw= -go.etcd.io/etcd/client/pkg/v3 v3.5.17/go.mod h1:4DqK1TKacp/86nJk4FLQqo6Mn2vvQFBmruW3pP14H/w= +go.etcd.io/etcd/api/v3 v3.5.20 h1:aKfz3nPZECWoZJXMSH9y6h2adXjtOHaHTGEVCuCmaz0= +go.etcd.io/etcd/api/v3 v3.5.20/go.mod h1:QqKGViq4KTgOG43dr/uH0vmGWIaoJY3ggFi6ZH0TH/U= +go.etcd.io/etcd/client/pkg/v3 v3.5.20 h1:sZIAtra+xCo56gdf6BR62to/hiie5Bwl7hQIqMzVTEM= +go.etcd.io/etcd/client/pkg/v3 v3.5.20/go.mod h1:qaOi1k4ZA9lVLejXNvyPABrVEe7VymMF2433yyRQ7O0= go.etcd.io/etcd/client/v2 v2.305.16 h1:kQrn9o5czVNaukf2A2At43cE9ZtWauOtf9vRZuiKXow= go.etcd.io/etcd/client/v2 v2.305.16/go.mod h1:h9YxWCzcdvZENbfzBTFCnoNumr2ax3F19sKMqHFmXHE= -go.etcd.io/etcd/client/v3 v3.5.17 h1:o48sINNeWz5+pjy/Z0+HKpj/xSnBkuVhVvXkjEXbqZY= -go.etcd.io/etcd/client/v3 v3.5.17/go.mod h1:j2d4eXTHWkT2ClBgnnEPm/Wuu7jsqku41v9DZ3OtjQo= +go.etcd.io/etcd/client/v3 v3.5.20 h1:jMT2MwQEhyvhQg49Cec+1ZHJzfUf6ZgcmV0GjPv0tIQ= +go.etcd.io/etcd/client/v3 v3.5.20/go.mod h1:J5lbzYRMUR20YolS5UjlqqMcu3/wdEvG5VNBhzyo3m0= go.etcd.io/etcd/pkg/v3 v3.5.16 h1:cnavs5WSPWeK4TYwPYfmcr3Joz9BH+TZ6qoUtz6/+mc= go.etcd.io/etcd/pkg/v3 v3.5.16/go.mod h1:+lutCZHG5MBBFI/U4eYT5yL7sJfnexsoM20Y0t2uNuY= go.etcd.io/etcd/raft/v3 v3.5.16 h1:zBXA3ZUpYs1AwiLGPafYAKKl/CORn/uaxYDwlNwndAk= @@ -269,22 +270,24 @@ go.etcd.io/etcd/server/v3 v3.5.16 h1:d0/SAdJ3vVsZvF8IFVb1k8zqMZ+heGcNfft71ul9GWE go.etcd.io/etcd/server/v3 v3.5.16/go.mod h1:ynhyZZpdDp1Gq49jkUg5mfkDWZwXnn3eIqCqtJnrD/s= go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.53.0 h1:9G6E0TXzGFVfTnawRzrPl83iHOAV7L8NJiR8RSGYV1g= go.opentelemetry.io/contrib/instrumentation/google.golang.org/grpc/otelgrpc v0.53.0/go.mod h1:azvtTADFQJA8mX80jIH/akaE7h+dbm/sVuaHqN13w74= -go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.53.0 h1:4K4tsIXefpVJtvA/8srF4V4y0akAoPHkIslgAkjixJA= -go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.53.0/go.mod h1:jjdQuTGVsXV4vSs+CJ2qYDeDPf9yIJV23qlIzBm73Vg= -go.opentelemetry.io/otel v1.28.0 h1:/SqNcYk+idO0CxKEUOtKQClMK/MimZihKYMruSMViUo= -go.opentelemetry.io/otel v1.28.0/go.mod h1:q68ijF8Fc8CnMHKyzqL6akLO46ePnjkgfIMIjUIX9z4= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.54.0 h1:TT4fX+nBOA/+LUkobKGW1ydGcn+G3vRw9+g5HwCphpk= +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.54.0/go.mod h1:L7UH0GbB0p47T4Rri3uHjbpCFYrVrwc1I25QhNPiGK8= +go.opentelemetry.io/otel v1.29.0 h1:PdomN/Al4q/lN6iBJEN3AwPvUiHPMlt93c8bqTG5Llw= +go.opentelemetry.io/otel v1.29.0/go.mod h1:N/WtXPs1CNCUEx+Agz5uouwCba+i+bJGFicT8SR4NP8= go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.28.0 h1:3Q/xZUyC1BBkualc9ROb4G8qkH90LXEIICcs5zv1OYY= go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.28.0/go.mod h1:s75jGIWA9OfCMzF0xr+ZgfrB5FEbbV7UuYo32ahUiFI= go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.27.0 h1:qFffATk0X+HD+f1Z8lswGiOQYKHRlzfmdJm0wEaVrFA= go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.27.0/go.mod h1:MOiCmryaYtc+V0Ei+Tx9o5S1ZjA7kzLucuVuyzBZloQ= -go.opentelemetry.io/otel/metric v1.28.0 h1:f0HGvSl1KRAU1DLgLGFjrwVyismPlnuU6JD6bOeuA5Q= -go.opentelemetry.io/otel/metric v1.28.0/go.mod h1:Fb1eVBFZmLVTMb6PPohq3TO9IIhUisDsbJoL/+uQW4s= -go.opentelemetry.io/otel/sdk v1.28.0 h1:b9d7hIry8yZsgtbmM0DKyPWMMUMlK9NEKuIG4aBqWyE= -go.opentelemetry.io/otel/sdk v1.28.0/go.mod h1:oYj7ClPUA7Iw3m+r7GeEjz0qckQRJK2B8zjcZEfu7Pg= -go.opentelemetry.io/otel/trace v1.28.0 h1:GhQ9cUuQGmNDd5BTCP2dAvv75RdMxEfTmYejp+lkx9g= -go.opentelemetry.io/otel/trace v1.28.0/go.mod h1:jPyXzNPg6da9+38HEwElrQiHlVMTnVfM3/yv2OlIHaI= +go.opentelemetry.io/otel/metric v1.29.0 h1:vPf/HFWTNkPu1aYeIsc98l4ktOQaL6LeSoeV2g+8YLc= +go.opentelemetry.io/otel/metric v1.29.0/go.mod h1:auu/QWieFVWx+DmQOUMgj0F8LHWdgalxXqvp7BII/W8= +go.opentelemetry.io/otel/sdk v1.29.0 h1:vkqKjk7gwhS8VaWb0POZKmIEDimRCMsopNYnriHyryo= +go.opentelemetry.io/otel/sdk v1.29.0/go.mod h1:pM8Dx5WKnvxLCb+8lG1PRNIDxu9g9b9g59Qr7hfAAok= +go.opentelemetry.io/otel/trace v1.29.0 h1:J/8ZNK4XgR7a21DZUAsbF8pZ5Jcw1VhACmnYt39JTi4= +go.opentelemetry.io/otel/trace v1.29.0/go.mod h1:eHl3w0sp3paPkYstJOmAimxhiFXPg+MMTlEh3nsQgWQ= go.opentelemetry.io/proto/otlp v1.3.1 h1:TrMUixzpM0yuc/znrFTP9MMRh8trP93mkCiDVeXrui0= go.opentelemetry.io/proto/otlp v1.3.1/go.mod h1:0X1WI4de4ZsLrrJNLAQbFeLCm3T7yBkR0XqQ7niQU+8= +go.uber.org/automaxprocs v1.6.0 h1:O3y2/QNTOdbF+e/dpXNNW7Rx2hZ4sTIPyybbxyNqTUs= +go.uber.org/automaxprocs v1.6.0/go.mod h1:ifeIMSnPZuznNm6jmdzmU3/bfk01Fe2fotchwEFJ8r8= go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto= go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE= go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0= @@ -294,14 +297,14 @@ go.uber.org/zap v1.27.0/go.mod h1:GB2qFLM7cTU87MWRP2mPIjqfIDnGu+VIO4V/SdhGo2E= golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= 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= -golang.org/x/crypto v0.32.0 h1:euUpcYgM8WcP71gNpTqQCn6rC2t6ULUPiOzfWaXVVfc= -golang.org/x/crypto v0.32.0/go.mod h1:ZnnJkOaASj8g0AjIduWNlq2NRxL0PlBrbKVyZ6V/Ugc= +golang.org/x/crypto v0.36.0 h1:AnAEvhDddvBdpY+uR+MyHmuZzzNqXSe/GvuDeob5L34= +golang.org/x/crypto v0.36.0/go.mod h1:Y4J0ReaxCR1IMaabaSMugxJES1EpwhBHhv2bDHklZvc= golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56 h1:2dVuKD2vS7b0QIHQbpyTISPd0LeHDbnYEryqj5Q1ug8= golang.org/x/exp v0.0.0-20240719175910-8a7402abbf56/go.mod h1:M4RDyNAINzryxdtnbRXRL/OHtkFuWGRjvuhBJpk2IlY= 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.22.0 h1:D4nJWe9zXqHOmWqj4VMOJhvzj7bEZg4wEYa759z1pH4= -golang.org/x/mod v0.22.0/go.mod h1:6SkKJ3Xj0I0BrPOZoBy3bdMptDDU9oJrpohJ3eWZ1fY= +golang.org/x/mod v0.24.0 h1:ZfthKaKaT4NrhGVZHO1/WDTwGES4De8KtWO0SIbNJMU= +golang.org/x/mod v0.24.0/go.mod h1:IXM97Txy2VM4PJ3gI61r1YEk/gAj6zAHN3AdZt6S9Ww= golang.org/x/net v0.0.0-20170114055629-f2499483f923/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180906233101-161cd47e91fd/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20190404232315-eb5bcb51f2a3/go.mod h1:t9HGtf8HONx5eT2rtn7q6eTqICYqUVnKs3thJo3Qplg= @@ -309,58 +312,58 @@ golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLL golang.org/x/net v0.0.0-20191004110552-13f9640d40b9/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20200226121028-0de0cce0169b/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= golang.org/x/net v0.0.0-20201021035429-f5854403a974/go.mod h1:sp8m0HH+o8qH0wwXwYZr8TS3Oi6o0r6Gce1SSxlDquU= -golang.org/x/net v0.34.0 h1:Mb7Mrk043xzHgnRM88suvJFwzVrRfHEHJEl5/71CKw0= -golang.org/x/net v0.34.0/go.mod h1:di0qlW3YNM5oh6GqDGQr92MyTozJPmybPK4Ev/Gm31k= -golang.org/x/oauth2 v0.25.0 h1:CY4y7XT9v0cRI9oupztF8AgiIu99L/ksR/Xp/6jrZ70= -golang.org/x/oauth2 v0.25.0/go.mod h1:XYTD2NtWslqkgxebSiOHnXEap4TF09sJSc7H1sXbhtI= +golang.org/x/net v0.38.0 h1:vRMAPTMaeGqVhG5QyLJHqNDwecKTomGeqbnfZyKlBI8= +golang.org/x/net v0.38.0/go.mod h1:ivrbrMbzFq5J41QOQh0siUuly180yBYtLp+CKbEaFx8= +golang.org/x/oauth2 v0.28.0 h1:CrgCKl8PPAVtLnU3c+EDw6x11699EWlsDeWNWKdIOkc= +golang.org/x/oauth2 v0.28.0/go.mod h1:onh5ek6nERTohokkhCD/y2cV4Do3fxFHFuAejCkRWT8= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20190911185100-cd5d95a43a6e/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= -golang.org/x/sync v0.10.0 h1:3NQrjDixjgGwUOCaF8w2+VYHv0Ve/vGYSbdkTa98gmQ= -golang.org/x/sync v0.10.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/sync v0.12.0 h1:MHc5BpPuC30uJk597Ri8TV3CNZcTLu6B6z4lJy+g6Jw= +golang.org/x/sync v0.12.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA= golang.org/x/sys v0.0.0-20170830134202-bb24a47a89ea/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20190412213103-97732733099d/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20190826190057-c7b8b68b1456/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20200930185726-fdedc70b468f/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.29.0 h1:TPYlXGxvx1MGTn2GiZDhnjPA9wZzZeGKHHmKhHYvgaU= -golang.org/x/sys v0.29.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/term v0.28.0 h1:/Ts8HFuMR2E6IP/jlo7QVLZHggjKQbhu/7H0LJFr3Gg= -golang.org/x/term v0.28.0/go.mod h1:Sw/lC2IAUZ92udQNf3WodGtn4k/XoLyZoh8v/8uiwek= +golang.org/x/sys v0.32.0 h1:s77OFDvIQeibCmezSnk/q6iAfkdiQaJi4VzroCFrN20= +golang.org/x/sys v0.32.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= +golang.org/x/term v0.30.0 h1:PQ39fJZ+mfadBm0y5WlL4vlM7Sx1Hgf13sMIY2+QS9Y= +golang.org/x/term v0.30.0/go.mod h1:NYYFdzHoI5wRh/h5tDMdMqCqPJZEuNqVR5xJLd/n67g= golang.org/x/text v0.0.0-20160726164857-2910a502d2bf/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= -golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo= -golang.org/x/text v0.21.0/go.mod h1:4IBbMaMmOPCJ8SecivzSH54+73PCFmPWxNTLm+vZkEQ= -golang.org/x/time v0.7.0 h1:ntUhktv3OPE6TgYxXWv9vKvUSJyIFJlyohwbkEwPrKQ= -golang.org/x/time v0.7.0/go.mod h1:3BpzKBy/shNhVucY/MWOyx10tF3SFh9QdLuxbVysPQM= +golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY= +golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4= +golang.org/x/time v0.8.0 h1:9i3RxcPv3PZnitoVGMPDKZSq1xW1gK1Xy3ArNOGZfEg= +golang.org/x/time v0.8.0/go.mod h1:3BpzKBy/shNhVucY/MWOyx10tF3SFh9QdLuxbVysPQM= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= golang.org/x/tools v0.0.0-20181011042414-1f849cf54d09/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-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= golang.org/x/tools v0.0.0-20200619180055-7c47624df98f/go.mod h1:EkVYQZoAsY45+roYkvgYkIh4xh/qjgUK9TdY2XT94GE= golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= -golang.org/x/tools v0.29.0 h1:Xx0h3TtM9rzQpQuR4dKLrdglAmCEN5Oi+P74JdhdzXE= -golang.org/x/tools v0.29.0/go.mod h1:KMQVMRsVxU6nHCFXrBPhDB8XncLNLM0lIy/F14RP588= +golang.org/x/tools v0.31.0 h1:0EedkvKDbh+qistFTd0Bcwe/YLh4vHwWEkiI0toFIBU= +golang.org/x/tools v0.31.0/go.mod h1:naFTU+Cev749tSJRXJlna0T3WxKvb1kWEx15xA4SdmQ= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -gomodules.xyz/jsonpatch/v2 v2.4.0 h1:Ci3iUJyx9UeRx7CeFN8ARgGbkESwJK+KB9lLcWxY/Zw= -gomodules.xyz/jsonpatch/v2 v2.4.0/go.mod h1:AH3dM2RI6uoBZxn3LVrfvJ3E0/9dG4cSrbuBJT4moAY= +gomodules.xyz/jsonpatch/v2 v2.5.0 h1:JELs8RLM12qJGXU4u/TO3V25KW8GreMKl9pdkk14RM0= +gomodules.xyz/jsonpatch/v2 v2.5.0/go.mod h1:AH3dM2RI6uoBZxn3LVrfvJ3E0/9dG4cSrbuBJT4moAY= google.golang.org/genproto v0.0.0-20240123012728-ef4313101c80 h1:KAeGQVN3M9nD0/bQXnr/ClcEMJ968gUXJQ9pwfSynuQ= google.golang.org/genproto v0.0.0-20240123012728-ef4313101c80/go.mod h1:cc8bqMqtv9gMOr0zHg2Vzff5ULhhL2IXP4sbcn32Dro= -google.golang.org/genproto/googleapis/api v0.0.0-20240826202546-f6391c0de4c7 h1:YcyjlL1PRr2Q17/I0dPk2JmYS5CDXfcdb2Z3YRioEbw= -google.golang.org/genproto/googleapis/api v0.0.0-20240826202546-f6391c0de4c7/go.mod h1:OCdP9MfskevB/rbYvHTsXTtKC+3bHWajPdoKgjcYkfo= -google.golang.org/genproto/googleapis/rpc v0.0.0-20240826202546-f6391c0de4c7 h1:2035KHhUv+EpyB+hWgJnaWKJOdX1E95w2S8Rr4uWKTs= -google.golang.org/genproto/googleapis/rpc v0.0.0-20240826202546-f6391c0de4c7/go.mod h1:UqMtugtsSgubUsoxbuAoiCXvqvErP7Gf0so0mK9tHxU= -google.golang.org/grpc v1.65.1 h1:toSN4j5/Xju+HVovfaY5g1YZVuJeHzQZhP8eJ0L0f1I= -google.golang.org/grpc v1.65.1/go.mod h1:WgYC2ypjlB0EiQi6wdKixMqukr6lBc0Vo+oOgjrM5ZQ= -google.golang.org/protobuf v1.36.1 h1:yBPeRvTftaleIgM3PZ/WBIZ7XM/eEYAaEyCwvyjq/gk= -google.golang.org/protobuf v1.36.1/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE= +google.golang.org/genproto/googleapis/api v0.0.0-20241209162323-e6fa225c2576 h1:CkkIfIt50+lT6NHAVoRYEyAvQGFM7xEwXUUywFvEb3Q= +google.golang.org/genproto/googleapis/api v0.0.0-20241209162323-e6fa225c2576/go.mod h1:1R3kvZ1dtP3+4p4d3G8uJ8rFk/fWlScl38vanWACI08= +google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8 h1:TqExAhdPaB60Ux47Cn0oLV07rGnxZzIsaRhQaqS666A= +google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8/go.mod h1:lcTa1sDdWEIHMWlITnIczmw5w60CF9ffkb8Z+DVmmjA= +google.golang.org/grpc v1.67.3 h1:OgPcDAFKHnH8X3O4WcO4XUc8GRDeKsKReqbQtiCj7N8= +google.golang.org/grpc v1.67.3/go.mod h1:YGaHCc6Oap+FzBJTZLBzkGSYt/cvGPFTPxkn7QfSU8s= +google.golang.org/protobuf v1.36.5 h1:tPhr+woSbjfYvY6/GPufUoYizxw1cF/yFoxJ2fmpwlM= +google.golang.org/protobuf v1.36.5/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20180628173108-788fd7840127/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/check.v1 v1.0.0-20201130134442-10cb98267c6c h1:Hei/4ADfdWqJk1ZMxUNpqntNwaWcugrBjAiHlqqRiVk= @@ -386,21 +389,21 @@ 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.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -k8s.io/api v0.32.1 h1:f562zw9cy+GvXzXf0CKlVQ7yHJVYzLfL6JAS4kOAaOc= -k8s.io/api v0.32.1/go.mod h1:/Yi/BqkuueW1BgpoePYBRdDYfjPF5sgTr5+YqDZra5k= -k8s.io/apiextensions-apiserver v0.32.1 h1:hjkALhRUeCariC8DiVmb5jj0VjIc1N0DREP32+6UXZw= -k8s.io/apiextensions-apiserver v0.32.1/go.mod h1:sxWIGuGiYov7Io1fAS2X06NjMIk5CbRHc2StSmbaQto= +k8s.io/api v0.32.3 h1:Hw7KqxRusq+6QSplE3NYG4MBxZw1BZnq4aP4cJVINls= +k8s.io/api v0.32.3/go.mod h1:2wEDTXADtm/HA7CCMD8D8bK4yuBUptzaRhYcYEEYA3k= +k8s.io/apiextensions-apiserver v0.32.3 h1:4D8vy+9GWerlErCwVIbcQjsWunF9SUGNu7O7hiQTyPY= +k8s.io/apiextensions-apiserver v0.32.3/go.mod h1:8YwcvVRMVzw0r1Stc7XfGAzB/SIVLunqApySV5V7Dss= k8s.io/apimachinery v0.17.4/go.mod h1:gxLnyZcGNdZTCLnq3fgzyg2A5BVCHTNDFrw8AmuJ+0g= -k8s.io/apimachinery v0.32.1 h1:683ENpaCBjma4CYqsmZyhEzrGz6cjn1MY/X2jB2hkZs= -k8s.io/apimachinery v0.32.1/go.mod h1:GpHVgxoKlTxClKcteaeuF1Ul/lDVb74KpZcxcmLDElE= -k8s.io/apiserver v0.32.1 h1:oo0OozRos66WFq87Zc5tclUX2r0mymoVHRq8JmR7Aak= -k8s.io/apiserver v0.32.1/go.mod h1:UcB9tWjBY7aryeI5zAgzVJB/6k7E97bkr1RgqDz0jPw= -k8s.io/client-go v0.32.1 h1:otM0AxdhdBIaQh7l1Q0jQpmo7WOFIk5FFa4bg6YMdUU= -k8s.io/client-go v0.32.1/go.mod h1:aTTKZY7MdxUaJ/KiUs8D+GssR9zJZi77ZqtzcGXIiDg= -k8s.io/cluster-bootstrap v0.32.1 h1:sHOsbrfWn2EDZus/vwPX2IE1wCw2CuByrIFcaY3zDMo= -k8s.io/cluster-bootstrap v0.32.1/go.mod h1:AAoSp7mIY02P2QBRYoFglKobjD++rPzAdlQeUYObVkA= -k8s.io/component-base v0.32.1 h1:/5IfJ0dHIKBWysGV0yKTFfacZ5yNV1sulPh3ilJjRZk= -k8s.io/component-base v0.32.1/go.mod h1:j1iMMHi/sqAHeG5z+O9BFNCF698a1u0186zkjMZQ28w= +k8s.io/apimachinery v0.32.3 h1:JmDuDarhDmA/Li7j3aPrwhpNBA94Nvk5zLeOge9HH1U= +k8s.io/apimachinery v0.32.3/go.mod h1:GpHVgxoKlTxClKcteaeuF1Ul/lDVb74KpZcxcmLDElE= +k8s.io/apiserver v0.32.3 h1:kOw2KBuHOA+wetX1MkmrxgBr648ksz653j26ESuWNY8= +k8s.io/apiserver v0.32.3/go.mod h1:q1x9B8E/WzShF49wh3ADOh6muSfpmFL0I2t+TG0Zdgc= +k8s.io/client-go v0.32.3 h1:RKPVltzopkSgHS7aS98QdscAgtgah/+zmpAogooIqVU= +k8s.io/client-go v0.32.3/go.mod h1:3v0+3k4IcT9bXTc4V2rt+d2ZPPG700Xy6Oi0Gdl2PaY= +k8s.io/cluster-bootstrap v0.32.3 h1:AqIpsUhB6MUeaAsl1WvaUw54AHRd2hfZrESlKChtd8s= +k8s.io/cluster-bootstrap v0.32.3/go.mod h1:CHbBwgOb6liDV6JFUTkx5t85T2xidy0sChBDoyYw344= +k8s.io/component-base v0.32.3 h1:98WJvvMs3QZ2LYHBzvltFSeJjEx7t5+8s71P7M74u8k= +k8s.io/component-base v0.32.3/go.mod h1:LWi9cR+yPAv7cu2X9rZanTiFKB2kHA+JjmhkKjCZRpI= k8s.io/gengo v0.0.0-20190128074634-0689ccc1d7d6/go.mod h1:ezvh/TsK7cY6rbqRK0oQQ8IAqLxYwwyPxAX1Pzy0ii0= k8s.io/klog v0.0.0-20181102134211-b9b56d5dfc92/go.mod h1:Gq+BEi5rUBO/HRz0bTSXDUcqjScdoY3a9IHpCEIOOfk= k8s.io/klog v1.0.0/go.mod h1:4Bi6QPql/J/LkTDqv7R/cd3hPo4k2DG6Ptcz060Ez5I= @@ -413,12 +416,12 @@ k8s.io/utils v0.0.0-20241104100929-3ea5e8cea738 h1:M3sRQVHv7vB20Xc2ybTt7ODCeFj6J k8s.io/utils v0.0.0-20241104100929-3ea5e8cea738/go.mod h1:OLgZIPagt7ERELqWJFomSt595RzquPNLL48iOWgYOg0= sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.31.0 h1:CPT0ExVicCzcpeN4baWEV2ko2Z/AsiZgEdwgcfwLgMo= sigs.k8s.io/apiserver-network-proxy/konnectivity-client v0.31.0/go.mod h1:Ve9uj1L+deCXFrPOk1LpFXqTg7LCFzFso6PA48q/XZw= -sigs.k8s.io/cluster-api v1.9.1 h1:s2YUB66XceK+EQ3Uq8Mq/N9TgqRU4TQUMsaQYXOIWlU= -sigs.k8s.io/cluster-api v1.9.1/go.mod h1:pkFqVPq0ELlJgyDjgqpb4MU1XnWEi98B2q3DbEjC4ww= -sigs.k8s.io/cluster-api-provider-vsphere v1.12.0-rc.0.0.20250203113257-38f6b67f9b7d h1:ZCzkwN471hfFSojkpSd1qbE2vSICLzr/R07g809MDbE= -sigs.k8s.io/cluster-api-provider-vsphere v1.12.0-rc.0.0.20250203113257-38f6b67f9b7d/go.mod h1:lmndKLUl+IXEFwEhC7PhkdeQJID8CkpLrwOM3in/A38= -sigs.k8s.io/controller-runtime v0.20.1 h1:JbGMAG/X94NeM3xvjenVUaBjy6Ui4Ogd/J5ZtjZnHaE= -sigs.k8s.io/controller-runtime v0.20.1/go.mod h1:BrP3w158MwvB3ZbNpaAcIKkHQ7YGpYnzpoSTZ8E14WU= +sigs.k8s.io/cluster-api v1.10.1 h1:5vsLNgQ4SkPudJ1USK532B0SIdJxRsCNKt2DZtBf+ww= +sigs.k8s.io/cluster-api v1.10.1/go.mod h1:aiPMrNPoaJc/GuJ4TCpWX8bVe11+iCJ4HI0f3c9QiJg= +sigs.k8s.io/cluster-api-provider-vsphere v1.13.1 h1:lCAPq0Ac96eDdcC2stsUh8GRAHd4W0nS/SewroDEedE= +sigs.k8s.io/cluster-api-provider-vsphere v1.13.1/go.mod h1:GlRQVTpd6wKWccWZk64bvlz1f52gRQ0LOxkXSBFstVU= +sigs.k8s.io/controller-runtime v0.20.4 h1:X3c+Odnxz+iPTRobG4tp092+CvBU9UK0t/bRf+n0DGU= +sigs.k8s.io/controller-runtime v0.20.4/go.mod h1:xg2XB0K5ShQzAgsoujxuKN4LNXR2LfwwHsPj7Iaw+XY= sigs.k8s.io/json v0.0.0-20241010143419-9aa6b5e7a4b3 h1:/Rv+M11QRah1itp8VhT6HoVx1Ray9eB4DBr+K+/sCJ8= sigs.k8s.io/json v0.0.0-20241010143419-9aa6b5e7a4b3/go.mod h1:18nIHnGi6636UCz6m8i4DhaJ65T6EruyzmoQqI2BVDo= sigs.k8s.io/structured-merge-diff v0.0.0-20190525122527-15d366b2352e/go.mod h1:wWxsB5ozmmv/SG7nM11ayaAW51xMvak/t1r0CSlcokI= diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.gitignore b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.gitignore deleted file mode 100644 index 8d69a9418aa..00000000000 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.gitignore +++ /dev/null @@ -1,15 +0,0 @@ -bin/ -.idea/ -# Binaries for programs and plugins -*.exe -*.exe~ -*.dll -*.so -*.dylib - -# Test binary, built with `go test -c` -*.test - -# Output of the go coverage tool, specifically when used with LiteIDE -*.out - diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.travis.yml b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.travis.yml index bb83c6670df..e29f8eef5ef 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.travis.yml +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/.travis.yml @@ -1,12 +1,14 @@ language: go -dist: xenial + go: - - '1.10' - - '1.11' - - '1.12' - - '1.13' - - 'tip' + - 1.1 + - 1.2 + - 1.3 + - 1.4 + - 1.5 + - 1.6 + - tip -script: - - go test -coverpkg=./... -coverprofile=coverage.info -timeout=5s - - bash <(curl -s https://codecov.io/bash) +notifications: + email: + - bwatas@gmail.com diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CODE_OF_CONDUCT.md b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CODE_OF_CONDUCT.md deleted file mode 100644 index 4b462b0d81b..00000000000 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CODE_OF_CONDUCT.md +++ /dev/null @@ -1,43 +0,0 @@ -# Contributor Code of Conduct - -This project adheres to [The Code Manifesto](http://codemanifesto.com) -as its guidelines for contributor interactions. - -## The Code Manifesto - -We want to work in an ecosystem that empowers developers to reach their -potential — one that encourages growth and effective collaboration. A space -that is safe for all. - -A space such as this benefits everyone that participates in it. It encourages -new developers to enter our field. It is through discussion and collaboration -that we grow, and through growth that we improve. - -In the effort to create such a place, we hold to these values: - -1. **Discrimination limits us.** This includes discrimination on the basis of - race, gender, sexual orientation, gender identity, age, nationality, - technology and any other arbitrary exclusion of a group of people. -2. **Boundaries honor us.** Your comfort levels are not everyone’s comfort - levels. Remember that, and if brought to your attention, heed it. -3. **We are our biggest assets.** None of us were born masters of our trade. - Each of us has been helped along the way. Return that favor, when and where - you can. -4. **We are resources for the future.** As an extension of #3, share what you - know. Make yourself a resource to help those that come after you. -5. **Respect defines us.** Treat others as you wish to be treated. Make your - discussions, criticisms and debates from a position of respectfulness. Ask - yourself, is it true? Is it necessary? Is it constructive? Anything less is - unacceptable. -6. **Reactions require grace.** Angry responses are valid, but abusive language - and vindictive actions are toxic. When something happens that offends you, - handle it assertively, but be respectful. Escalate reasonably, and try to - allow the offender an opportunity to explain themselves, and possibly - correct the issue. -7. **Opinions are just that: opinions.** Each and every one of us, due to our - background and upbringing, have varying opinions. That is perfectly - acceptable. Remember this: if you respect your own opinions, you should - respect the opinions of others. -8. **To err is human.** You might not intend it, but mistakes do happen and - contribute to build experience. Tolerate honest mistakes, and don't - hesitate to apologize if you make one yourself. diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CONTRIBUTING.md b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CONTRIBUTING.md index 7ed268a1edd..f0f7e3a8add 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CONTRIBUTING.md +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/CONTRIBUTING.md @@ -11,7 +11,7 @@ If you don't know what to do, there are some features and functions that need to - [ ] Update actual [list of functions](https://github.com/asaskevich/govalidator#list-of-functions) - [ ] Update [list of validators](https://github.com/asaskevich/govalidator#validatestruct-2) that available for `ValidateStruct` and add new - [ ] Implement new validators: `IsFQDN`, `IsIMEI`, `IsPostalCode`, `IsISIN`, `IsISRC` etc -- [x] Implement [validation by maps](https://github.com/asaskevich/govalidator/issues/224) +- [ ] Implement [validation by maps](https://github.com/asaskevich/govalidator/issues/224) - [ ] Implement fuzzing testing - [ ] Implement some struct/map/array utilities - [ ] Implement map/array validation @@ -37,7 +37,7 @@ Anyone can file an expense. If the expense makes sense for the development of th ### Contributors Thank you to all the people who have already contributed to govalidator! - + ### Backers diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/LICENSE b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/LICENSE index cacba910240..2f9a31fadf6 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/LICENSE +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2014-2020 Alex Saskevich +Copyright (c) 2014 Alex Saskevich Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/README.md b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/README.md index 2c3fc35eb64..40f9a87811b 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/README.md +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/README.md @@ -1,8 +1,7 @@ govalidator =========== -[![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/asaskevich/govalidator?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge) [![GoDoc](https://godoc.org/github.com/asaskevich/govalidator?status.png)](https://godoc.org/github.com/asaskevich/govalidator) -[![Build Status](https://travis-ci.org/asaskevich/govalidator.svg?branch=master)](https://travis-ci.org/asaskevich/govalidator) -[![Coverage](https://codecov.io/gh/asaskevich/govalidator/branch/master/graph/badge.svg)](https://codecov.io/gh/asaskevich/govalidator) [![Go Report Card](https://goreportcard.com/badge/github.com/asaskevich/govalidator)](https://goreportcard.com/report/github.com/asaskevich/govalidator) [![GoSearch](http://go-search.org/badge?id=github.com%2Fasaskevich%2Fgovalidator)](http://go-search.org/view?id=github.com%2Fasaskevich%2Fgovalidator) [![Backers on Open Collective](https://opencollective.com/govalidator/backers/badge.svg)](#backers) [![Sponsors on Open Collective](https://opencollective.com/govalidator/sponsors/badge.svg)](#sponsors) [![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator.svg?type=shield)](https://app.fossa.io/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator?ref=badge_shield) +[![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/asaskevich/govalidator?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge) [![GoDoc](https://godoc.org/github.com/asaskevich/govalidator?status.png)](https://godoc.org/github.com/asaskevich/govalidator) [![Coverage Status](https://img.shields.io/coveralls/asaskevich/govalidator.svg)](https://coveralls.io/r/asaskevich/govalidator?branch=master) [![wercker status](https://app.wercker.com/status/1ec990b09ea86c910d5f08b0e02c6043/s "wercker status")](https://app.wercker.com/project/bykey/1ec990b09ea86c910d5f08b0e02c6043) +[![Build Status](https://travis-ci.org/asaskevich/govalidator.svg?branch=master)](https://travis-ci.org/asaskevich/govalidator) [![Go Report Card](https://goreportcard.com/badge/github.com/asaskevich/govalidator)](https://goreportcard.com/report/github.com/asaskevich/govalidator) [![GoSearch](http://go-search.org/badge?id=github.com%2Fasaskevich%2Fgovalidator)](http://go-search.org/view?id=github.com%2Fasaskevich%2Fgovalidator) [![Backers on Open Collective](https://opencollective.com/govalidator/backers/badge.svg)](#backers) [![Sponsors on Open Collective](https://opencollective.com/govalidator/sponsors/badge.svg)](#sponsors) [![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator.svg?type=shield)](https://app.fossa.io/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator?ref=badge_shield) A package of validators and sanitizers for strings, structs and collections. Based on [validator.js](https://github.com/chriso/validator.js). @@ -14,7 +13,7 @@ Type the following command in your terminal: or you can get specified release of the package with `gopkg.in`: - go get gopkg.in/asaskevich/govalidator.v10 + go get gopkg.in/asaskevich/govalidator.v4 After it the package is ready to use. @@ -84,14 +83,14 @@ This was changed to prevent data races when accessing custom validators. import "github.com/asaskevich/govalidator" // before -govalidator.CustomTypeTagMap["customByteArrayValidator"] = func(i interface{}, o interface{}) bool { +govalidator.CustomTypeTagMap["customByteArrayValidator"] = CustomTypeValidator(func(i interface{}, o interface{}) bool { // ... -} +}) // after -govalidator.CustomTypeTagMap.Set("customByteArrayValidator", func(i interface{}, o interface{}) bool { +govalidator.CustomTypeTagMap.Set("customByteArrayValidator", CustomTypeValidator(func(i interface{}, o interface{}) bool { // ... -}) +})) ``` #### List of functions: @@ -109,34 +108,23 @@ func Filter(array []interface{}, iterator ConditionIterator) []interface{} func Find(array []interface{}, iterator ConditionIterator) interface{} func GetLine(s string, index int) (string, error) func GetLines(s string) []string -func HasLowerCase(str string) bool -func HasUpperCase(str string) bool -func HasWhitespace(str string) bool -func HasWhitespaceOnly(str string) bool -func InRange(value interface{}, left interface{}, right interface{}) bool -func InRangeFloat32(value, left, right float32) bool -func InRangeFloat64(value, left, right float64) bool -func InRangeInt(value, left, right interface{}) bool +func InRange(value, left, right float64) bool func IsASCII(str string) bool func IsAlpha(str string) bool func IsAlphanumeric(str string) bool func IsBase64(str string) bool func IsByteLength(str string, min, max int) bool func IsCIDR(str string) bool -func IsCRC32(str string) bool -func IsCRC32b(str string) bool func IsCreditCard(str string) bool func IsDNSName(str string) bool func IsDataURI(str string) bool func IsDialString(str string) bool func IsDivisibleBy(str, num string) bool func IsEmail(str string) bool -func IsExistingEmail(email string) bool func IsFilePath(str string) (bool, int) func IsFloat(str string) bool func IsFullWidth(str string) bool func IsHalfWidth(str string) bool -func IsHash(str string, algorithm string) bool func IsHexadecimal(str string) bool func IsHexcolor(str string) bool func IsHost(str string) bool @@ -148,27 +136,22 @@ func IsISBN10(str string) bool func IsISBN13(str string) bool func IsISO3166Alpha2(str string) bool func IsISO3166Alpha3(str string) bool -func IsISO4217(str string) bool func IsISO693Alpha2(str string) bool func IsISO693Alpha3b(str string) bool +func IsISO4217(str string) bool func IsIn(str string, params ...string) bool -func IsInRaw(str string, params ...string) bool func IsInt(str string) bool func IsJSON(str string) bool func IsLatitude(str string) bool func IsLongitude(str string) bool func IsLowerCase(str string) bool func IsMAC(str string) bool -func IsMD4(str string) bool -func IsMD5(str string) bool -func IsMagnetURI(str string) bool func IsMongoID(str string) bool func IsMultibyte(str string) bool func IsNatural(value float64) bool func IsNegative(value float64) bool func IsNonNegative(value float64) bool func IsNonPositive(value float64) bool -func IsNotNull(str string) bool func IsNull(str string) bool func IsNumeric(str string) bool func IsPort(str string) bool @@ -177,24 +160,11 @@ func IsPrintableASCII(str string) bool func IsRFC3339(str string) bool func IsRFC3339WithoutZone(str string) bool func IsRGBcolor(str string) bool -func IsRegex(str string) bool func IsRequestURI(rawurl string) bool func IsRequestURL(rawurl string) bool -func IsRipeMD128(str string) bool -func IsRipeMD160(str string) bool -func IsRsaPub(str string, params ...string) bool -func IsRsaPublicKey(str string, keylen int) bool -func IsSHA1(str string) bool -func IsSHA256(str string) bool -func IsSHA384(str string) bool -func IsSHA512(str string) bool func IsSSN(str string) bool func IsSemver(str string) bool -func IsTiger128(str string) bool -func IsTiger160(str string) bool -func IsTiger192(str string) bool func IsTime(str string, format string) bool -func IsType(v interface{}, params ...string) bool func IsURL(str string) bool func IsUTFDigit(str string) bool func IsUTFLetter(str string) bool @@ -204,21 +174,16 @@ func IsUUID(str string) bool func IsUUIDv3(str string) bool func IsUUIDv4(str string) bool func IsUUIDv5(str string) bool -func IsULID(str string) bool -func IsUnixTime(str string) bool func IsUpperCase(str string) bool func IsVariableWidth(str string) bool func IsWhole(value float64) bool func LeftTrim(str, chars string) string func Map(array []interface{}, iterator ResultIterator) []interface{} func Matches(str, pattern string) bool -func MaxStringLength(str string, params ...string) bool -func MinStringLength(str string, params ...string) bool func NormalizeEmail(str string) (string, error) func PadBoth(str string, padStr string, padLen int) string func PadLeft(str string, padStr string, padLen int) string func PadRight(str string, padStr string, padLen int) string -func PrependPathToErrors(err error, path string) error func Range(str string, params ...string) bool func RemoveTags(s string) string func ReplacePattern(str, pattern, replace string) string @@ -227,21 +192,18 @@ func RightTrim(str, chars string) string func RuneLength(str string, params ...string) bool func SafeFileName(str string) string func SetFieldsRequiredByDefault(value bool) -func SetNilPtrAllowedByRequired(value bool) func Sign(value float64) float64 func StringLength(str string, params ...string) bool func StringMatches(s string, params ...string) bool func StripLow(str string, keepNewLines bool) string func ToBoolean(str string) (bool, error) func ToFloat(str string) (float64, error) -func ToInt(value interface{}) (res int64, err error) +func ToInt(str string) (int64, error) func ToJSON(obj interface{}) (string, error) func ToString(obj interface{}) string func Trim(str, chars string) string func Truncate(str string, length int, ending string) string -func TruncatingErrorf(str string, args ...interface{}) error func UnderscoreToCamelCase(s string) string -func ValidateMap(inputMap map[string]interface{}, validationMap map[string]interface{}) (bool, error) func ValidateStruct(s interface{}) (bool, error) func WhiteList(str, chars string) string type ConditionIterator @@ -252,8 +214,6 @@ type Errors func (es Errors) Error() string func (es Errors) Errors() []error type ISO3166Entry -type ISO693Entry -type InterfaceParamValidator type Iterator type ParamValidator type ResultIterator @@ -267,27 +227,6 @@ type Validator ```go println(govalidator.IsURL(`http://user@pass:domain.com/path/page`)) ``` -###### IsType -```go -println(govalidator.IsType("Bob", "string")) -println(govalidator.IsType(1, "int")) -i := 1 -println(govalidator.IsType(&i, "*int")) -``` - -IsType can be used through the tag `type` which is essential for map validation: -```go -type User struct { - Name string `valid:"type(string)"` - Age int `valid:"type(int)"` - Meta interface{} `valid:"type(string)"` -} -result, err := govalidator.ValidateStruct(User{"Bob", 20, "meta"}) -if err != nil { - println("error: " + err.Error()) -} -println(result) -``` ###### ToString ```go type User struct { @@ -384,7 +323,6 @@ Here is a list of available validators for struct fields (validator - used funct "rfc3339WithoutZone": IsRFC3339WithoutZone, "ISO3166Alpha2": IsISO3166Alpha2, "ISO3166Alpha3": IsISO3166Alpha3, -"ulid": IsULID, ``` Validators with parameters @@ -396,13 +334,6 @@ Validators with parameters "matches(pattern)": StringMatches, "in(string1|string2|...|stringN)": IsIn, "rsapub(keylength)" : IsRsaPub, -"minstringlength(int): MinStringLength, -"maxstringlength(int): MaxStringLength, -``` -Validators with parameters for any type - -```go -"type(type)": IsType, ``` And here is small example of usage: @@ -439,41 +370,6 @@ if err != nil { } println(result) ``` -###### ValidateMap [#2](https://github.com/asaskevich/govalidator/pull/338) -If you want to validate maps, you can use the map to be validated and a validation map that contain the same tags used in ValidateStruct, both maps have to be in the form `map[string]interface{}` - -So here is small example of usage: -```go -var mapTemplate = map[string]interface{}{ - "name":"required,alpha", - "family":"required,alpha", - "email":"required,email", - "cell-phone":"numeric", - "address":map[string]interface{}{ - "line1":"required,alphanum", - "line2":"alphanum", - "postal-code":"numeric", - }, -} - -var inputMap = map[string]interface{}{ - "name":"Bob", - "family":"Smith", - "email":"foo@bar.baz", - "address":map[string]interface{}{ - "line1":"", - "line2":"", - "postal-code":"", - }, -} - -result, err := govalidator.ValidateMap(inputMap, mapTemplate) -if err != nil { - println("error: " + err.Error()) -} -println(result) -``` - ###### WhiteList ```go // Remove all characters from string ignoring characters between "a" and "z" @@ -493,7 +389,7 @@ type StructWithCustomByteArray struct { CustomMinLength int `valid:"-"` } -govalidator.CustomTypeTagMap.Set("customByteArrayValidator", func(i interface{}, context interface{}) bool { +govalidator.CustomTypeTagMap.Set("customByteArrayValidator", CustomTypeValidator(func(i interface{}, context interface{}) bool { switch v := context.(type) { // you can type switch on the context interface being validated case StructWithCustomByteArray: // you can check and validate against some other field in the context, @@ -513,25 +409,14 @@ govalidator.CustomTypeTagMap.Set("customByteArrayValidator", func(i interface{}, } } return false -}) -govalidator.CustomTypeTagMap.Set("customMinLengthValidator", func(i interface{}, context interface{}) bool { +})) +govalidator.CustomTypeTagMap.Set("customMinLengthValidator", CustomTypeValidator(func(i interface{}, context interface{}) bool { switch v := context.(type) { // this validates a field against the value in another field, i.e. dependent validation case StructWithCustomByteArray: return len(v.ID) >= v.CustomMinLength } return false -}) -``` - -###### Loop over Error() -By default .Error() returns all errors in a single String. To access each error you can do this: -```go - if err != nil { - errs := err.(govalidator.Errors).Errors() - for _, e := range errs { - fmt.Println(e.Error()) - } - } +})) ``` ###### Custom error messages @@ -560,7 +445,7 @@ If you don't know what to do, there are some features and functions that need to - [ ] Update actual [list of functions](https://github.com/asaskevich/govalidator#list-of-functions) - [ ] Update [list of validators](https://github.com/asaskevich/govalidator#validatestruct-2) that available for `ValidateStruct` and add new - [ ] Implement new validators: `IsFQDN`, `IsIMEI`, `IsPostalCode`, `IsISIN`, `IsISRC` etc -- [x] Implement [validation by maps](https://github.com/asaskevich/govalidator/issues/224) +- [ ] Implement [validation by maps](https://github.com/asaskevich/govalidator/issues/224) - [ ] Implement fuzzing testing - [ ] Implement some struct/map/array utilities - [ ] Implement map/array validation @@ -590,7 +475,7 @@ This project exists thanks to all the people who contribute. [[Contribute](CONTR * [Matt Sanford](https://github.com/mzsanford) * [Simon ccl1115](https://github.com/ccl1115) - + ### Backers @@ -619,4 +504,4 @@ Support this project by becoming a sponsor. Your logo will show up here with a l ## License -[![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator.svg?type=large)](https://app.fossa.io/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator?ref=badge_large) +[![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator.svg?type=large)](https://app.fossa.io/projects/git%2Bgithub.com%2Fasaskevich%2Fgovalidator?ref=badge_large) \ No newline at end of file diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/arrays.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/arrays.go index 3e1da7cb480..5bace2654d3 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/arrays.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/arrays.go @@ -9,35 +9,6 @@ type ResultIterator func(interface{}, int) interface{} // ConditionIterator is the function that accepts element of slice/array and its index and returns boolean type ConditionIterator func(interface{}, int) bool -// ReduceIterator is the function that accepts two element of slice/array and returns result of merging those values -type ReduceIterator func(interface{}, interface{}) interface{} - -// Some validates that any item of array corresponds to ConditionIterator. Returns boolean. -func Some(array []interface{}, iterator ConditionIterator) bool { - res := false - for index, data := range array { - res = res || iterator(data, index) - } - return res -} - -// Every validates that every item of array corresponds to ConditionIterator. Returns boolean. -func Every(array []interface{}, iterator ConditionIterator) bool { - res := true - for index, data := range array { - res = res && iterator(data, index) - } - return res -} - -// Reduce boils down a list of values into a single value by ReduceIterator -func Reduce(array []interface{}, iterator ReduceIterator, initialValue interface{}) interface{} { - for _, data := range array { - initialValue = iterator(initialValue, data) - } - return initialValue -} - // Each iterates over the slice and apply Iterator to every item func Each(array []interface{}, iterator Iterator) { for index, data := range array { diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/converter.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/converter.go index d68e990fc25..cf1e5d569ba 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/converter.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/converter.go @@ -10,7 +10,7 @@ import ( // ToString convert the input to a string. func ToString(obj interface{}) string { res := fmt.Sprintf("%v", obj) - return res + return string(res) } // ToJSON convert the input to a valid JSON string @@ -23,27 +23,12 @@ func ToJSON(obj interface{}) (string, error) { } // ToFloat convert the input string to a float, or 0.0 if the input is not a float. -func ToFloat(value interface{}) (res float64, err error) { - val := reflect.ValueOf(value) - - switch value.(type) { - case int, int8, int16, int32, int64: - res = float64(val.Int()) - case uint, uint8, uint16, uint32, uint64: - res = float64(val.Uint()) - case float32, float64: - res = val.Float() - case string: - res, err = strconv.ParseFloat(val.String(), 64) - if err != nil { - res = 0 - } - default: - err = fmt.Errorf("ToInt: unknown interface type %T", value) - res = 0 +func ToFloat(str string) (float64, error) { + res, err := strconv.ParseFloat(str, 64) + if err != nil { + res = 0.0 } - - return + return res, err } // ToInt convert the input string or any int type to an integer type 64, or 0 if the input is not an integer. @@ -55,8 +40,6 @@ func ToInt(value interface{}) (res int64, err error) { res = val.Int() case uint, uint8, uint16, uint32, uint64: res = int64(val.Uint()) - case float32, float64: - res = int64(val.Float()) case string: if IsInt(val.String()) { res, err = strconv.ParseInt(val.String(), 0, 64) @@ -64,11 +47,11 @@ func ToInt(value interface{}) (res int64, err error) { res = 0 } } else { - err = fmt.Errorf("ToInt: invalid numeric format %g", value) + err = fmt.Errorf("math: square root of negative number %g", value) res = 0 } default: - err = fmt.Errorf("ToInt: unknown interface type %T", value) + err = fmt.Errorf("math: square root of negative number %g", value) res = 0 } diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/doc.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/doc.go deleted file mode 100644 index 55dce62dc8c..00000000000 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/doc.go +++ /dev/null @@ -1,3 +0,0 @@ -package govalidator - -// A package of validators and sanitizers for strings, structures and collections. diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/error.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/error.go index 1da2336f47e..655b750cb8f 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/error.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/error.go @@ -1,9 +1,6 @@ package govalidator -import ( - "sort" - "strings" -) +import "strings" // Errors is an array of multiple errors and conforms to the error interface. type Errors []error @@ -18,7 +15,6 @@ func (es Errors) Error() string { for _, e := range es { errs = append(errs, e.Error()) } - sort.Strings(errs) return strings.Join(errs, ";") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/numerics.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/numerics.go index 5041d9e8684..7e6c652e140 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/numerics.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/numerics.go @@ -2,6 +2,7 @@ package govalidator import ( "math" + "reflect" ) // Abs returns absolute value of number @@ -40,7 +41,7 @@ func IsNonPositive(value float64) bool { return value <= 0 } -// InRangeInt returns true if value lies between left and right border +// InRange returns true if value lies between left and right border func InRangeInt(value, left, right interface{}) bool { value64, _ := ToInt(value) left64, _ := ToInt(left) @@ -51,7 +52,7 @@ func InRangeInt(value, left, right interface{}) bool { return value64 >= left64 && value64 <= right64 } -// InRangeFloat32 returns true if value lies between left and right border +// InRange returns true if value lies between left and right border func InRangeFloat32(value, left, right float32) bool { if left > right { left, right = right, left @@ -59,7 +60,7 @@ func InRangeFloat32(value, left, right float32) bool { return value >= left && value <= right } -// InRangeFloat64 returns true if value lies between left and right border +// InRange returns true if value lies between left and right border func InRangeFloat64(value, left, right float64) bool { if left > right { left, right = right, left @@ -67,24 +68,20 @@ func InRangeFloat64(value, left, right float64) bool { return value >= left && value <= right } -// InRange returns true if value lies between left and right border, generic type to handle int, float32, float64 and string. -// All types must the same type. -// False if value doesn't lie in range or if it incompatible or not comparable +// InRange returns true if value lies between left and right border, generic type to handle int, float32 or float64, all types must the same type func InRange(value interface{}, left interface{}, right interface{}) bool { - switch value.(type) { - case int: - intValue, _ := ToInt(value) - intLeft, _ := ToInt(left) - intRight, _ := ToInt(right) - return InRangeInt(intValue, intLeft, intRight) - case float32, float64: - intValue, _ := ToFloat(value) - intLeft, _ := ToFloat(left) - intRight, _ := ToFloat(right) - return InRangeFloat64(intValue, intLeft, intRight) - case string: - return value.(string) >= left.(string) && value.(string) <= right.(string) - default: + + reflectValue := reflect.TypeOf(value).Kind() + reflectLeft := reflect.TypeOf(left).Kind() + reflectRight := reflect.TypeOf(right).Kind() + + if reflectValue == reflect.Int && reflectLeft == reflect.Int && reflectRight == reflect.Int { + return InRangeInt(value.(int), left.(int), right.(int)) + } else if reflectValue == reflect.Float32 && reflectLeft == reflect.Float32 && reflectRight == reflect.Float32 { + return InRangeFloat32(value.(float32), left.(float32), right.(float32)) + } else if reflectValue == reflect.Float64 && reflectLeft == reflect.Float64 && reflectRight == reflect.Float64 { + return InRangeFloat64(value.(float64), left.(float64), right.(float64)) + } else { return false } } diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/patterns.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/patterns.go index bafc3765ea1..61a05d438e1 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/patterns.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/patterns.go @@ -4,55 +4,49 @@ import "regexp" // Basic regular expressions for validating strings const ( - Email string = "^(((([a-zA-Z]|\\d|[!#\\$%&'\\*\\+\\-\\/=\\?\\^_`{\\|}~]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])+(\\.([a-zA-Z]|\\d|[!#\\$%&'\\*\\+\\-\\/=\\?\\^_`{\\|}~]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])+)*)|((\\x22)((((\\x20|\\x09)*(\\x0d\\x0a))?(\\x20|\\x09)+)?(([\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x7f]|\\x21|[\\x23-\\x5b]|[\\x5d-\\x7e]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(\\([\\x01-\\x09\\x0b\\x0c\\x0d-\\x7f]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}]))))*(((\\x20|\\x09)*(\\x0d\\x0a))?(\\x20|\\x09)+)?(\\x22)))@((([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])([a-zA-Z]|\\d|-|\\.|_|~|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])*([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])))\\.)+(([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])([a-zA-Z]|\\d|-|_|~|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])*([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])))\\.?$" - CreditCard string = "^(?:4[0-9]{12}(?:[0-9]{3})?|5[1-5][0-9]{14}|(222[1-9]|22[3-9][0-9]|2[3-6][0-9]{2}|27[01][0-9]|2720)[0-9]{12}|6(?:011|5[0-9][0-9])[0-9]{12}|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])[0-9]{11}|(?:2131|1800|35\\d{3})\\d{11}|6[27][0-9]{14})$" - ISBN10 string = "^(?:[0-9]{9}X|[0-9]{10})$" - ISBN13 string = "^(?:[0-9]{13})$" - UUID3 string = "^[0-9a-f]{8}-[0-9a-f]{4}-3[0-9a-f]{3}-[0-9a-f]{4}-[0-9a-f]{12}$" - UUID4 string = "^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$" - UUID5 string = "^[0-9a-f]{8}-[0-9a-f]{4}-5[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$" - UUID string = "^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$" - Alpha string = "^[a-zA-Z]+$" - Alphanumeric string = "^[a-zA-Z0-9]+$" - Numeric string = "^[0-9]+$" - Int string = "^(?:[-+]?(?:0|[1-9][0-9]*))$" - Float string = "^(?:[-+]?(?:[0-9]+))?(?:\\.[0-9]*)?(?:[eE][\\+\\-]?(?:[0-9]+))?$" - Hexadecimal string = "^[0-9a-fA-F]+$" - Hexcolor string = "^#?([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$" - RGBcolor string = "^rgb\\(\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*\\)$" - ASCII string = "^[\x00-\x7F]+$" - Multibyte string = "[^\x00-\x7F]" - FullWidth string = "[^\u0020-\u007E\uFF61-\uFF9F\uFFA0-\uFFDC\uFFE8-\uFFEE0-9a-zA-Z]" - HalfWidth string = "[\u0020-\u007E\uFF61-\uFF9F\uFFA0-\uFFDC\uFFE8-\uFFEE0-9a-zA-Z]" - Base64 string = "^(?:[A-Za-z0-9+\\/]{4})*(?:[A-Za-z0-9+\\/]{2}==|[A-Za-z0-9+\\/]{3}=|[A-Za-z0-9+\\/]{4})$" - PrintableASCII string = "^[\x20-\x7E]+$" - DataURI string = "^data:.+\\/(.+);base64$" - MagnetURI string = "^magnet:\\?xt=urn:[a-zA-Z0-9]+:[a-zA-Z0-9]{32,40}&dn=.+&tr=.+$" - Latitude string = "^[-+]?([1-8]?\\d(\\.\\d+)?|90(\\.0+)?)$" - Longitude string = "^[-+]?(180(\\.0+)?|((1[0-7]\\d)|([1-9]?\\d))(\\.\\d+)?)$" - DNSName string = `^([a-zA-Z0-9_]{1}[a-zA-Z0-9_-]{0,62}){1}(\.[a-zA-Z0-9_]{1}[a-zA-Z0-9_-]{0,62})*[\._]?$` - IP string = `(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:)|fe80:(:[0-9a-fA-F]{0,4}){0,4}%[0-9a-zA-Z]{1,}|::(ffff(:0{1,4}){0,1}:){0,1}((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])|([0-9a-fA-F]{1,4}:){1,4}:((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]))` - URLSchema string = `((ftp|tcp|udp|wss?|https?):\/\/)` - URLUsername string = `(\S+(:\S*)?@)` - URLPath string = `((\/|\?|#)[^\s]*)` - URLPort string = `(:(\d{1,5}))` - URLIP string = `([1-9]\d?|1\d\d|2[01]\d|22[0-3]|24\d|25[0-5])(\.(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])){2}(?:\.([0-9]\d?|1\d\d|2[0-4]\d|25[0-5]))` - URLSubdomain string = `((www\.)|([a-zA-Z0-9]+([-_\.]?[a-zA-Z0-9])*[a-zA-Z0-9]\.[a-zA-Z0-9]+))` - URL = `^` + URLSchema + `?` + URLUsername + `?` + `((` + URLIP + `|(\[` + IP + `\])|(([a-zA-Z0-9]([a-zA-Z0-9-_]+)?[a-zA-Z0-9]([-\.][a-zA-Z0-9]+)*)|(` + URLSubdomain + `?))?(([a-zA-Z\x{00a1}-\x{ffff}0-9]+-?-?)*[a-zA-Z\x{00a1}-\x{ffff}0-9]+)(?:\.([a-zA-Z\x{00a1}-\x{ffff}]{1,}))?))\.?` + URLPort + `?` + URLPath + `?$` - SSN string = `^\d{3}[- ]?\d{2}[- ]?\d{4}$` - WinPath string = `^[a-zA-Z]:\\(?:[^\\/:*?"<>|\r\n]+\\)*[^\\/:*?"<>|\r\n]*$` - UnixPath string = `^(/[^/\x00]*)+/?$` - WinARPath string = `^(?:(?:[a-zA-Z]:|\\\\[a-z0-9_.$●-]+\\[a-z0-9_.$●-]+)\\|\\?[^\\/:*?"<>|\r\n]+\\?)(?:[^\\/:*?"<>|\r\n]+\\)*[^\\/:*?"<>|\r\n]*$` - UnixARPath string = `^((\.{0,2}/)?([^/\x00]*))+/?$` - Semver string = "^v?(?:0|[1-9]\\d*)\\.(?:0|[1-9]\\d*)\\.(?:0|[1-9]\\d*)(-(0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*)(\\.(0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*))*)?(\\+[0-9a-zA-Z-]+(\\.[0-9a-zA-Z-]+)*)?$" - tagName string = "valid" - hasLowerCase string = ".*[[:lower:]]" - hasUpperCase string = ".*[[:upper:]]" - hasWhitespace string = ".*[[:space:]]" - hasWhitespaceOnly string = "^[[:space:]]+$" - IMEI string = "^[0-9a-f]{14}$|^\\d{15}$|^\\d{18}$" - IMSI string = "^\\d{14,15}$" - E164 string = `^\+?[1-9]\d{1,14}$` + Email string = "^(((([a-zA-Z]|\\d|[!#\\$%&'\\*\\+\\-\\/=\\?\\^_`{\\|}~]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])+(\\.([a-zA-Z]|\\d|[!#\\$%&'\\*\\+\\-\\/=\\?\\^_`{\\|}~]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])+)*)|((\\x22)((((\\x20|\\x09)*(\\x0d\\x0a))?(\\x20|\\x09)+)?(([\\x01-\\x08\\x0b\\x0c\\x0e-\\x1f\\x7f]|\\x21|[\\x23-\\x5b]|[\\x5d-\\x7e]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(\\([\\x01-\\x09\\x0b\\x0c\\x0d-\\x7f]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}]))))*(((\\x20|\\x09)*(\\x0d\\x0a))?(\\x20|\\x09)+)?(\\x22)))@((([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])([a-zA-Z]|\\d|-|\\.|_|~|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])*([a-zA-Z]|\\d|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])))\\.)+(([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])|(([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])([a-zA-Z]|\\d|-|_|~|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])*([a-zA-Z]|[\\x{00A0}-\\x{D7FF}\\x{F900}-\\x{FDCF}\\x{FDF0}-\\x{FFEF}])))\\.?$" + CreditCard string = "^(?:4[0-9]{12}(?:[0-9]{3})?|5[1-5][0-9]{14}|6(?:011|5[0-9][0-9])[0-9]{12}|3[47][0-9]{13}|3(?:0[0-5]|[68][0-9])[0-9]{11}|(?:2131|1800|35\\d{3})\\d{11})$" + ISBN10 string = "^(?:[0-9]{9}X|[0-9]{10})$" + ISBN13 string = "^(?:[0-9]{13})$" + UUID3 string = "^[0-9a-f]{8}-[0-9a-f]{4}-3[0-9a-f]{3}-[0-9a-f]{4}-[0-9a-f]{12}$" + UUID4 string = "^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$" + UUID5 string = "^[0-9a-f]{8}-[0-9a-f]{4}-5[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$" + UUID string = "^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$" + Alpha string = "^[a-zA-Z]+$" + Alphanumeric string = "^[a-zA-Z0-9]+$" + Numeric string = "^[0-9]+$" + Int string = "^(?:[-+]?(?:0|[1-9][0-9]*))$" + Float string = "^(?:[-+]?(?:[0-9]+))?(?:\\.[0-9]*)?(?:[eE][\\+\\-]?(?:[0-9]+))?$" + Hexadecimal string = "^[0-9a-fA-F]+$" + Hexcolor string = "^#?([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$" + RGBcolor string = "^rgb\\(\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*,\\s*(0|[1-9]\\d?|1\\d\\d?|2[0-4]\\d|25[0-5])\\s*\\)$" + ASCII string = "^[\x00-\x7F]+$" + Multibyte string = "[^\x00-\x7F]" + FullWidth string = "[^\u0020-\u007E\uFF61-\uFF9F\uFFA0-\uFFDC\uFFE8-\uFFEE0-9a-zA-Z]" + HalfWidth string = "[\u0020-\u007E\uFF61-\uFF9F\uFFA0-\uFFDC\uFFE8-\uFFEE0-9a-zA-Z]" + Base64 string = "^(?:[A-Za-z0-9+\\/]{4})*(?:[A-Za-z0-9+\\/]{2}==|[A-Za-z0-9+\\/]{3}=|[A-Za-z0-9+\\/]{4})$" + PrintableASCII string = "^[\x20-\x7E]+$" + DataURI string = "^data:.+\\/(.+);base64$" + Latitude string = "^[-+]?([1-8]?\\d(\\.\\d+)?|90(\\.0+)?)$" + Longitude string = "^[-+]?(180(\\.0+)?|((1[0-7]\\d)|([1-9]?\\d))(\\.\\d+)?)$" + DNSName string = `^([a-zA-Z0-9_]{1}[a-zA-Z0-9_-]{0,62}){1}(\.[a-zA-Z0-9_]{1}[a-zA-Z0-9_-]{0,62})*[\._]?$` + IP string = `(([0-9a-fA-F]{1,4}:){7,7}[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,7}:|([0-9a-fA-F]{1,4}:){1,6}:[0-9a-fA-F]{1,4}|([0-9a-fA-F]{1,4}:){1,5}(:[0-9a-fA-F]{1,4}){1,2}|([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,3}|([0-9a-fA-F]{1,4}:){1,3}(:[0-9a-fA-F]{1,4}){1,4}|([0-9a-fA-F]{1,4}:){1,2}(:[0-9a-fA-F]{1,4}){1,5}|[0-9a-fA-F]{1,4}:((:[0-9a-fA-F]{1,4}){1,6})|:((:[0-9a-fA-F]{1,4}){1,7}|:)|fe80:(:[0-9a-fA-F]{0,4}){0,4}%[0-9a-zA-Z]{1,}|::(ffff(:0{1,4}){0,1}:){0,1}((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])|([0-9a-fA-F]{1,4}:){1,4}:((25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9])\.){3,3}(25[0-5]|(2[0-4]|1{0,1}[0-9]){0,1}[0-9]))` + URLSchema string = `((ftp|tcp|udp|wss?|https?):\/\/)` + URLUsername string = `(\S+(:\S*)?@)` + URLPath string = `((\/|\?|#)[^\s]*)` + URLPort string = `(:(\d{1,5}))` + URLIP string = `([1-9]\d?|1\d\d|2[01]\d|22[0-3])(\.(1?\d{1,2}|2[0-4]\d|25[0-5])){2}(?:\.([0-9]\d?|1\d\d|2[0-4]\d|25[0-4]))` + URLSubdomain string = `((www\.)|([a-zA-Z0-9]+([-_\.]?[a-zA-Z0-9])*[a-zA-Z0-9]\.[a-zA-Z0-9]+))` + URL string = `^` + URLSchema + `?` + URLUsername + `?` + `((` + URLIP + `|(\[` + IP + `\])|(([a-zA-Z0-9]([a-zA-Z0-9-_]+)?[a-zA-Z0-9]([-\.][a-zA-Z0-9]+)*)|(` + URLSubdomain + `?))?(([a-zA-Z\x{00a1}-\x{ffff}0-9]+-?-?)*[a-zA-Z\x{00a1}-\x{ffff}0-9]+)(?:\.([a-zA-Z\x{00a1}-\x{ffff}]{1,}))?))\.?` + URLPort + `?` + URLPath + `?$` + SSN string = `^\d{3}[- ]?\d{2}[- ]?\d{4}$` + WinPath string = `^[a-zA-Z]:\\(?:[^\\/:*?"<>|\r\n]+\\)*[^\\/:*?"<>|\r\n]*$` + UnixPath string = `^(/[^/\x00]*)+/?$` + Semver string = "^v?(?:0|[1-9]\\d*)\\.(?:0|[1-9]\\d*)\\.(?:0|[1-9]\\d*)(-(0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*)(\\.(0|[1-9]\\d*|\\d*[a-zA-Z-][0-9a-zA-Z-]*))*)?(\\+[0-9a-zA-Z-]+(\\.[0-9a-zA-Z-]+)*)?$" + tagName string = "valid" + hasLowerCase string = ".*[[:lower:]]" + hasUpperCase string = ".*[[:upper:]]" + hasWhitespace string = ".*[[:space:]]" + hasWhitespaceOnly string = "^[[:space:]]+$" ) // Used by IsFilePath func @@ -66,48 +60,42 @@ const ( ) var ( - userRegexp = regexp.MustCompile("^[a-zA-Z0-9!#$%&'*+/=?^_`{|}~.-]+$") - hostRegexp = regexp.MustCompile("^[^\\s]+\\.[^\\s]+$") - userDotRegexp = regexp.MustCompile("(^[.]{1})|([.]{1}$)|([.]{2,})") - rxEmail = regexp.MustCompile(Email) - rxCreditCard = regexp.MustCompile(CreditCard) - rxISBN10 = regexp.MustCompile(ISBN10) - rxISBN13 = regexp.MustCompile(ISBN13) - rxUUID3 = regexp.MustCompile(UUID3) - rxUUID4 = regexp.MustCompile(UUID4) - rxUUID5 = regexp.MustCompile(UUID5) - rxUUID = regexp.MustCompile(UUID) - rxAlpha = regexp.MustCompile(Alpha) - rxAlphanumeric = regexp.MustCompile(Alphanumeric) - rxNumeric = regexp.MustCompile(Numeric) - rxInt = regexp.MustCompile(Int) - rxFloat = regexp.MustCompile(Float) - rxHexadecimal = regexp.MustCompile(Hexadecimal) - rxHexcolor = regexp.MustCompile(Hexcolor) - rxRGBcolor = regexp.MustCompile(RGBcolor) - rxASCII = regexp.MustCompile(ASCII) - rxPrintableASCII = regexp.MustCompile(PrintableASCII) - rxMultibyte = regexp.MustCompile(Multibyte) - rxFullWidth = regexp.MustCompile(FullWidth) - rxHalfWidth = regexp.MustCompile(HalfWidth) - rxBase64 = regexp.MustCompile(Base64) - rxDataURI = regexp.MustCompile(DataURI) - rxMagnetURI = regexp.MustCompile(MagnetURI) - rxLatitude = regexp.MustCompile(Latitude) - rxLongitude = regexp.MustCompile(Longitude) - rxDNSName = regexp.MustCompile(DNSName) - rxURL = regexp.MustCompile(URL) - rxSSN = regexp.MustCompile(SSN) - rxWinPath = regexp.MustCompile(WinPath) - rxUnixPath = regexp.MustCompile(UnixPath) - rxARWinPath = regexp.MustCompile(WinARPath) - rxARUnixPath = regexp.MustCompile(UnixARPath) - rxSemver = regexp.MustCompile(Semver) - rxHasLowerCase = regexp.MustCompile(hasLowerCase) - rxHasUpperCase = regexp.MustCompile(hasUpperCase) - rxHasWhitespace = regexp.MustCompile(hasWhitespace) - rxHasWhitespaceOnly = regexp.MustCompile(hasWhitespaceOnly) - rxIMEI = regexp.MustCompile(IMEI) - rxIMSI = regexp.MustCompile(IMSI) - rxE164 = regexp.MustCompile(E164) + userRegexp = regexp.MustCompile("^[a-zA-Z0-9!#$%&'*+/=?^_`{|}~.-]+$") + hostRegexp = regexp.MustCompile("^[^\\s]+\\.[^\\s]+$") + userDotRegexp = regexp.MustCompile("(^[.]{1})|([.]{1}$)|([.]{2,})") + rxEmail = regexp.MustCompile(Email) + rxCreditCard = regexp.MustCompile(CreditCard) + rxISBN10 = regexp.MustCompile(ISBN10) + rxISBN13 = regexp.MustCompile(ISBN13) + rxUUID3 = regexp.MustCompile(UUID3) + rxUUID4 = regexp.MustCompile(UUID4) + rxUUID5 = regexp.MustCompile(UUID5) + rxUUID = regexp.MustCompile(UUID) + rxAlpha = regexp.MustCompile(Alpha) + rxAlphanumeric = regexp.MustCompile(Alphanumeric) + rxNumeric = regexp.MustCompile(Numeric) + rxInt = regexp.MustCompile(Int) + rxFloat = regexp.MustCompile(Float) + rxHexadecimal = regexp.MustCompile(Hexadecimal) + rxHexcolor = regexp.MustCompile(Hexcolor) + rxRGBcolor = regexp.MustCompile(RGBcolor) + rxASCII = regexp.MustCompile(ASCII) + rxPrintableASCII = regexp.MustCompile(PrintableASCII) + rxMultibyte = regexp.MustCompile(Multibyte) + rxFullWidth = regexp.MustCompile(FullWidth) + rxHalfWidth = regexp.MustCompile(HalfWidth) + rxBase64 = regexp.MustCompile(Base64) + rxDataURI = regexp.MustCompile(DataURI) + rxLatitude = regexp.MustCompile(Latitude) + rxLongitude = regexp.MustCompile(Longitude) + rxDNSName = regexp.MustCompile(DNSName) + rxURL = regexp.MustCompile(URL) + rxSSN = regexp.MustCompile(SSN) + rxWinPath = regexp.MustCompile(WinPath) + rxUnixPath = regexp.MustCompile(UnixPath) + rxSemver = regexp.MustCompile(Semver) + rxHasLowerCase = regexp.MustCompile(hasLowerCase) + rxHasUpperCase = regexp.MustCompile(hasUpperCase) + rxHasWhitespace = regexp.MustCompile(hasWhitespace) + rxHasWhitespaceOnly = regexp.MustCompile(hasWhitespaceOnly) ) diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/types.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/types.go index c573abb51af..4f7e9274ade 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/types.go @@ -14,11 +14,8 @@ type Validator func(str string) bool // The second parameter should be the context (in the case of validating a struct: the whole object being validated). type CustomTypeValidator func(i interface{}, o interface{}) bool -// ParamValidator is a wrapper for validator functions that accept additional parameters. +// ParamValidator is a wrapper for validator functions that accepts additional parameters. type ParamValidator func(str string, params ...string) bool - -// InterfaceParamValidator is a wrapper for functions that accept variants parameters for an interface value -type InterfaceParamValidator func(in interface{}, params ...string) bool type tagOptionsMap map[string]tagOption func (t tagOptionsMap) orderedKeys() []string { @@ -49,40 +46,26 @@ type UnsupportedTypeError struct { // It implements the methods to sort by string. type stringValues []reflect.Value -// InterfaceParamTagMap is a map of functions accept variants parameters for an interface value -var InterfaceParamTagMap = map[string]InterfaceParamValidator{ - "type": IsType, -} - -// InterfaceParamTagRegexMap maps interface param tags to their respective regexes. -var InterfaceParamTagRegexMap = map[string]*regexp.Regexp{ - "type": regexp.MustCompile(`^type\((.*)\)$`), -} - // ParamTagMap is a map of functions accept variants parameters var ParamTagMap = map[string]ParamValidator{ - "length": ByteLength, - "range": Range, - "runelength": RuneLength, - "stringlength": StringLength, - "matches": StringMatches, - "in": IsInRaw, - "rsapub": IsRsaPub, - "minstringlength": MinStringLength, - "maxstringlength": MaxStringLength, + "length": ByteLength, + "range": Range, + "runelength": RuneLength, + "stringlength": StringLength, + "matches": StringMatches, + "in": isInRaw, + "rsapub": IsRsaPub, } // ParamTagRegexMap maps param tags to their respective regexes. var ParamTagRegexMap = map[string]*regexp.Regexp{ - "range": regexp.MustCompile("^range\\((\\d+)\\|(\\d+)\\)$"), - "length": regexp.MustCompile("^length\\((\\d+)\\|(\\d+)\\)$"), - "runelength": regexp.MustCompile("^runelength\\((\\d+)\\|(\\d+)\\)$"), - "stringlength": regexp.MustCompile("^stringlength\\((\\d+)\\|(\\d+)\\)$"), - "in": regexp.MustCompile(`^in\((.*)\)`), - "matches": regexp.MustCompile(`^matches\((.+)\)$`), - "rsapub": regexp.MustCompile("^rsapub\\((\\d+)\\)$"), - "minstringlength": regexp.MustCompile("^minstringlength\\((\\d+)\\)$"), - "maxstringlength": regexp.MustCompile("^maxstringlength\\((\\d+)\\)$"), + "range": regexp.MustCompile("^range\\((\\d+)\\|(\\d+)\\)$"), + "length": regexp.MustCompile("^length\\((\\d+)\\|(\\d+)\\)$"), + "runelength": regexp.MustCompile("^runelength\\((\\d+)\\|(\\d+)\\)$"), + "stringlength": regexp.MustCompile("^stringlength\\((\\d+)\\|(\\d+)\\)$"), + "in": regexp.MustCompile(`^in\((.*)\)`), + "matches": regexp.MustCompile(`^matches\((.+)\)$`), + "rsapub": regexp.MustCompile("^rsapub\\((\\d+)\\)$"), } type customTypeTagMap struct { @@ -131,7 +114,6 @@ var TagMap = map[string]Validator{ "int": IsInt, "float": IsFloat, "null": IsNull, - "notnull": IsNotNull, "uuid": IsUUID, "uuidv3": IsUUIDv3, "uuidv4": IsUUIDv4, @@ -164,8 +146,6 @@ var TagMap = map[string]Validator{ "ISO3166Alpha2": IsISO3166Alpha2, "ISO3166Alpha3": IsISO3166Alpha3, "ISO4217": IsISO4217, - "IMEI": IsIMEI, - "ulid": IsULID, } // ISO3166Entry stores country codes @@ -450,10 +430,10 @@ var ISO4217List = []string{ "PAB", "PEN", "PGK", "PHP", "PKR", "PLN", "PYG", "QAR", "RON", "RSD", "RUB", "RWF", - "SAR", "SBD", "SCR", "SDG", "SEK", "SGD", "SHP", "SLL", "SOS", "SRD", "SSP", "STD", "STN", "SVC", "SYP", "SZL", + "SAR", "SBD", "SCR", "SDG", "SEK", "SGD", "SHP", "SLL", "SOS", "SRD", "SSP", "STD", "SVC", "SYP", "SZL", "THB", "TJS", "TMT", "TND", "TOP", "TRY", "TTD", "TWD", "TZS", - "UAH", "UGX", "USD", "USN", "UYI", "UYU", "UYW", "UZS", - "VEF", "VES", "VND", "VUV", + "UAH", "UGX", "USD", "USN", "UYI", "UYU", "UZS", + "VEF", "VND", "VUV", "WST", "XAF", "XAG", "XAU", "XBA", "XBB", "XBC", "XBD", "XCD", "XDR", "XOF", "XPD", "XPF", "XPT", "XSU", "XTS", "XUA", "XXX", "YER", diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/utils.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/utils.go index f4c30f824a2..a0b706a743c 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/utils.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/utils.go @@ -12,20 +12,20 @@ import ( "unicode/utf8" ) -// Contains checks if the string contains the substring. +// Contains check if the string contains the substring. func Contains(str, substring string) bool { return strings.Contains(str, substring) } -// Matches checks if string matches the pattern (pattern is regular expression) +// Matches check if string matches the pattern (pattern is regular expression) // In case of error return false func Matches(str, pattern string) bool { match, _ := regexp.MatchString(pattern, str) return match } -// LeftTrim trims characters from the left side of the input. -// If second argument is empty, it will remove leading spaces. +// LeftTrim trim characters from the left-side of the input. +// If second argument is empty, it's will be remove leading spaces. func LeftTrim(str, chars string) string { if chars == "" { return strings.TrimLeftFunc(str, unicode.IsSpace) @@ -34,8 +34,8 @@ func LeftTrim(str, chars string) string { return r.ReplaceAllString(str, "") } -// RightTrim trims characters from the right side of the input. -// If second argument is empty, it will remove trailing spaces. +// RightTrim trim characters from the right-side of the input. +// If second argument is empty, it's will be remove spaces. func RightTrim(str, chars string) string { if chars == "" { return strings.TrimRightFunc(str, unicode.IsSpace) @@ -44,27 +44,27 @@ func RightTrim(str, chars string) string { return r.ReplaceAllString(str, "") } -// Trim trims characters from both sides of the input. -// If second argument is empty, it will remove spaces. +// Trim trim characters from both sides of the input. +// If second argument is empty, it's will be remove spaces. func Trim(str, chars string) string { return LeftTrim(RightTrim(str, chars), chars) } -// WhiteList removes characters that do not appear in the whitelist. +// WhiteList remove characters that do not appear in the whitelist. func WhiteList(str, chars string) string { pattern := "[^" + chars + "]+" r, _ := regexp.Compile(pattern) return r.ReplaceAllString(str, "") } -// BlackList removes characters that appear in the blacklist. +// BlackList remove characters that appear in the blacklist. func BlackList(str, chars string) string { pattern := "[" + chars + "]+" r, _ := regexp.Compile(pattern) return r.ReplaceAllString(str, "") } -// StripLow removes characters with a numerical value < 32 and 127, mostly control characters. +// StripLow remove characters with a numerical value < 32 and 127, mostly control characters. // If keep_new_lines is true, newline characters are preserved (\n and \r, hex 0xA and 0xD). func StripLow(str string, keepNewLines bool) string { chars := "" @@ -76,13 +76,13 @@ func StripLow(str string, keepNewLines bool) string { return BlackList(str, chars) } -// ReplacePattern replaces regular expression pattern in string +// ReplacePattern replace regular expression pattern in string func ReplacePattern(str, pattern, replace string) string { r, _ := regexp.Compile(pattern) return r.ReplaceAllString(str, replace) } -// Escape replaces <, >, & and " with HTML entities. +// Escape replace <, >, & and " with HTML entities. var Escape = html.EscapeString func addSegment(inrune, segment []rune) []rune { @@ -120,7 +120,7 @@ func CamelCaseToUnderscore(str string) string { return string(output) } -// Reverse returns reversed string +// Reverse return reversed string func Reverse(s string) string { r := []rune(s) for i, j := 0, len(r)-1; i < j; i, j = i+1, j-1 { @@ -129,12 +129,12 @@ func Reverse(s string) string { return string(r) } -// GetLines splits string by "\n" and return array of lines +// GetLines split string by "\n" and return array of lines func GetLines(s string) []string { return strings.Split(s, "\n") } -// GetLine returns specified line of multiline string +// GetLine return specified line of multiline string func GetLine(s string, index int) (string, error) { lines := GetLines(s) if index < 0 || index >= len(lines) { @@ -143,12 +143,12 @@ func GetLine(s string, index int) (string, error) { return lines[index], nil } -// RemoveTags removes all tags from HTML string +// RemoveTags remove all tags from HTML string func RemoveTags(s string) string { return ReplacePattern(s, "<[^>]*>", "") } -// SafeFileName returns safe string that can be used in file names +// SafeFileName return safe string that can be used in file names func SafeFileName(str string) string { name := strings.ToLower(str) name = path.Clean(path.Base(name)) @@ -210,23 +210,23 @@ func Truncate(str string, length int, ending string) string { return str } -// PadLeft pads left side of a string if size of string is less then indicated pad length +// PadLeft pad left side of string if size of string is less then indicated pad length func PadLeft(str string, padStr string, padLen int) string { return buildPadStr(str, padStr, padLen, true, false) } -// PadRight pads right side of a string if size of string is less then indicated pad length +// PadRight pad right side of string if size of string is less then indicated pad length func PadRight(str string, padStr string, padLen int) string { return buildPadStr(str, padStr, padLen, false, true) } -// PadBoth pads both sides of a string if size of string is less then indicated pad length +// PadBoth pad sides of string if size of string is less then indicated pad length func PadBoth(str string, padStr string, padLen int) string { return buildPadStr(str, padStr, padLen, true, true) } -// PadString either left, right or both sides. -// Note that padding string can be unicode and more then one character +// PadString either left, right or both sides, not the padding string can be unicode and more then one +// character func buildPadStr(str string, padStr string, padLen int, padLeft bool, padRight bool) string { // When padded length is less then the current string size diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/validator.go b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/validator.go index c9c4fac0655..b18bbcb4c99 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/validator.go +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/validator.go @@ -32,7 +32,7 @@ var ( const maxURLRuneCount = 2083 const minURLRuneCount = 3 -const rfc3339WithoutZone = "2006-01-02T15:04:05" +const RF3339WithoutZone = "2006-01-02T15:04:05" // SetFieldsRequiredByDefault causes validation to fail when struct fields // do not include validations or are not explicitly marked as exempt (using `valid:"-"` or `valid:"email,optional"`). @@ -63,13 +63,13 @@ func SetNilPtrAllowedByRequired(value bool) { nilPtrAllowedByRequired = value } -// IsEmail checks if the string is an email. +// IsEmail check if the string is an email. func IsEmail(str string) bool { // TODO uppercase letters are not supported return rxEmail.MatchString(str) } -// IsExistingEmail checks if the string is an email of existing domain +// IsExistingEmail check if the string is an email of existing domain func IsExistingEmail(email string) bool { if len(email) < 6 || len(email) > 254 { @@ -84,13 +84,13 @@ func IsExistingEmail(email string) bool { if len(user) > 64 { return false } + if userDotRegexp.MatchString(user) || !userRegexp.MatchString(user) || !hostRegexp.MatchString(host) { + return false + } switch host { case "localhost", "example.com": return true } - if userDotRegexp.MatchString(user) || !userRegexp.MatchString(user) || !hostRegexp.MatchString(host) { - return false - } if _, err := net.LookupMX(host); err != nil { if _, err := net.LookupIP(host); err != nil { return false @@ -100,7 +100,7 @@ func IsExistingEmail(email string) bool { return true } -// IsURL checks if the string is an URL. +// IsURL check if the string is an URL. func IsURL(str string) bool { if str == "" || utf8.RuneCountInString(str) >= maxURLRuneCount || len(str) <= minURLRuneCount || strings.HasPrefix(str, ".") { return false @@ -124,7 +124,7 @@ func IsURL(str string) bool { return rxURL.MatchString(str) } -// IsRequestURL checks if the string rawurl, assuming +// IsRequestURL check if the string rawurl, assuming // it was received in an HTTP request, is a valid // URL confirm to RFC 3986 func IsRequestURL(rawurl string) bool { @@ -138,7 +138,7 @@ func IsRequestURL(rawurl string) bool { return true } -// IsRequestURI checks if the string rawurl, assuming +// IsRequestURI check if the string rawurl, assuming // it was received in an HTTP request, is an // absolute URI or an absolute path. func IsRequestURI(rawurl string) bool { @@ -146,7 +146,7 @@ func IsRequestURI(rawurl string) bool { return err == nil } -// IsAlpha checks if the string contains only letters (a-zA-Z). Empty string is valid. +// IsAlpha check if the string contains only letters (a-zA-Z). Empty string is valid. func IsAlpha(str string) bool { if IsNull(str) { return true @@ -154,7 +154,7 @@ func IsAlpha(str string) bool { return rxAlpha.MatchString(str) } -//IsUTFLetter checks if the string contains only unicode letter characters. +//IsUTFLetter check if the string contains only unicode letter characters. //Similar to IsAlpha but for all languages. Empty string is valid. func IsUTFLetter(str string) bool { if IsNull(str) { @@ -170,7 +170,7 @@ func IsUTFLetter(str string) bool { } -// IsAlphanumeric checks if the string contains only letters and numbers. Empty string is valid. +// IsAlphanumeric check if the string contains only letters and numbers. Empty string is valid. func IsAlphanumeric(str string) bool { if IsNull(str) { return true @@ -178,7 +178,7 @@ func IsAlphanumeric(str string) bool { return rxAlphanumeric.MatchString(str) } -// IsUTFLetterNumeric checks if the string contains only unicode letters and numbers. Empty string is valid. +// IsUTFLetterNumeric check if the string contains only unicode letters and numbers. Empty string is valid. func IsUTFLetterNumeric(str string) bool { if IsNull(str) { return true @@ -192,7 +192,7 @@ func IsUTFLetterNumeric(str string) bool { } -// IsNumeric checks if the string contains only numbers. Empty string is valid. +// IsNumeric check if the string contains only numbers. Empty string is valid. func IsNumeric(str string) bool { if IsNull(str) { return true @@ -200,7 +200,7 @@ func IsNumeric(str string) bool { return rxNumeric.MatchString(str) } -// IsUTFNumeric checks if the string contains only unicode numbers of any kind. +// IsUTFNumeric check if the string contains only unicode numbers of any kind. // Numbers can be 0-9 but also Fractions ¾,Roman Ⅸ and Hangzhou 〩. Empty string is valid. func IsUTFNumeric(str string) bool { if IsNull(str) { @@ -222,7 +222,7 @@ func IsUTFNumeric(str string) bool { } -// IsUTFDigit checks if the string contains only unicode radix-10 decimal digits. Empty string is valid. +// IsUTFDigit check if the string contains only unicode radix-10 decimal digits. Empty string is valid. func IsUTFDigit(str string) bool { if IsNull(str) { return true @@ -243,22 +243,22 @@ func IsUTFDigit(str string) bool { } -// IsHexadecimal checks if the string is a hexadecimal number. +// IsHexadecimal check if the string is a hexadecimal number. func IsHexadecimal(str string) bool { return rxHexadecimal.MatchString(str) } -// IsHexcolor checks if the string is a hexadecimal color. +// IsHexcolor check if the string is a hexadecimal color. func IsHexcolor(str string) bool { return rxHexcolor.MatchString(str) } -// IsRGBcolor checks if the string is a valid RGB color in form rgb(RRR, GGG, BBB). +// IsRGBcolor check if the string is a valid RGB color in form rgb(RRR, GGG, BBB). func IsRGBcolor(str string) bool { return rxRGBcolor.MatchString(str) } -// IsLowerCase checks if the string is lowercase. Empty string is valid. +// IsLowerCase check if the string is lowercase. Empty string is valid. func IsLowerCase(str string) bool { if IsNull(str) { return true @@ -266,7 +266,7 @@ func IsLowerCase(str string) bool { return str == strings.ToLower(str) } -// IsUpperCase checks if the string is uppercase. Empty string is valid. +// IsUpperCase check if the string is uppercase. Empty string is valid. func IsUpperCase(str string) bool { if IsNull(str) { return true @@ -274,7 +274,7 @@ func IsUpperCase(str string) bool { return str == strings.ToUpper(str) } -// HasLowerCase checks if the string contains at least 1 lowercase. Empty string is valid. +// HasLowerCase check if the string contains at least 1 lowercase. Empty string is valid. func HasLowerCase(str string) bool { if IsNull(str) { return true @@ -282,7 +282,7 @@ func HasLowerCase(str string) bool { return rxHasLowerCase.MatchString(str) } -// HasUpperCase checks if the string contains as least 1 uppercase. Empty string is valid. +// HasUpperCase check if the string contians as least 1 uppercase. Empty string is valid. func HasUpperCase(str string) bool { if IsNull(str) { return true @@ -290,7 +290,7 @@ func HasUpperCase(str string) bool { return rxHasUpperCase.MatchString(str) } -// IsInt checks if the string is an integer. Empty string is valid. +// IsInt check if the string is an integer. Empty string is valid. func IsInt(str string) bool { if IsNull(str) { return true @@ -298,12 +298,12 @@ func IsInt(str string) bool { return rxInt.MatchString(str) } -// IsFloat checks if the string is a float. +// IsFloat check if the string is a float. func IsFloat(str string) bool { return str != "" && rxFloat.MatchString(str) } -// IsDivisibleBy checks if the string is a number that's divisible by another. +// IsDivisibleBy check if the string is a number that's divisible by another. // If second argument is not valid integer or zero, it's return false. // Otherwise, if first argument is not valid integer or zero, it's return true (Invalid string converts to zero). func IsDivisibleBy(str, num string) bool { @@ -316,178 +316,87 @@ func IsDivisibleBy(str, num string) bool { return (p == 0) || (p%q == 0) } -// IsNull checks if the string is null. +// IsNull check if the string is null. func IsNull(str string) bool { return len(str) == 0 } -// IsNotNull checks if the string is not null. -func IsNotNull(str string) bool { - return !IsNull(str) -} - // HasWhitespaceOnly checks the string only contains whitespace func HasWhitespaceOnly(str string) bool { - return len(str) > 0 && rxHasWhitespaceOnly.MatchString(str) + return len(str) > 0 && rxHasWhitespaceOnly.MatchString(str) } // HasWhitespace checks if the string contains any whitespace func HasWhitespace(str string) bool { - return len(str) > 0 && rxHasWhitespace.MatchString(str) + return len(str) > 0 && rxHasWhitespace.MatchString(str) } -// IsByteLength checks if the string's length (in bytes) falls in a range. +// IsByteLength check if the string's length (in bytes) falls in a range. func IsByteLength(str string, min, max int) bool { return len(str) >= min && len(str) <= max } -// IsUUIDv3 checks if the string is a UUID version 3. +// IsUUIDv3 check if the string is a UUID version 3. func IsUUIDv3(str string) bool { return rxUUID3.MatchString(str) } -// IsUUIDv4 checks if the string is a UUID version 4. +// IsUUIDv4 check if the string is a UUID version 4. func IsUUIDv4(str string) bool { return rxUUID4.MatchString(str) } -// IsUUIDv5 checks if the string is a UUID version 5. +// IsUUIDv5 check if the string is a UUID version 5. func IsUUIDv5(str string) bool { return rxUUID5.MatchString(str) } -// IsUUID checks if the string is a UUID (version 3, 4 or 5). +// IsUUID check if the string is a UUID (version 3, 4 or 5). func IsUUID(str string) bool { return rxUUID.MatchString(str) } -// Byte to index table for O(1) lookups when unmarshaling. -// We use 0xFF as sentinel value for invalid indexes. -var ulidDec = [...]byte{ - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x01, - 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, - 0x0F, 0x10, 0x11, 0xFF, 0x12, 0x13, 0xFF, 0x14, 0x15, 0xFF, - 0x16, 0x17, 0x18, 0x19, 0x1A, 0xFF, 0x1B, 0x1C, 0x1D, 0x1E, - 0x1F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0x0A, 0x0B, 0x0C, - 0x0D, 0x0E, 0x0F, 0x10, 0x11, 0xFF, 0x12, 0x13, 0xFF, 0x14, - 0x15, 0xFF, 0x16, 0x17, 0x18, 0x19, 0x1A, 0xFF, 0x1B, 0x1C, - 0x1D, 0x1E, 0x1F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, - 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, -} - -// EncodedSize is the length of a text encoded ULID. -const ulidEncodedSize = 26 - -// IsULID checks if the string is a ULID. -// -// Implementation got from: -// https://github.com/oklog/ulid (Apache-2.0 License) -// -func IsULID(str string) bool { - // Check if a base32 encoded ULID is the right length. - if len(str) != ulidEncodedSize { - return false - } - - // Check if all the characters in a base32 encoded ULID are part of the - // expected base32 character set. - if ulidDec[str[0]] == 0xFF || - ulidDec[str[1]] == 0xFF || - ulidDec[str[2]] == 0xFF || - ulidDec[str[3]] == 0xFF || - ulidDec[str[4]] == 0xFF || - ulidDec[str[5]] == 0xFF || - ulidDec[str[6]] == 0xFF || - ulidDec[str[7]] == 0xFF || - ulidDec[str[8]] == 0xFF || - ulidDec[str[9]] == 0xFF || - ulidDec[str[10]] == 0xFF || - ulidDec[str[11]] == 0xFF || - ulidDec[str[12]] == 0xFF || - ulidDec[str[13]] == 0xFF || - ulidDec[str[14]] == 0xFF || - ulidDec[str[15]] == 0xFF || - ulidDec[str[16]] == 0xFF || - ulidDec[str[17]] == 0xFF || - ulidDec[str[18]] == 0xFF || - ulidDec[str[19]] == 0xFF || - ulidDec[str[20]] == 0xFF || - ulidDec[str[21]] == 0xFF || - ulidDec[str[22]] == 0xFF || - ulidDec[str[23]] == 0xFF || - ulidDec[str[24]] == 0xFF || - ulidDec[str[25]] == 0xFF { - return false - } - - // Check if the first character in a base32 encoded ULID will overflow. This - // happens because the base32 representation encodes 130 bits, while the - // ULID is only 128 bits. - // - // See https://github.com/oklog/ulid/issues/9 for details. - if str[0] > '7' { - return false - } - return true -} - -// IsCreditCard checks if the string is a credit card. +// IsCreditCard check if the string is a credit card. func IsCreditCard(str string) bool { - sanitized := whiteSpacesAndMinus.ReplaceAllString(str, "") + sanitized := notNumberRegexp.ReplaceAllString(str, "") if !rxCreditCard.MatchString(sanitized) { return false } - - number, _ := ToInt(sanitized) - number, lastDigit := number / 10, number % 10 - var sum int64 - for i:=0; number > 0; i++ { - digit := number % 10 - - if i % 2 == 0 { - digit *= 2 - if digit > 9 { - digit -= 9 + var digit string + var tmpNum int64 + var shouldDouble bool + for i := len(sanitized) - 1; i >= 0; i-- { + digit = sanitized[i:(i + 1)] + tmpNum, _ = ToInt(digit) + if shouldDouble { + tmpNum *= 2 + if tmpNum >= 10 { + sum += ((tmpNum % 10) + 1) + } else { + sum += tmpNum } + } else { + sum += tmpNum } - - sum += digit - number = number / 10 + shouldDouble = !shouldDouble } - - return (sum + lastDigit) % 10 == 0 + + return sum%10 == 0 } -// IsISBN10 checks if the string is an ISBN version 10. +// IsISBN10 check if the string is an ISBN version 10. func IsISBN10(str string) bool { return IsISBN(str, 10) } -// IsISBN13 checks if the string is an ISBN version 13. +// IsISBN13 check if the string is an ISBN version 13. func IsISBN13(str string) bool { return IsISBN(str, 13) } -// IsISBN checks if the string is an ISBN (version 10 or 13). -// If version value is not equal to 10 or 13, it will be checks both variants. +// IsISBN check if the string is an ISBN (version 10 or 13). +// If version value is not equal to 10 or 13, it will be check both variants. func IsISBN(str string, version int) bool { sanitized := whiteSpacesAndMinus.ReplaceAllString(str, "") var checksum int32 @@ -521,13 +430,13 @@ func IsISBN(str string, version int) bool { return IsISBN(str, 10) || IsISBN(str, 13) } -// IsJSON checks if the string is valid JSON (note: uses json.Unmarshal). +// IsJSON check if the string is valid JSON (note: uses json.Unmarshal). func IsJSON(str string) bool { var js json.RawMessage return json.Unmarshal([]byte(str), &js) == nil } -// IsMultibyte checks if the string contains one or more multibyte chars. Empty string is valid. +// IsMultibyte check if the string contains one or more multibyte chars. Empty string is valid. func IsMultibyte(str string) bool { if IsNull(str) { return true @@ -535,7 +444,7 @@ func IsMultibyte(str string) bool { return rxMultibyte.MatchString(str) } -// IsASCII checks if the string contains ASCII chars only. Empty string is valid. +// IsASCII check if the string contains ASCII chars only. Empty string is valid. func IsASCII(str string) bool { if IsNull(str) { return true @@ -543,7 +452,7 @@ func IsASCII(str string) bool { return rxASCII.MatchString(str) } -// IsPrintableASCII checks if the string contains printable ASCII chars only. Empty string is valid. +// IsPrintableASCII check if the string contains printable ASCII chars only. Empty string is valid. func IsPrintableASCII(str string) bool { if IsNull(str) { return true @@ -551,7 +460,7 @@ func IsPrintableASCII(str string) bool { return rxPrintableASCII.MatchString(str) } -// IsFullWidth checks if the string contains any full-width chars. Empty string is valid. +// IsFullWidth check if the string contains any full-width chars. Empty string is valid. func IsFullWidth(str string) bool { if IsNull(str) { return true @@ -559,7 +468,7 @@ func IsFullWidth(str string) bool { return rxFullWidth.MatchString(str) } -// IsHalfWidth checks if the string contains any half-width chars. Empty string is valid. +// IsHalfWidth check if the string contains any half-width chars. Empty string is valid. func IsHalfWidth(str string) bool { if IsNull(str) { return true @@ -567,7 +476,7 @@ func IsHalfWidth(str string) bool { return rxHalfWidth.MatchString(str) } -// IsVariableWidth checks if the string contains a mixture of full and half-width chars. Empty string is valid. +// IsVariableWidth check if the string contains a mixture of full and half-width chars. Empty string is valid. func IsVariableWidth(str string) bool { if IsNull(str) { return true @@ -575,12 +484,12 @@ func IsVariableWidth(str string) bool { return rxHalfWidth.MatchString(str) && rxFullWidth.MatchString(str) } -// IsBase64 checks if a string is base64 encoded. +// IsBase64 check if a string is base64 encoded. func IsBase64(str string) bool { return rxBase64.MatchString(str) } -// IsFilePath checks is a string is Win or Unix file path and returns it's type. +// IsFilePath check is a string is Win or Unix file path and returns it's type. func IsFilePath(str string) (bool, int) { if rxWinPath.MatchString(str) { //check windows path limit see: @@ -595,27 +504,6 @@ func IsFilePath(str string) (bool, int) { return false, Unknown } -//IsWinFilePath checks both relative & absolute paths in Windows -func IsWinFilePath(str string) bool { - if rxARWinPath.MatchString(str) { - //check windows path limit see: - // http://msdn.microsoft.com/en-us/library/aa365247(VS.85).aspx#maxpath - if len(str[3:]) > 32767 { - return false - } - return true - } - return false -} - -//IsUnixFilePath checks both relative & absolute paths in Unix -func IsUnixFilePath(str string) bool { - if rxARUnixPath.MatchString(str) { - return true - } - return false -} - // IsDataURI checks if a string is base64 encoded data URI such as an image func IsDataURI(str string) bool { dataURI := strings.Split(str, ",") @@ -625,11 +513,6 @@ func IsDataURI(str string) bool { return IsBase64(dataURI[1]) } -// IsMagnetURI checks if a string is valid magnet URI -func IsMagnetURI(str string) bool { - return rxMagnetURI.MatchString(str) -} - // IsISO3166Alpha2 checks if a string is valid two-letter country code func IsISO3166Alpha2(str string) bool { for _, entry := range ISO3166List { @@ -682,7 +565,7 @@ func IsDNSName(str string) bool { // IsHash checks if a string is a hash of type algorithm. // Algorithm is one of ['md4', 'md5', 'sha1', 'sha256', 'sha384', 'sha512', 'ripemd128', 'ripemd160', 'tiger128', 'tiger160', 'tiger192', 'crc32', 'crc32b'] func IsHash(str string, algorithm string) bool { - var len string + len := "0" algo := strings.ToLower(algorithm) if algo == "crc32" || algo == "crc32b" { @@ -693,13 +576,11 @@ func IsHash(str string, algorithm string) bool { len = "40" } else if algo == "tiger192" { len = "48" - } else if algo == "sha3-224" { - len = "56" - } else if algo == "sha256" || algo == "sha3-256" { + } else if algo == "sha256" { len = "64" - } else if algo == "sha384" || algo == "sha3-384" { + } else if algo == "sha384" { len = "96" - } else if algo == "sha512" || algo == "sha3-512" { + } else if algo == "sha512" { len = "128" } else { return false @@ -708,93 +589,9 @@ func IsHash(str string, algorithm string) bool { return Matches(str, "^[a-f0-9]{"+len+"}$") } -// IsSHA3224 checks is a string is a SHA3-224 hash. Alias for `IsHash(str, "sha3-224")` -func IsSHA3224(str string) bool { - return IsHash(str, "sha3-224") -} - -// IsSHA3256 checks is a string is a SHA3-256 hash. Alias for `IsHash(str, "sha3-256")` -func IsSHA3256(str string) bool { - return IsHash(str, "sha3-256") -} - -// IsSHA3384 checks is a string is a SHA3-384 hash. Alias for `IsHash(str, "sha3-384")` -func IsSHA3384(str string) bool { - return IsHash(str, "sha3-384") -} - -// IsSHA3512 checks is a string is a SHA3-512 hash. Alias for `IsHash(str, "sha3-512")` -func IsSHA3512(str string) bool { - return IsHash(str, "sha3-512") -} - -// IsSHA512 checks is a string is a SHA512 hash. Alias for `IsHash(str, "sha512")` -func IsSHA512(str string) bool { - return IsHash(str, "sha512") -} - -// IsSHA384 checks is a string is a SHA384 hash. Alias for `IsHash(str, "sha384")` -func IsSHA384(str string) bool { - return IsHash(str, "sha384") -} - -// IsSHA256 checks is a string is a SHA256 hash. Alias for `IsHash(str, "sha256")` -func IsSHA256(str string) bool { - return IsHash(str, "sha256") -} - -// IsTiger192 checks is a string is a Tiger192 hash. Alias for `IsHash(str, "tiger192")` -func IsTiger192(str string) bool { - return IsHash(str, "tiger192") -} - -// IsTiger160 checks is a string is a Tiger160 hash. Alias for `IsHash(str, "tiger160")` -func IsTiger160(str string) bool { - return IsHash(str, "tiger160") -} - -// IsRipeMD160 checks is a string is a RipeMD160 hash. Alias for `IsHash(str, "ripemd160")` -func IsRipeMD160(str string) bool { - return IsHash(str, "ripemd160") -} - -// IsSHA1 checks is a string is a SHA-1 hash. Alias for `IsHash(str, "sha1")` -func IsSHA1(str string) bool { - return IsHash(str, "sha1") -} - -// IsTiger128 checks is a string is a Tiger128 hash. Alias for `IsHash(str, "tiger128")` -func IsTiger128(str string) bool { - return IsHash(str, "tiger128") -} - -// IsRipeMD128 checks is a string is a RipeMD128 hash. Alias for `IsHash(str, "ripemd128")` -func IsRipeMD128(str string) bool { - return IsHash(str, "ripemd128") -} - -// IsCRC32 checks is a string is a CRC32 hash. Alias for `IsHash(str, "crc32")` -func IsCRC32(str string) bool { - return IsHash(str, "crc32") -} - -// IsCRC32b checks is a string is a CRC32b hash. Alias for `IsHash(str, "crc32b")` -func IsCRC32b(str string) bool { - return IsHash(str, "crc32b") -} - -// IsMD5 checks is a string is a MD5 hash. Alias for `IsHash(str, "md5")` -func IsMD5(str string) bool { - return IsHash(str, "md5") -} - -// IsMD4 checks is a string is a MD4 hash. Alias for `IsHash(str, "md4")` -func IsMD4(str string) bool { - return IsHash(str, "md4") -} - // IsDialString validates the given string for usage with the various Dial() functions func IsDialString(str string) bool { + if h, p, err := net.SplitHostPort(str); err == nil && h != "" && p != "" && (IsDNSName(h) || IsIP(h)) && IsPort(p) { return true } @@ -802,7 +599,7 @@ func IsDialString(str string) bool { return false } -// IsIP checks if a string is either IP version 4 or 6. Alias for `net.ParseIP` +// IsIP checks if a string is either IP version 4 or 6. func IsIP(str string) bool { return net.ParseIP(str) != nil } @@ -815,25 +612,25 @@ func IsPort(str string) bool { return false } -// IsIPv4 checks if the string is an IP version 4. +// IsIPv4 check if the string is an IP version 4. func IsIPv4(str string) bool { ip := net.ParseIP(str) return ip != nil && strings.Contains(str, ".") } -// IsIPv6 checks if the string is an IP version 6. +// IsIPv6 check if the string is an IP version 6. func IsIPv6(str string) bool { ip := net.ParseIP(str) return ip != nil && strings.Contains(str, ":") } -// IsCIDR checks if the string is an valid CIDR notiation (IPV4 & IPV6) +// IsCIDR check if the string is an valid CIDR notiation (IPV4 & IPV6) func IsCIDR(str string) bool { _, _, err := net.ParseCIDR(str) return err == nil } -// IsMAC checks if a string is valid MAC address. +// IsMAC check if a string is valid MAC address. // Possible MAC formats: // 01:23:45:67:89:ab // 01:23:45:67:89:ab:cd:ef @@ -851,70 +648,22 @@ func IsHost(str string) bool { return IsIP(str) || IsDNSName(str) } -// IsMongoID checks if the string is a valid hex-encoded representation of a MongoDB ObjectId. +// IsMongoID check if the string is a valid hex-encoded representation of a MongoDB ObjectId. func IsMongoID(str string) bool { return rxHexadecimal.MatchString(str) && (len(str) == 24) } -// IsLatitude checks if a string is valid latitude. +// IsLatitude check if a string is valid latitude. func IsLatitude(str string) bool { return rxLatitude.MatchString(str) } -// IsLongitude checks if a string is valid longitude. +// IsLongitude check if a string is valid longitude. func IsLongitude(str string) bool { return rxLongitude.MatchString(str) } -// IsIMEI checks if a string is valid IMEI -func IsIMEI(str string) bool { - return rxIMEI.MatchString(str) -} - -// IsIMSI checks if a string is valid IMSI -func IsIMSI(str string) bool { - if !rxIMSI.MatchString(str) { - return false - } - - mcc, err := strconv.ParseInt(str[0:3], 10, 32) - if err != nil { - return false - } - - switch mcc { - case 202, 204, 206, 208, 212, 213, 214, 216, 218, 219: - case 220, 221, 222, 226, 228, 230, 231, 232, 234, 235: - case 238, 240, 242, 244, 246, 247, 248, 250, 255, 257: - case 259, 260, 262, 266, 268, 270, 272, 274, 276, 278: - case 280, 282, 283, 284, 286, 288, 289, 290, 292, 293: - case 294, 295, 297, 302, 308, 310, 311, 312, 313, 314: - case 315, 316, 330, 332, 334, 338, 340, 342, 344, 346: - case 348, 350, 352, 354, 356, 358, 360, 362, 363, 364: - case 365, 366, 368, 370, 372, 374, 376, 400, 401, 402: - case 404, 405, 406, 410, 412, 413, 414, 415, 416, 417: - case 418, 419, 420, 421, 422, 424, 425, 426, 427, 428: - case 429, 430, 431, 432, 434, 436, 437, 438, 440, 441: - case 450, 452, 454, 455, 456, 457, 460, 461, 466, 467: - case 470, 472, 502, 505, 510, 514, 515, 520, 525, 528: - case 530, 536, 537, 539, 540, 541, 542, 543, 544, 545: - case 546, 547, 548, 549, 550, 551, 552, 553, 554, 555: - case 602, 603, 604, 605, 606, 607, 608, 609, 610, 611: - case 612, 613, 614, 615, 616, 617, 618, 619, 620, 621: - case 622, 623, 624, 625, 626, 627, 628, 629, 630, 631: - case 632, 633, 634, 635, 636, 637, 638, 639, 640, 641: - case 642, 643, 645, 646, 647, 648, 649, 650, 651, 652: - case 653, 654, 655, 657, 658, 659, 702, 704, 706, 708: - case 710, 712, 714, 716, 722, 724, 730, 732, 734, 736: - case 738, 740, 742, 744, 746, 748, 750, 995: - return true - default: - return false - } - return true -} - -// IsRsaPublicKey checks if a string is valid public key with provided length +// IsRsaPublicKey check if a string is valid public key with provided length func IsRsaPublicKey(str string, keylen int) bool { bb := bytes.NewBufferString(str) pemBytes, err := ioutil.ReadAll(bb) @@ -948,14 +697,6 @@ func IsRsaPublicKey(str string, keylen int) bool { return bitlen == int(keylen) } -// IsRegex checks if a give string is a valid regex with RE2 syntax or not -func IsRegex(str string) bool { - if _, err := regexp.Compile(str); err == nil { - return true - } - return false -} - func toJSONName(tag string) string { if tag == "" { return "" @@ -976,7 +717,7 @@ func toJSONName(tag string) string { return name } -func prependPathToErrors(err error, path string) error { +func PrependPathToErrors(err error, path string) error { switch err2 := err.(type) { case Error: err2.Path = append([]string{path}, err2.Path...) @@ -984,125 +725,16 @@ func prependPathToErrors(err error, path string) error { case Errors: errors := err2.Errors() for i, err3 := range errors { - errors[i] = prependPathToErrors(err3, path) + errors[i] = PrependPathToErrors(err3, path) } return err2 } + fmt.Println(err) return err } -// ValidateArray performs validation according to condition iterator that validates every element of the array -func ValidateArray(array []interface{}, iterator ConditionIterator) bool { - return Every(array, iterator) -} - -// ValidateMap use validation map for fields. -// result will be equal to `false` if there are any errors. -// s is the map containing the data to be validated. -// m is the validation map in the form: -// map[string]interface{}{"name":"required,alpha","address":map[string]interface{}{"line1":"required,alphanum"}} -func ValidateMap(s map[string]interface{}, m map[string]interface{}) (bool, error) { - if s == nil { - return true, nil - } - result := true - var err error - var errs Errors - var index int - val := reflect.ValueOf(s) - for key, value := range s { - presentResult := true - validator, ok := m[key] - if !ok { - presentResult = false - var err error - err = fmt.Errorf("all map keys has to be present in the validation map; got %s", key) - err = prependPathToErrors(err, key) - errs = append(errs, err) - } - valueField := reflect.ValueOf(value) - mapResult := true - typeResult := true - structResult := true - resultField := true - switch subValidator := validator.(type) { - case map[string]interface{}: - var err error - if v, ok := value.(map[string]interface{}); !ok { - mapResult = false - err = fmt.Errorf("map validator has to be for the map type only; got %s", valueField.Type().String()) - err = prependPathToErrors(err, key) - errs = append(errs, err) - } else { - mapResult, err = ValidateMap(v, subValidator) - if err != nil { - mapResult = false - err = prependPathToErrors(err, key) - errs = append(errs, err) - } - } - case string: - if (valueField.Kind() == reflect.Struct || - (valueField.Kind() == reflect.Ptr && valueField.Elem().Kind() == reflect.Struct)) && - subValidator != "-" { - var err error - structResult, err = ValidateStruct(valueField.Interface()) - if err != nil { - err = prependPathToErrors(err, key) - errs = append(errs, err) - } - } - resultField, err = typeCheck(valueField, reflect.StructField{ - Name: key, - PkgPath: "", - Type: val.Type(), - Tag: reflect.StructTag(fmt.Sprintf("%s:%q", tagName, subValidator)), - Offset: 0, - Index: []int{index}, - Anonymous: false, - }, val, nil) - if err != nil { - errs = append(errs, err) - } - case nil: - // already handlerd when checked before - default: - typeResult = false - err = fmt.Errorf("map validator has to be either map[string]interface{} or string; got %s", valueField.Type().String()) - err = prependPathToErrors(err, key) - errs = append(errs, err) - } - result = result && presentResult && typeResult && resultField && structResult && mapResult - index++ - } - // checks required keys - requiredResult := true - for key, value := range m { - if schema, ok := value.(string); ok { - tags := parseTagIntoMap(schema) - if required, ok := tags["required"]; ok { - if _, ok := s[key]; !ok { - requiredResult = false - if required.customErrorMessage != "" { - err = Error{key, fmt.Errorf(required.customErrorMessage), true, "required", []string{}} - } else { - err = Error{key, fmt.Errorf("required field missing"), false, "required", []string{}} - } - errs = append(errs, err) - } - } - } - } - - if len(errs) > 0 { - err = errs - } - return result && requiredResult, err -} - // ValidateStruct use tags for fields. // result will be equal to `false` if there are any errors. -// todo currently there is no guarantee that errors will be returned in predictable order (tests may to fail) func ValidateStruct(s interface{}) (bool, error) { if s == nil { return true, nil @@ -1134,7 +766,7 @@ func ValidateStruct(s interface{}) (bool, error) { var err error structResult, err = ValidateStruct(valueField.Interface()) if err != nil { - err = prependPathToErrors(err, typeField.Name) + err = PrependPathToErrors(err, typeField.Name) errs = append(errs, err) } } @@ -1171,42 +803,6 @@ func ValidateStruct(s interface{}) (bool, error) { return result, err } -// ValidateStructAsync performs async validation of the struct and returns results through the channels -func ValidateStructAsync(s interface{}) (<-chan bool, <-chan error) { - res := make(chan bool) - errors := make(chan error) - - go func() { - defer close(res) - defer close(errors) - - isValid, isFailed := ValidateStruct(s) - - res <- isValid - errors <- isFailed - }() - - return res, errors -} - -// ValidateMapAsync performs async validation of the map and returns results through the channels -func ValidateMapAsync(s map[string]interface{}, m map[string]interface{}) (<-chan bool, <-chan error) { - res := make(chan bool) - errors := make(chan error) - - go func() { - defer close(res) - defer close(errors) - - isValid, isFailed := ValidateMap(s, m) - - res <- isValid - errors <- isFailed - }() - - return res, errors -} - // parseTagIntoMap parses a struct tag `valid:required~Some error message,length(2|3)` into map[string]string{"required": "Some error message", "length(2|3)": ""} func parseTagIntoMap(tag string) tagOptionsMap { optionsMap := make(tagOptionsMap) @@ -1255,45 +851,28 @@ func IsSSN(str string) bool { return rxSSN.MatchString(str) } -// IsSemver checks if string is valid semantic version +// IsSemver check if string is valid semantic version func IsSemver(str string) bool { return rxSemver.MatchString(str) } -// IsType checks if interface is of some type -func IsType(v interface{}, params ...string) bool { - if len(params) == 1 { - typ := params[0] - return strings.Replace(reflect.TypeOf(v).String(), " ", "", -1) == strings.Replace(typ, " ", "", -1) - } - return false -} - -// IsTime checks if string is valid according to given format +// IsTime check if string is valid according to given format func IsTime(str string, format string) bool { _, err := time.Parse(format, str) return err == nil } -// IsUnixTime checks if string is valid unix timestamp value -func IsUnixTime(str string) bool { - if _, err := strconv.Atoi(str); err == nil { - return true - } - return false -} - -// IsRFC3339 checks if string is valid timestamp value according to RFC3339 +// IsRFC3339 check if string is valid timestamp value according to RFC3339 func IsRFC3339(str string) bool { return IsTime(str, time.RFC3339) } -// IsRFC3339WithoutZone checks if string is valid timestamp value according to RFC3339 which excludes the timezone. +// IsRFC3339WithoutZone check if string is valid timestamp value according to RFC3339 which excludes the timezone. func IsRFC3339WithoutZone(str string) bool { - return IsTime(str, rfc3339WithoutZone) + return IsTime(str, RF3339WithoutZone) } -// IsISO4217 checks if string is valid ISO currency code +// IsISO4217 check if string is valid ISO currency code func IsISO4217(str string) bool { for _, currency := range ISO4217List { if str == currency { @@ -1304,7 +883,7 @@ func IsISO4217(str string) bool { return false } -// ByteLength checks string's length +// ByteLength check string's length func ByteLength(str string, params ...string) bool { if len(params) == 2 { min, _ := ToInt(params[0]) @@ -1315,13 +894,13 @@ func ByteLength(str string, params ...string) bool { return false } -// RuneLength checks string's length +// RuneLength check string's length // Alias for StringLength func RuneLength(str string, params ...string) bool { return StringLength(str, params...) } -// IsRsaPub checks whether string is valid RSA key +// IsRsaPub check whether string is valid RSA key // Alias for IsRsaPublicKey func IsRsaPub(str string, params ...string) bool { if len(params) == 1 { @@ -1341,7 +920,7 @@ func StringMatches(s string, params ...string) bool { return false } -// StringLength checks string's length (including multi byte strings) +// StringLength check string's length (including multi byte strings) func StringLength(str string, params ...string) bool { if len(params) == 2 { @@ -1354,31 +933,7 @@ func StringLength(str string, params ...string) bool { return false } -// MinStringLength checks string's minimum length (including multi byte strings) -func MinStringLength(str string, params ...string) bool { - - if len(params) == 1 { - strLength := utf8.RuneCountInString(str) - min, _ := ToInt(params[0]) - return strLength >= int(min) - } - - return false -} - -// MaxStringLength checks string's maximum length (including multi byte strings) -func MaxStringLength(str string, params ...string) bool { - - if len(params) == 1 { - strLength := utf8.RuneCountInString(str) - max, _ := ToInt(params[0]) - return strLength <= int(max) - } - - return false -} - -// Range checks string's length +// Range check string's length func Range(str string, params ...string) bool { if len(params) == 2 { value, _ := ToFloat(str) @@ -1390,8 +945,7 @@ func Range(str string, params ...string) bool { return false } -// IsInRaw checks if string is in list of allowed values -func IsInRaw(str string, params ...string) bool { +func isInRaw(str string, params ...string) bool { if len(params) == 1 { rawParams := params[0] @@ -1403,7 +957,7 @@ func IsInRaw(str string, params ...string) bool { return false } -// IsIn checks if string str is a member of the set of strings params +// IsIn check if string str is a member of the set of strings params func IsIn(str string, params ...string) bool { for _, param := range params { if str == param { @@ -1441,7 +995,7 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options tag := t.Tag.Get(tagName) - // checks if the field should be ignored + // Check if the field should be ignored switch tag { case "": if v.Kind() != reflect.Slice && v.Kind() != reflect.Map { @@ -1461,7 +1015,7 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options } if isEmptyValue(v) { - // an empty value is not validated, checks only required + // an empty value is not validated, check only required isValid, resultErr = checkRequired(v, t, options) for key := range options { delete(options, key) @@ -1508,65 +1062,26 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options }() } - for _, validatorSpec := range optionsOrder { - validatorStruct := options[validatorSpec] - var negate bool - validator := validatorSpec - customMsgExists := len(validatorStruct.customErrorMessage) > 0 - - // checks whether the tag looks like '!something' or 'something' - if validator[0] == '!' { - validator = validator[1:] - negate = true - } - - // checks for interface param validators - for key, value := range InterfaceParamTagRegexMap { - ps := value.FindStringSubmatch(validator) - if len(ps) == 0 { - continue - } - - validatefunc, ok := InterfaceParamTagMap[key] - if !ok { - continue - } - - delete(options, validatorSpec) - - field := fmt.Sprint(v) - if result := validatefunc(v.Interface(), ps[1:]...); (!result && !negate) || (result && negate) { - if customMsgExists { - return false, Error{t.Name, TruncatingErrorf(validatorStruct.customErrorMessage, field, validator), customMsgExists, stripParams(validatorSpec), []string{}} - } - if negate { - return false, Error{t.Name, fmt.Errorf("%s does validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}} - } - return false, Error{t.Name, fmt.Errorf("%s does not validate as %s", field, validator), customMsgExists, stripParams(validatorSpec), []string{}} - } - } - } - switch v.Kind() { case reflect.Bool, reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr, reflect.Float32, reflect.Float64, reflect.String: - // for each tag option checks the map of validator functions + // for each tag option check the map of validator functions for _, validatorSpec := range optionsOrder { validatorStruct := options[validatorSpec] var negate bool validator := validatorSpec customMsgExists := len(validatorStruct.customErrorMessage) > 0 - // checks whether the tag looks like '!something' or 'something' + // Check whether the tag looks like '!something' or 'something' if validator[0] == '!' { validator = validator[1:] negate = true } - // checks for param validators + // Check for param validators for key, value := range ParamTagRegexMap { ps := value.FindStringSubmatch(validator) if len(ps) == 0 { @@ -1606,10 +1121,10 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options delete(options, validatorSpec) switch v.Kind() { - case reflect.String, - reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, - reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, - reflect.Float32, reflect.Float64: + case reflect.String, + reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64, + reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, + reflect.Float32, reflect.Float64: field := fmt.Sprint(v) // make value into string, then validate with regex if result := validatefunc(field); !result && !negate || result && negate { if customMsgExists { @@ -1647,7 +1162,7 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options } else { resultItem, err = ValidateStruct(v.MapIndex(k).Interface()) if err != nil { - err = prependPathToErrors(err, t.Name+"."+sv[i].Interface().(string)) + err = PrependPathToErrors(err, t.Name+"."+sv[i].Interface().(string)) return false, err } } @@ -1667,7 +1182,7 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options } else { resultItem, err = ValidateStruct(v.Index(i).Interface()) if err != nil { - err = prependPathToErrors(err, t.Name+"."+strconv.Itoa(i)) + err = PrependPathToErrors(err, t.Name+"."+strconv.Itoa(i)) return false, err } } @@ -1681,13 +1196,13 @@ func typeCheck(v reflect.Value, t reflect.StructField, o reflect.Value, options } return ValidateStruct(v.Interface()) case reflect.Ptr: - // If the value is a pointer then checks its element + // If the value is a pointer then check its element if v.IsNil() { return true, nil } return typeCheck(v.Elem(), t, o, options) case reflect.Struct: - return true, nil + return ValidateStruct(v.Interface()) default: return false, &UnsupportedTypeError{v.Type()} } @@ -1697,7 +1212,6 @@ func stripParams(validatorString string) string { return paramsRegexp.ReplaceAllString(validatorString, "") } -// isEmptyValue checks whether value empty or not func isEmptyValue(v reflect.Value) bool { switch v.Kind() { case reflect.String, reflect.Array: @@ -1738,11 +1252,11 @@ func ErrorsByField(e error) map[string]string { } // prototype for ValidateStruct - switch e := e.(type) { + switch e.(type) { case Error: - m[e.Name] = e.Err.Error() + m[e.(Error).Name] = e.(Error).Err.Error() case Errors: - for _, item := range e.Errors() { + for _, item := range e.(Errors).Errors() { n := ErrorsByField(item) for k, v := range n { m[k] = v @@ -1762,7 +1276,3 @@ func (sv stringValues) Len() int { return len(sv) } func (sv stringValues) Swap(i, j int) { sv[i], sv[j] = sv[j], sv[i] } func (sv stringValues) Less(i, j int) bool { return sv.get(i) < sv.get(j) } func (sv stringValues) get(i int) string { return sv[i].String() } - -func IsE164(str string) bool { - return rxE164.MatchString(str) -} diff --git a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/wercker.yml b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/wercker.yml index bc5f7b0864b..cac7a5fcf06 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/wercker.yml +++ b/cluster-api/providers/vsphere/vendor/github.com/asaskevich/govalidator/wercker.yml @@ -12,4 +12,4 @@ build: - script: name: go test code: | - go test -race -v ./... + go test -race ./... diff --git a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/CHANGES.md b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/CHANGES.md index 92b78048e23..6f24dfff562 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/CHANGES.md +++ b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/CHANGES.md @@ -1,5 +1,8 @@ # Change history of go-restful +## [v3.12.2] - 2025-02-21 + +- allow empty payloads in post,put,patch, issue #580 ( thanks @liggitt, Jordan Liggitt) ## [v3.12.1] - 2024-05-28 @@ -18,7 +21,7 @@ - fix by restoring custom JSON handler functions (Mike Beaumont #540) -## [v3.12.0] - 2023-08-19 +## [v3.11.0] - 2023-08-19 - restored behavior as <= v3.9.0 with option to change path strategy using TrimRightSlashEnabled. diff --git a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/README.md b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/README.md index 7234604e47b..3fb40d19808 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/README.md +++ b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/README.md @@ -3,7 +3,7 @@ go-restful package for building REST-style Web Services using Google Go [![Go Report Card](https://goreportcard.com/badge/github.com/emicklei/go-restful)](https://goreportcard.com/report/github.com/emicklei/go-restful) -[![GoDoc](https://godoc.org/github.com/emicklei/go-restful?status.svg)](https://pkg.go.dev/github.com/emicklei/go-restful) +[![Go Reference](https://pkg.go.dev/badge/github.com/emicklei/go-restful.svg)](https://pkg.go.dev/github.com/emicklei/go-restful/v3) [![codecov](https://codecov.io/gh/emicklei/go-restful/branch/master/graph/badge.svg)](https://codecov.io/gh/emicklei/go-restful) - [Code examples use v3](https://github.com/emicklei/go-restful/tree/v3/examples) diff --git a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/jsr311.go b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/jsr311.go index a9b3faaa81f..7f04bd90533 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/jsr311.go +++ b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/jsr311.go @@ -65,7 +65,7 @@ func (RouterJSR311) extractParams(pathExpr *pathExpression, matches []string) ma return params } -// http://jsr311.java.net/nonav/releases/1.1/spec/spec3.html#x3-360003.7.2 +// https://download.oracle.com/otndocs/jcp/jaxrs-1.1-mrel-eval-oth-JSpec/ func (r RouterJSR311) detectRoute(routes []Route, httpRequest *http.Request) (*Route, error) { candidates := make([]*Route, 0, 8) for i, each := range routes { @@ -126,9 +126,7 @@ func (r RouterJSR311) detectRoute(routes []Route, httpRequest *http.Request) (*R if trace { traceLogger.Printf("no Route found (from %d) that matches HTTP Content-Type: %s\n", len(previous), contentType) } - if httpRequest.ContentLength > 0 { - return nil, NewError(http.StatusUnsupportedMediaType, "415: Unsupported Media Type") - } + return nil, NewError(http.StatusUnsupportedMediaType, "415: Unsupported Media Type") } // accept @@ -151,20 +149,9 @@ func (r RouterJSR311) detectRoute(routes []Route, httpRequest *http.Request) (*R for _, candidate := range previous { available = append(available, candidate.Produces...) } - // if POST,PUT,PATCH without body - method, length := httpRequest.Method, httpRequest.Header.Get("Content-Length") - if (method == http.MethodPost || - method == http.MethodPut || - method == http.MethodPatch) && (length == "" || length == "0") { - return nil, NewError( - http.StatusUnsupportedMediaType, - fmt.Sprintf("415: Unsupported Media Type\n\nAvailable representations: %s", strings.Join(available, ", ")), - ) - } return nil, NewError( http.StatusNotAcceptable, - fmt.Sprintf("406: Not Acceptable\n\nAvailable representations: %s", strings.Join(available, ", ")), - ) + fmt.Sprintf("406: Not Acceptable\n\nAvailable representations: %s", strings.Join(available, ", "))) } // return r.bestMatchByMedia(outputMediaOk, contentType, accept), nil return candidates[0], nil diff --git a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/route.go b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/route.go index 306c44be779..a2056e2acbb 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/route.go +++ b/cluster-api/providers/vsphere/vendor/github.com/emicklei/go-restful/v3/route.go @@ -111,6 +111,8 @@ func (r Route) matchesAccept(mimeTypesWithQuality string) bool { } // Return whether this Route can consume content with a type specified by mimeTypes (can be empty). +// If the route does not specify Consumes then return true (*/*). +// If no content type is set then return true for GET,HEAD,OPTIONS,DELETE and TRACE. func (r Route) matchesContentType(mimeTypes string) bool { if len(r.Consumes) == 0 { diff --git a/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/merge.go b/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/merge.go index f79caf3135a..d60afadcf1e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/merge.go +++ b/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/merge.go @@ -103,8 +103,8 @@ func pruneAryNulls(ary *partialArray, options *ApplyOptions) *partialArray { return ary } -var errBadJSONDoc = fmt.Errorf("Invalid JSON Document") -var errBadJSONPatch = fmt.Errorf("Invalid JSON Patch") +var ErrBadJSONDoc = fmt.Errorf("Invalid JSON Document") +var ErrBadJSONPatch = fmt.Errorf("Invalid JSON Patch") var errBadMergeTypes = fmt.Errorf("Mismatched JSON Documents") // MergeMergePatches merges two merge patches together, such that @@ -121,11 +121,11 @@ func MergePatch(docData, patchData []byte) ([]byte, error) { func doMergePatch(docData, patchData []byte, mergeMerge bool) ([]byte, error) { if !json.Valid(docData) { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } if !json.Valid(patchData) { - return nil, errBadJSONPatch + return nil, ErrBadJSONPatch } options := NewApplyOptions() @@ -143,7 +143,7 @@ func doMergePatch(docData, patchData []byte, mergeMerge bool) ([]byte, error) { patchErr := patch.UnmarshalJSON(patchData) if isSyntaxError(docErr) { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } if isSyntaxError(patchErr) { @@ -151,7 +151,7 @@ func doMergePatch(docData, patchData []byte, mergeMerge bool) ([]byte, error) { } if docErr == nil && doc.obj == nil { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } if patchErr == nil && patch.obj == nil { @@ -175,7 +175,7 @@ func doMergePatch(docData, patchData []byte, mergeMerge bool) ([]byte, error) { if json.Valid(patchData) { return patchData, nil } - return nil, errBadJSONPatch + return nil, ErrBadJSONPatch } pruneAryNulls(patchAry, options) @@ -183,7 +183,7 @@ func doMergePatch(docData, patchData []byte, mergeMerge bool) ([]byte, error) { out, patchErr := json.Marshal(patchAry.nodes) if patchErr != nil { - return nil, errBadJSONPatch + return nil, ErrBadJSONPatch } return out, nil @@ -256,12 +256,12 @@ func createObjectMergePatch(originalJSON, modifiedJSON []byte) ([]byte, error) { err := unmarshal(originalJSON, &originalDoc) if err != nil { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } err = unmarshal(modifiedJSON, &modifiedDoc) if err != nil { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } dest, err := getDiff(originalDoc, modifiedDoc) @@ -286,17 +286,17 @@ func createArrayMergePatch(originalJSON, modifiedJSON []byte) ([]byte, error) { err := unmarshal(originalJSON, &originalDocs) if err != nil { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } err = unmarshal(modifiedJSON, &modifiedDocs) if err != nil { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } total := len(originalDocs) if len(modifiedDocs) != total { - return nil, errBadJSONDoc + return nil, ErrBadJSONDoc } result := []json.RawMessage{} diff --git a/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/patch.go b/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/patch.go index 7a7f71c8b66..83102e5570a 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/patch.go +++ b/cluster-api/providers/vsphere/vendor/github.com/evanphx/json-patch/v5/patch.go @@ -2,13 +2,13 @@ package jsonpatch import ( "bytes" + "errors" "fmt" "strconv" "strings" "unicode" "github.com/evanphx/json-patch/v5/internal/json" - "github.com/pkg/errors" ) const ( @@ -461,7 +461,7 @@ func (o Operation) Path() (string, error) { return op, nil } - return "unknown", errors.Wrapf(ErrMissing, "operation missing path field") + return "unknown", fmt.Errorf("operation missing path field: %w", ErrMissing) } // From reads the "from" field of the Operation. @@ -478,7 +478,7 @@ func (o Operation) From() (string, error) { return op, nil } - return "unknown", errors.Wrapf(ErrMissing, "operation, missing from field") + return "unknown", fmt.Errorf("operation, missing from field: %w", ErrMissing) } func (o Operation) value() *lazyNode { @@ -511,7 +511,7 @@ func (o Operation) ValueInterface() (interface{}, error) { return v, nil } - return nil, errors.Wrapf(ErrMissing, "operation, missing value field") + return nil, fmt.Errorf("operation, missing value field: %w", ErrMissing) } func isArray(buf []byte) bool { @@ -610,7 +610,7 @@ func (d *partialDoc) get(key string, options *ApplyOptions) (*lazyNode, error) { v, ok := d.obj[key] if !ok { - return v, errors.Wrapf(ErrMissing, "unable to get nonexistent key: %s", key) + return v, fmt.Errorf("unable to get nonexistent key: %s: %w", key, ErrMissing) } return v, nil } @@ -625,7 +625,7 @@ func (d *partialDoc) remove(key string, options *ApplyOptions) error { if options.AllowMissingPathOnRemove { return nil } - return errors.Wrapf(ErrMissing, "unable to remove nonexistent key: %s", key) + return fmt.Errorf("unable to remove nonexistent key: %s: %w", key, ErrMissing) } idx := -1 for i, k := range d.keys { @@ -649,10 +649,10 @@ func (d *partialArray) set(key string, val *lazyNode, options *ApplyOptions) err if idx < 0 { if !options.SupportNegativeIndices { - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } if idx < -len(d.nodes) { - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } idx += len(d.nodes) } @@ -669,7 +669,7 @@ func (d *partialArray) add(key string, val *lazyNode, options *ApplyOptions) err idx, err := strconv.Atoi(key) if err != nil { - return errors.Wrapf(err, "value was not a proper array index: '%s'", key) + return fmt.Errorf("value was not a proper array index: '%s': %w", key, err) } sz := len(d.nodes) + 1 @@ -679,15 +679,15 @@ func (d *partialArray) add(key string, val *lazyNode, options *ApplyOptions) err cur := d if idx >= len(ary) { - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } if idx < 0 { if !options.SupportNegativeIndices { - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } if idx < -len(ary) { - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } idx += len(ary) } @@ -713,16 +713,16 @@ func (d *partialArray) get(key string, options *ApplyOptions) (*lazyNode, error) if idx < 0 { if !options.SupportNegativeIndices { - return nil, errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return nil, fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } if idx < -len(d.nodes) { - return nil, errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return nil, fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } idx += len(d.nodes) } if idx >= len(d.nodes) { - return nil, errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return nil, fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } return d.nodes[idx], nil @@ -740,18 +740,18 @@ func (d *partialArray) remove(key string, options *ApplyOptions) error { if options.AllowMissingPathOnRemove { return nil } - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } if idx < 0 { if !options.SupportNegativeIndices { - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } if idx < -len(cur.nodes) { if options.AllowMissingPathOnRemove { return nil } - return errors.Wrapf(ErrInvalidIndex, "Unable to access invalid index: %d", idx) + return fmt.Errorf("Unable to access invalid index: %d: %w", idx, ErrInvalidIndex) } idx += len(cur.nodes) } @@ -768,7 +768,7 @@ func (d *partialArray) remove(key string, options *ApplyOptions) error { func (p Patch) add(doc *container, op Operation, options *ApplyOptions) error { path, err := op.Path() if err != nil { - return errors.Wrapf(ErrMissing, "add operation failed to decode path") + return fmt.Errorf("add operation failed to decode path: %w", ErrMissing) } // special case, adding to empty means replacing the container with the value given @@ -809,12 +809,12 @@ func (p Patch) add(doc *container, op Operation, options *ApplyOptions) error { con, key := findObject(doc, path, options) if con == nil { - return errors.Wrapf(ErrMissing, "add operation does not apply: doc is missing path: \"%s\"", path) + return fmt.Errorf("add operation does not apply: doc is missing path: \"%s\": %w", path, ErrMissing) } err = con.add(key, op.value(), options) if err != nil { - return errors.Wrapf(err, "error in add for path: '%s'", path) + return fmt.Errorf("error in add for path: '%s': %w", path, err) } return nil @@ -867,11 +867,11 @@ func ensurePathExists(pd *container, path string, options *ApplyOptions) error { if arrIndex < 0 { if !options.SupportNegativeIndices { - return errors.Wrapf(ErrInvalidIndex, "Unable to ensure path for invalid index: %d", arrIndex) + return fmt.Errorf("Unable to ensure path for invalid index: %d: %w", arrIndex, ErrInvalidIndex) } if arrIndex < -1 { - return errors.Wrapf(ErrInvalidIndex, "Unable to ensure path for negative index other than -1: %d", arrIndex) + return fmt.Errorf("Unable to ensure path for negative index other than -1: %d: %w", arrIndex, ErrInvalidIndex) } arrIndex = 0 @@ -918,11 +918,11 @@ func validateOperation(op Operation) error { switch op.Kind() { case "add", "replace": if _, err := op.ValueInterface(); err != nil { - return errors.Wrapf(err, "failed to decode 'value'") + return fmt.Errorf("failed to decode 'value': %w", err) } case "move", "copy": if _, err := op.From(); err != nil { - return errors.Wrapf(err, "failed to decode 'from'") + return fmt.Errorf("failed to decode 'from': %w", err) } case "remove", "test": default: @@ -930,7 +930,7 @@ func validateOperation(op Operation) error { } if _, err := op.Path(); err != nil { - return errors.Wrapf(err, "failed to decode 'path'") + return fmt.Errorf("failed to decode 'path': %w", err) } return nil @@ -941,10 +941,10 @@ func validatePatch(p Patch) error { if err := validateOperation(op); err != nil { opData, infoErr := json.Marshal(op) if infoErr != nil { - return errors.Wrapf(err, "invalid operation") + return fmt.Errorf("invalid operation: %w", err) } - return errors.Wrapf(err, "invalid operation %s", opData) + return fmt.Errorf("invalid operation %s: %w", opData, err) } } @@ -954,7 +954,7 @@ func validatePatch(p Patch) error { func (p Patch) remove(doc *container, op Operation, options *ApplyOptions) error { path, err := op.Path() if err != nil { - return errors.Wrapf(ErrMissing, "remove operation failed to decode path") + return fmt.Errorf("remove operation failed to decode path: %w", ErrMissing) } con, key := findObject(doc, path, options) @@ -963,12 +963,12 @@ func (p Patch) remove(doc *container, op Operation, options *ApplyOptions) error if options.AllowMissingPathOnRemove { return nil } - return errors.Wrapf(ErrMissing, "remove operation does not apply: doc is missing path: \"%s\"", path) + return fmt.Errorf("remove operation does not apply: doc is missing path: \"%s\": %w", path, ErrMissing) } err = con.remove(key, options) if err != nil { - return errors.Wrapf(err, "error in remove for path: '%s'", path) + return fmt.Errorf("error in remove for path: '%s': %w", path, err) } return nil @@ -977,7 +977,7 @@ func (p Patch) remove(doc *container, op Operation, options *ApplyOptions) error func (p Patch) replace(doc *container, op Operation, options *ApplyOptions) error { path, err := op.Path() if err != nil { - return errors.Wrapf(err, "replace operation failed to decode path") + return fmt.Errorf("replace operation failed to decode path: %w", err) } if path == "" { @@ -986,7 +986,7 @@ func (p Patch) replace(doc *container, op Operation, options *ApplyOptions) erro if val.which == eRaw { if !val.tryDoc() { if !val.tryAry() { - return errors.Wrapf(err, "replace operation value must be object or array") + return fmt.Errorf("replace operation value must be object or array: %w", err) } } else { val.doc.opts = options @@ -999,7 +999,7 @@ func (p Patch) replace(doc *container, op Operation, options *ApplyOptions) erro case eDoc: *doc = val.doc case eRaw: - return errors.Wrapf(err, "replace operation hit impossible case") + return fmt.Errorf("replace operation hit impossible case: %w", err) } return nil @@ -1008,17 +1008,17 @@ func (p Patch) replace(doc *container, op Operation, options *ApplyOptions) erro con, key := findObject(doc, path, options) if con == nil { - return errors.Wrapf(ErrMissing, "replace operation does not apply: doc is missing path: %s", path) + return fmt.Errorf("replace operation does not apply: doc is missing path: %s: %w", path, ErrMissing) } _, ok := con.get(key, options) if ok != nil { - return errors.Wrapf(ErrMissing, "replace operation does not apply: doc is missing key: %s", path) + return fmt.Errorf("replace operation does not apply: doc is missing key: %s: %w", path, ErrMissing) } err = con.set(key, op.value(), options) if err != nil { - return errors.Wrapf(err, "error in remove for path: '%s'", path) + return fmt.Errorf("error in remove for path: '%s': %w", path, err) } return nil @@ -1027,43 +1027,43 @@ func (p Patch) replace(doc *container, op Operation, options *ApplyOptions) erro func (p Patch) move(doc *container, op Operation, options *ApplyOptions) error { from, err := op.From() if err != nil { - return errors.Wrapf(err, "move operation failed to decode from") + return fmt.Errorf("move operation failed to decode from: %w", err) } if from == "" { - return errors.Wrapf(ErrInvalid, "unable to move entire document to another path") + return fmt.Errorf("unable to move entire document to another path: %w", ErrInvalid) } con, key := findObject(doc, from, options) if con == nil { - return errors.Wrapf(ErrMissing, "move operation does not apply: doc is missing from path: %s", from) + return fmt.Errorf("move operation does not apply: doc is missing from path: %s: %w", from, ErrMissing) } val, err := con.get(key, options) if err != nil { - return errors.Wrapf(err, "error in move for path: '%s'", key) + return fmt.Errorf("error in move for path: '%s': %w", key, err) } err = con.remove(key, options) if err != nil { - return errors.Wrapf(err, "error in move for path: '%s'", key) + return fmt.Errorf("error in move for path: '%s': %w", key, err) } path, err := op.Path() if err != nil { - return errors.Wrapf(err, "move operation failed to decode path") + return fmt.Errorf("move operation failed to decode path: %w", err) } con, key = findObject(doc, path, options) if con == nil { - return errors.Wrapf(ErrMissing, "move operation does not apply: doc is missing destination path: %s", path) + return fmt.Errorf("move operation does not apply: doc is missing destination path: %s: %w", path, ErrMissing) } err = con.add(key, val, options) if err != nil { - return errors.Wrapf(err, "error in move for path: '%s'", path) + return fmt.Errorf("error in move for path: '%s': %w", path, err) } return nil @@ -1072,7 +1072,7 @@ func (p Patch) move(doc *container, op Operation, options *ApplyOptions) error { func (p Patch) test(doc *container, op Operation, options *ApplyOptions) error { path, err := op.Path() if err != nil { - return errors.Wrapf(err, "test operation failed to decode path") + return fmt.Errorf("test operation failed to decode path: %w", err) } if path == "" { @@ -1091,18 +1091,18 @@ func (p Patch) test(doc *container, op Operation, options *ApplyOptions) error { return nil } - return errors.Wrapf(ErrTestFailed, "testing value %s failed", path) + return fmt.Errorf("testing value %s failed: %w", path, ErrTestFailed) } con, key := findObject(doc, path, options) if con == nil { - return errors.Wrapf(ErrMissing, "test operation does not apply: is missing path: %s", path) + return fmt.Errorf("test operation does not apply: is missing path: %s: %w", path, ErrMissing) } val, err := con.get(key, options) - if err != nil && errors.Cause(err) != ErrMissing { - return errors.Wrapf(err, "error in test for path: '%s'", path) + if err != nil && errors.Unwrap(err) != ErrMissing { + return fmt.Errorf("error in test for path: '%s': %w", path, err) } ov := op.value() @@ -1111,49 +1111,49 @@ func (p Patch) test(doc *container, op Operation, options *ApplyOptions) error { if ov.isNull() { return nil } - return errors.Wrapf(ErrTestFailed, "testing value %s failed", path) + return fmt.Errorf("testing value %s failed: %w", path, ErrTestFailed) } else if ov.isNull() { - return errors.Wrapf(ErrTestFailed, "testing value %s failed", path) + return fmt.Errorf("testing value %s failed: %w", path, ErrTestFailed) } if val.equal(op.value()) { return nil } - return errors.Wrapf(ErrTestFailed, "testing value %s failed", path) + return fmt.Errorf("testing value %s failed: %w", path, ErrTestFailed) } func (p Patch) copy(doc *container, op Operation, accumulatedCopySize *int64, options *ApplyOptions) error { from, err := op.From() if err != nil { - return errors.Wrapf(err, "copy operation failed to decode from") + return fmt.Errorf("copy operation failed to decode from: %w", err) } con, key := findObject(doc, from, options) if con == nil { - return errors.Wrapf(ErrMissing, "copy operation does not apply: doc is missing from path: \"%s\"", from) + return fmt.Errorf("copy operation does not apply: doc is missing from path: \"%s\": %w", from, ErrMissing) } val, err := con.get(key, options) if err != nil { - return errors.Wrapf(err, "error in copy for from: '%s'", from) + return fmt.Errorf("error in copy for from: '%s': %w", from, err) } path, err := op.Path() if err != nil { - return errors.Wrapf(ErrMissing, "copy operation failed to decode path") + return fmt.Errorf("copy operation failed to decode path: %w", ErrMissing) } con, key = findObject(doc, path, options) if con == nil { - return errors.Wrapf(ErrMissing, "copy operation does not apply: doc is missing destination path: %s", path) + return fmt.Errorf("copy operation does not apply: doc is missing destination path: %s: %w", path, ErrMissing) } valCopy, sz, err := deepCopy(val, options) if err != nil { - return errors.Wrapf(err, "error while performing deep copy") + return fmt.Errorf("error while performing deep copy: %w", err) } (*accumulatedCopySize) += int64(sz) @@ -1163,7 +1163,7 @@ func (p Patch) copy(doc *container, op Operation, accumulatedCopySize *int64, op err = con.add(key, valCopy, options) if err != nil { - return errors.Wrapf(err, "error while adding value during copy") + return fmt.Errorf("error while adding value during copy: %w", err) } return nil diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.cirrus.yml b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.cirrus.yml index ffc7b992b3c..f4e7dbf37b3 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.cirrus.yml +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.cirrus.yml @@ -1,7 +1,7 @@ freebsd_task: name: 'FreeBSD' freebsd_instance: - image_family: freebsd-13-2 + image_family: freebsd-14-1 install_script: - pkg update -f - pkg install -y go @@ -9,5 +9,6 @@ freebsd_task: # run tests as user "cirrus" instead of root - pw useradd cirrus -m - chown -R cirrus:cirrus . - - FSNOTIFY_BUFFER=4096 sudo --preserve-env=FSNOTIFY_BUFFER -u cirrus go test -parallel 1 -race ./... - - sudo --preserve-env=FSNOTIFY_BUFFER -u cirrus go test -parallel 1 -race ./... + - FSNOTIFY_BUFFER=4096 sudo --preserve-env=FSNOTIFY_BUFFER -u cirrus go test -parallel 1 -race ./... + - sudo --preserve-env=FSNOTIFY_BUFFER -u cirrus go test -parallel 1 -race ./... + - FSNOTIFY_DEBUG=1 sudo --preserve-env=FSNOTIFY_BUFFER -u cirrus go test -parallel 1 -race -v ./... diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitattributes b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitattributes deleted file mode 100644 index 32f1001be0a..00000000000 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitattributes +++ /dev/null @@ -1 +0,0 @@ -go.sum linguist-generated diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitignore b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitignore index 391cc076b12..daea9dd6d6d 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitignore +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.gitignore @@ -5,3 +5,6 @@ # Output of go build ./cmd/fsnotify /fsnotify /fsnotify.exe + +/test/kqueue +/test/a.out diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CHANGELOG.md b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CHANGELOG.md index e0e57575496..fa854785d0f 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CHANGELOG.md +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CHANGELOG.md @@ -1,8 +1,36 @@ # Changelog -Unreleased ----------- -Nothing yet. +1.8.0 2023-10-31 +---------------- + +### Additions + +- all: add `FSNOTIFY_DEBUG` to print debug logs to stderr ([#619]) + +### Changes and fixes + +- windows: fix behaviour of `WatchList()` to be consistent with other platforms ([#610]) + +- kqueue: ignore events with Ident=0 ([#590]) + +- kqueue: set O_CLOEXEC to prevent passing file descriptors to children ([#617]) + +- kqueue: emit events as "/path/dir/file" instead of "path/link/file" when watching a symlink ([#625]) + +- inotify: don't send event for IN_DELETE_SELF when also watching the parent ([#620]) + +- inotify: fix panic when calling Remove() in a goroutine ([#650]) + +- fen: allow watching subdirectories of watched directories ([#621]) + +[#590]: https://github.com/fsnotify/fsnotify/pull/590 +[#610]: https://github.com/fsnotify/fsnotify/pull/610 +[#617]: https://github.com/fsnotify/fsnotify/pull/617 +[#619]: https://github.com/fsnotify/fsnotify/pull/619 +[#620]: https://github.com/fsnotify/fsnotify/pull/620 +[#621]: https://github.com/fsnotify/fsnotify/pull/621 +[#625]: https://github.com/fsnotify/fsnotify/pull/625 +[#650]: https://github.com/fsnotify/fsnotify/pull/650 1.7.0 - 2023-10-22 ------------------ diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CONTRIBUTING.md b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CONTRIBUTING.md index ea379759d51..e4ac2a2fffd 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CONTRIBUTING.md +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/CONTRIBUTING.md @@ -1,7 +1,7 @@ Thank you for your interest in contributing to fsnotify! We try to review and merge PRs in a reasonable timeframe, but please be aware that: -- To avoid "wasted" work, please discus changes on the issue tracker first. You +- To avoid "wasted" work, please discuss changes on the issue tracker first. You can just send PRs, but they may end up being rejected for one reason or the other. @@ -20,6 +20,124 @@ platforms. Testing different platforms locally can be done with something like Use the `-short` flag to make the "stress test" run faster. +Writing new tests +----------------- +Scripts in the testdata directory allow creating test cases in a "shell-like" +syntax. The basic format is: + + script + + Output: + desired output + +For example: + + # Create a new empty file with some data. + watch / + echo data >/file + + Output: + create /file + write /file + +Just create a new file to add a new test; select which tests to run with +`-run TestScript/[path]`. + +script +------ +The script is a "shell-like" script: + + cmd arg arg + +Comments are supported with `#`: + + # Comment + cmd arg arg # Comment + +All operations are done in a temp directory; a path like "/foo" is rewritten to +"/tmp/TestFoo/foo". + +Arguments can be quoted with `"` or `'`; there are no escapes and they're +functionally identical right now, but this may change in the future, so best to +assume shell-like rules. + + touch "/file with spaces" + +End-of-line escapes with `\` are not supported. + +### Supported commands + + watch path [ops] # Watch the path, reporting events for it. Nothing is + # watched by default. Optionally a list of ops can be + # given, as with AddWith(path, WithOps(...)). + unwatch path # Stop watching the path. + watchlist n # Assert watchlist length. + + stop # Stop running the script; for debugging. + debug [yes/no] # Enable/disable FSNOTIFY_DEBUG (tests are run in + parallel by default, so -parallel=1 is probably a good + idea). + + touch path + mkdir [-p] dir + ln -s target link # Only ln -s supported. + mkfifo path + mknod dev path + mv src dst + rm [-r] path + chmod mode path # Octal only + sleep time-in-ms + + cat path # Read path (does nothing with the data; just reads it). + echo str >>path # Append "str" to "path". + echo str >path # Truncate "path" and write "str". + + require reason # Skip the test if "reason" is true; "skip" and + skip reason # "require" behave identical; it supports both for + # readability. Possible reasons are: + # + # always Always skip this test. + # symlink Symlinks are supported (requires admin + # permissions on Windows). + # mkfifo Platform doesn't support FIFO named sockets. + # mknod Platform doesn't support device nodes. + + +output +------ +After `Output:` the desired output is given; this is indented by convention, but +that's not required. + +The format of that is: + + # Comment + event path # Comment + + system: + event path + system2: + event path + +Every event is one line, and any whitespace between the event and path are +ignored. The path can optionally be surrounded in ". Anything after a "#" is +ignored. + +Platform-specific tests can be added after GOOS; for example: + + watch / + touch /file + + Output: + # Tested if nothing else matches + create /file + + # Windows-specific test. + windows: + write /file + +You can specify multiple platforms with a comma (e.g. "windows, linux:"). +"kqueue" is a shortcut for all kqueue systems (BSD, macOS). + [goon]: https://github.com/arp242/goon [Vagrant]: https://www.vagrantup.com/ diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_fen.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_fen.go index 28497f1dd8e..c349c326c71 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_fen.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_fen.go @@ -1,8 +1,8 @@ //go:build solaris -// +build solaris -// Note: the documentation on the Watcher type and methods is generated from -// mkdoc.zsh +// FEN backend for illumos (supported) and Solaris (untested, but should work). +// +// See port_create(3c) etc. for docs. https://www.illumos.org/man/3C/port_create package fsnotify @@ -12,150 +12,33 @@ import ( "os" "path/filepath" "sync" + "time" + "github.com/fsnotify/fsnotify/internal" "golang.org/x/sys/unix" ) -// Watcher watches a set of paths, delivering events on a channel. -// -// A watcher should not be copied (e.g. pass it by pointer, rather than by -// value). -// -// # Linux notes -// -// When a file is removed a Remove event won't be emitted until all file -// descriptors are closed, and deletes will always emit a Chmod. For example: -// -// fp := os.Open("file") -// os.Remove("file") // Triggers Chmod -// fp.Close() // Triggers Remove -// -// This is the event that inotify sends, so not much can be changed about this. -// -// The fs.inotify.max_user_watches sysctl variable specifies the upper limit -// for the number of watches per user, and fs.inotify.max_user_instances -// specifies the maximum number of inotify instances per user. Every Watcher you -// create is an "instance", and every path you add is a "watch". -// -// These are also exposed in /proc as /proc/sys/fs/inotify/max_user_watches and -// /proc/sys/fs/inotify/max_user_instances -// -// To increase them you can use sysctl or write the value to the /proc file: -// -// # Default values on Linux 5.18 -// sysctl fs.inotify.max_user_watches=124983 -// sysctl fs.inotify.max_user_instances=128 -// -// To make the changes persist on reboot edit /etc/sysctl.conf or -// /usr/lib/sysctl.d/50-default.conf (details differ per Linux distro; check -// your distro's documentation): -// -// fs.inotify.max_user_watches=124983 -// fs.inotify.max_user_instances=128 -// -// Reaching the limit will result in a "no space left on device" or "too many open -// files" error. -// -// # kqueue notes (macOS, BSD) -// -// kqueue requires opening a file descriptor for every file that's being watched; -// so if you're watching a directory with five files then that's six file -// descriptors. You will run in to your system's "max open files" limit faster on -// these platforms. -// -// The sysctl variables kern.maxfiles and kern.maxfilesperproc can be used to -// control the maximum number of open files, as well as /etc/login.conf on BSD -// systems. -// -// # Windows notes -// -// Paths can be added as "C:\path\to\dir", but forward slashes -// ("C:/path/to/dir") will also work. -// -// When a watched directory is removed it will always send an event for the -// directory itself, but may not send events for all files in that directory. -// Sometimes it will send events for all times, sometimes it will send no -// events, and often only for some files. -// -// The default ReadDirectoryChangesW() buffer size is 64K, which is the largest -// value that is guaranteed to work with SMB filesystems. If you have many -// events in quick succession this may not be enough, and you will have to use -// [WithBufferSize] to increase the value. -type Watcher struct { - // Events sends the filesystem change events. - // - // fsnotify can send the following events; a "path" here can refer to a - // file, directory, symbolic link, or special file like a FIFO. - // - // fsnotify.Create A new path was created; this may be followed by one - // or more Write events if data also gets written to a - // file. - // - // fsnotify.Remove A path was removed. - // - // fsnotify.Rename A path was renamed. A rename is always sent with the - // old path as Event.Name, and a Create event will be - // sent with the new name. Renames are only sent for - // paths that are currently watched; e.g. moving an - // unmonitored file into a monitored directory will - // show up as just a Create. Similarly, renaming a file - // to outside a monitored directory will show up as - // only a Rename. - // - // fsnotify.Write A file or named pipe was written to. A Truncate will - // also trigger a Write. A single "write action" - // initiated by the user may show up as one or multiple - // writes, depending on when the system syncs things to - // disk. For example when compiling a large Go program - // you may get hundreds of Write events, and you may - // want to wait until you've stopped receiving them - // (see the dedup example in cmd/fsnotify). - // - // Some systems may send Write event for directories - // when the directory content changes. - // - // fsnotify.Chmod Attributes were changed. On Linux this is also sent - // when a file is removed (or more accurately, when a - // link to an inode is removed). On kqueue it's sent - // when a file is truncated. On Windows it's never - // sent. +type fen struct { Events chan Event - - // Errors sends any errors. - // - // ErrEventOverflow is used to indicate there are too many events: - // - // - inotify: There are too many queued events (fs.inotify.max_queued_events sysctl) - // - windows: The buffer size is too small; WithBufferSize() can be used to increase it. - // - kqueue, fen: Not used. Errors chan error mu sync.Mutex port *unix.EventPort - done chan struct{} // Channel for sending a "quit message" to the reader goroutine - dirs map[string]struct{} // Explicitly watched directories - watches map[string]struct{} // Explicitly watched non-directories + done chan struct{} // Channel for sending a "quit message" to the reader goroutine + dirs map[string]Op // Explicitly watched directories + watches map[string]Op // Explicitly watched non-directories } -// NewWatcher creates a new Watcher. -func NewWatcher() (*Watcher, error) { - return NewBufferedWatcher(0) +func newBackend(ev chan Event, errs chan error) (backend, error) { + return newBufferedBackend(0, ev, errs) } -// NewBufferedWatcher creates a new Watcher with a buffered Watcher.Events -// channel. -// -// The main use case for this is situations with a very large number of events -// where the kernel buffer size can't be increased (e.g. due to lack of -// permissions). An unbuffered Watcher will perform better for almost all use -// cases, and whenever possible you will be better off increasing the kernel -// buffers instead of adding a large userspace buffer. -func NewBufferedWatcher(sz uint) (*Watcher, error) { - w := &Watcher{ - Events: make(chan Event, sz), - Errors: make(chan error), - dirs: make(map[string]struct{}), - watches: make(map[string]struct{}), +func newBufferedBackend(sz uint, ev chan Event, errs chan error) (backend, error) { + w := &fen{ + Events: ev, + Errors: errs, + dirs: make(map[string]Op), + watches: make(map[string]Op), done: make(chan struct{}), } @@ -171,27 +54,30 @@ func NewBufferedWatcher(sz uint) (*Watcher, error) { // sendEvent attempts to send an event to the user, returning true if the event // was put in the channel successfully and false if the watcher has been closed. -func (w *Watcher) sendEvent(name string, op Op) (sent bool) { +func (w *fen) sendEvent(name string, op Op) (sent bool) { select { - case w.Events <- Event{Name: name, Op: op}: - return true case <-w.done: return false + case w.Events <- Event{Name: name, Op: op}: + return true } } // sendError attempts to send an error to the user, returning true if the error // was put in the channel successfully and false if the watcher has been closed. -func (w *Watcher) sendError(err error) (sent bool) { - select { - case w.Errors <- err: +func (w *fen) sendError(err error) (sent bool) { + if err == nil { return true + } + select { case <-w.done: return false + case w.Errors <- err: + return true } } -func (w *Watcher) isClosed() bool { +func (w *fen) isClosed() bool { select { case <-w.done: return true @@ -200,8 +86,7 @@ func (w *Watcher) isClosed() bool { } } -// Close removes all watches and closes the Events channel. -func (w *Watcher) Close() error { +func (w *fen) Close() error { // Take the lock used by associateFile to prevent lingering events from // being processed after the close w.mu.Lock() @@ -213,60 +98,21 @@ func (w *Watcher) Close() error { return w.port.Close() } -// Add starts monitoring the path for changes. -// -// A path can only be watched once; watching it more than once is a no-op and will -// not return an error. Paths that do not yet exist on the filesystem cannot be -// watched. -// -// A watch will be automatically removed if the watched path is deleted or -// renamed. The exception is the Windows backend, which doesn't remove the -// watcher on renames. -// -// Notifications on network filesystems (NFS, SMB, FUSE, etc.) or special -// filesystems (/proc, /sys, etc.) generally don't work. -// -// Returns [ErrClosed] if [Watcher.Close] was called. -// -// See [Watcher.AddWith] for a version that allows adding options. -// -// # Watching directories -// -// All files in a directory are monitored, including new files that are created -// after the watcher is started. Subdirectories are not watched (i.e. it's -// non-recursive). -// -// # Watching files -// -// Watching individual files (rather than directories) is generally not -// recommended as many programs (especially editors) update files atomically: it -// will write to a temporary file which is then moved to to destination, -// overwriting the original (or some variant thereof). The watcher on the -// original file is now lost, as that no longer exists. -// -// The upshot of this is that a power failure or crash won't leave a -// half-written file. -// -// Watch the parent directory and use Event.Name to filter out files you're not -// interested in. There is an example of this in cmd/fsnotify/file.go. -func (w *Watcher) Add(name string) error { return w.AddWith(name) } +func (w *fen) Add(name string) error { return w.AddWith(name) } -// AddWith is like [Watcher.Add], but allows adding options. When using Add() -// the defaults described below are used. -// -// Possible options are: -// -// - [WithBufferSize] sets the buffer size for the Windows backend; no-op on -// other platforms. The default is 64K (65536 bytes). -func (w *Watcher) AddWith(name string, opts ...addOpt) error { +func (w *fen) AddWith(name string, opts ...addOpt) error { if w.isClosed() { return ErrClosed } - if w.port.PathIsWatched(name) { - return nil + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s AddWith(%q)\n", + time.Now().Format("15:04:05.000000000"), name) } - _ = getOptions(opts...) + with := getOptions(opts...) + if !w.xSupports(with.op) { + return fmt.Errorf("%w: %s", xErrUnsupported, with.op) + } // Currently we resolve symlinks that were explicitly requested to be // watched. Otherwise we would use LStat here. @@ -283,7 +129,7 @@ func (w *Watcher) AddWith(name string, opts ...addOpt) error { } w.mu.Lock() - w.dirs[name] = struct{}{} + w.dirs[name] = with.op w.mu.Unlock() return nil } @@ -294,26 +140,22 @@ func (w *Watcher) AddWith(name string, opts ...addOpt) error { } w.mu.Lock() - w.watches[name] = struct{}{} + w.watches[name] = with.op w.mu.Unlock() return nil } -// Remove stops monitoring the path for changes. -// -// Directories are always removed non-recursively. For example, if you added -// /tmp/dir and /tmp/dir/subdir then you will need to remove both. -// -// Removing a path that has not yet been added returns [ErrNonExistentWatch]. -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) Remove(name string) error { +func (w *fen) Remove(name string) error { if w.isClosed() { return nil } if !w.port.PathIsWatched(name) { return fmt.Errorf("%w: %s", ErrNonExistentWatch, name) } + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s Remove(%q)\n", + time.Now().Format("15:04:05.000000000"), name) + } // The user has expressed an intent. Immediately remove this name from // whichever watch list it might be in. If it's not in there the delete @@ -346,7 +188,7 @@ func (w *Watcher) Remove(name string) error { } // readEvents contains the main loop that runs in a goroutine watching for events. -func (w *Watcher) readEvents() { +func (w *fen) readEvents() { // If this function returns, the watcher has been closed and we can close // these channels defer func() { @@ -382,17 +224,19 @@ func (w *Watcher) readEvents() { continue } + if debug { + internal.Debug(pevent.Path, pevent.Events) + } + err = w.handleEvent(&pevent) - if err != nil { - if !w.sendError(err) { - return - } + if !w.sendError(err) { + return } } } } -func (w *Watcher) handleDirectory(path string, stat os.FileInfo, follow bool, handler func(string, os.FileInfo, bool) error) error { +func (w *fen) handleDirectory(path string, stat os.FileInfo, follow bool, handler func(string, os.FileInfo, bool) error) error { files, err := os.ReadDir(path) if err != nil { return err @@ -418,7 +262,7 @@ func (w *Watcher) handleDirectory(path string, stat os.FileInfo, follow bool, ha // bitmap matches more than one event type (e.g. the file was both modified and // had the attributes changed between when the association was created and the // when event was returned) -func (w *Watcher) handleEvent(event *unix.PortEvent) error { +func (w *fen) handleEvent(event *unix.PortEvent) error { var ( events = event.Events path = event.Path @@ -510,15 +354,9 @@ func (w *Watcher) handleEvent(event *unix.PortEvent) error { } if events&unix.FILE_MODIFIED != 0 { - if fmode.IsDir() { - if watchedDir { - if err := w.updateDirectory(path); err != nil { - return err - } - } else { - if !w.sendEvent(path, Write) { - return nil - } + if fmode.IsDir() && watchedDir { + if err := w.updateDirectory(path); err != nil { + return err } } else { if !w.sendEvent(path, Write) { @@ -543,7 +381,7 @@ func (w *Watcher) handleEvent(event *unix.PortEvent) error { return nil } -func (w *Watcher) updateDirectory(path string) error { +func (w *fen) updateDirectory(path string) error { // The directory was modified, so we must find unwatched entities and watch // them. If something was removed from the directory, nothing will happen, // as everything else should still be watched. @@ -563,10 +401,8 @@ func (w *Watcher) updateDirectory(path string) error { return err } err = w.associateFile(path, finfo, false) - if err != nil { - if !w.sendError(err) { - return nil - } + if !w.sendError(err) { + return nil } if !w.sendEvent(path, Create) { return nil @@ -575,7 +411,7 @@ func (w *Watcher) updateDirectory(path string) error { return nil } -func (w *Watcher) associateFile(path string, stat os.FileInfo, follow bool) error { +func (w *fen) associateFile(path string, stat os.FileInfo, follow bool) error { if w.isClosed() { return ErrClosed } @@ -593,34 +429,34 @@ func (w *Watcher) associateFile(path string, stat os.FileInfo, follow bool) erro // cleared up that discrepancy. The most likely cause is that the event // has fired but we haven't processed it yet. err := w.port.DissociatePath(path) - if err != nil && err != unix.ENOENT { + if err != nil && !errors.Is(err, unix.ENOENT) { return err } } - // FILE_NOFOLLOW means we watch symlinks themselves rather than their - // targets. - events := unix.FILE_MODIFIED | unix.FILE_ATTRIB | unix.FILE_NOFOLLOW - if follow { - // We *DO* follow symlinks for explicitly watched entries. - events = unix.FILE_MODIFIED | unix.FILE_ATTRIB + + var events int + if !follow { + // Watch symlinks themselves rather than their targets unless this entry + // is explicitly watched. + events |= unix.FILE_NOFOLLOW + } + if true { // TODO: implement withOps() + events |= unix.FILE_MODIFIED } - return w.port.AssociatePath(path, stat, - events, - stat.Mode()) + if true { + events |= unix.FILE_ATTRIB + } + return w.port.AssociatePath(path, stat, events, stat.Mode()) } -func (w *Watcher) dissociateFile(path string, stat os.FileInfo, unused bool) error { +func (w *fen) dissociateFile(path string, stat os.FileInfo, unused bool) error { if !w.port.PathIsWatched(path) { return nil } return w.port.DissociatePath(path) } -// WatchList returns all paths explicitly added with [Watcher.Add] (and are not -// yet removed). -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) WatchList() []string { +func (w *fen) WatchList() []string { if w.isClosed() { return nil } @@ -638,3 +474,11 @@ func (w *Watcher) WatchList() []string { return entries } + +func (w *fen) xSupports(op Op) bool { + if op.Has(xUnportableOpen) || op.Has(xUnportableRead) || + op.Has(xUnportableCloseWrite) || op.Has(xUnportableCloseRead) { + return false + } + return true +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_inotify.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_inotify.go index 921c1c1e401..36c311694cd 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_inotify.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_inotify.go @@ -1,8 +1,4 @@ //go:build linux && !appengine -// +build linux,!appengine - -// Note: the documentation on the Watcher type and methods is generated from -// mkdoc.zsh package fsnotify @@ -10,127 +6,20 @@ import ( "errors" "fmt" "io" + "io/fs" "os" "path/filepath" "strings" "sync" + "time" "unsafe" + "github.com/fsnotify/fsnotify/internal" "golang.org/x/sys/unix" ) -// Watcher watches a set of paths, delivering events on a channel. -// -// A watcher should not be copied (e.g. pass it by pointer, rather than by -// value). -// -// # Linux notes -// -// When a file is removed a Remove event won't be emitted until all file -// descriptors are closed, and deletes will always emit a Chmod. For example: -// -// fp := os.Open("file") -// os.Remove("file") // Triggers Chmod -// fp.Close() // Triggers Remove -// -// This is the event that inotify sends, so not much can be changed about this. -// -// The fs.inotify.max_user_watches sysctl variable specifies the upper limit -// for the number of watches per user, and fs.inotify.max_user_instances -// specifies the maximum number of inotify instances per user. Every Watcher you -// create is an "instance", and every path you add is a "watch". -// -// These are also exposed in /proc as /proc/sys/fs/inotify/max_user_watches and -// /proc/sys/fs/inotify/max_user_instances -// -// To increase them you can use sysctl or write the value to the /proc file: -// -// # Default values on Linux 5.18 -// sysctl fs.inotify.max_user_watches=124983 -// sysctl fs.inotify.max_user_instances=128 -// -// To make the changes persist on reboot edit /etc/sysctl.conf or -// /usr/lib/sysctl.d/50-default.conf (details differ per Linux distro; check -// your distro's documentation): -// -// fs.inotify.max_user_watches=124983 -// fs.inotify.max_user_instances=128 -// -// Reaching the limit will result in a "no space left on device" or "too many open -// files" error. -// -// # kqueue notes (macOS, BSD) -// -// kqueue requires opening a file descriptor for every file that's being watched; -// so if you're watching a directory with five files then that's six file -// descriptors. You will run in to your system's "max open files" limit faster on -// these platforms. -// -// The sysctl variables kern.maxfiles and kern.maxfilesperproc can be used to -// control the maximum number of open files, as well as /etc/login.conf on BSD -// systems. -// -// # Windows notes -// -// Paths can be added as "C:\path\to\dir", but forward slashes -// ("C:/path/to/dir") will also work. -// -// When a watched directory is removed it will always send an event for the -// directory itself, but may not send events for all files in that directory. -// Sometimes it will send events for all times, sometimes it will send no -// events, and often only for some files. -// -// The default ReadDirectoryChangesW() buffer size is 64K, which is the largest -// value that is guaranteed to work with SMB filesystems. If you have many -// events in quick succession this may not be enough, and you will have to use -// [WithBufferSize] to increase the value. -type Watcher struct { - // Events sends the filesystem change events. - // - // fsnotify can send the following events; a "path" here can refer to a - // file, directory, symbolic link, or special file like a FIFO. - // - // fsnotify.Create A new path was created; this may be followed by one - // or more Write events if data also gets written to a - // file. - // - // fsnotify.Remove A path was removed. - // - // fsnotify.Rename A path was renamed. A rename is always sent with the - // old path as Event.Name, and a Create event will be - // sent with the new name. Renames are only sent for - // paths that are currently watched; e.g. moving an - // unmonitored file into a monitored directory will - // show up as just a Create. Similarly, renaming a file - // to outside a monitored directory will show up as - // only a Rename. - // - // fsnotify.Write A file or named pipe was written to. A Truncate will - // also trigger a Write. A single "write action" - // initiated by the user may show up as one or multiple - // writes, depending on when the system syncs things to - // disk. For example when compiling a large Go program - // you may get hundreds of Write events, and you may - // want to wait until you've stopped receiving them - // (see the dedup example in cmd/fsnotify). - // - // Some systems may send Write event for directories - // when the directory content changes. - // - // fsnotify.Chmod Attributes were changed. On Linux this is also sent - // when a file is removed (or more accurately, when a - // link to an inode is removed). On kqueue it's sent - // when a file is truncated. On Windows it's never - // sent. +type inotify struct { Events chan Event - - // Errors sends any errors. - // - // ErrEventOverflow is used to indicate there are too many events: - // - // - inotify: There are too many queued events (fs.inotify.max_queued_events sysctl) - // - windows: The buffer size is too small; WithBufferSize() can be used to increase it. - // - kqueue, fen: Not used. Errors chan error // Store fd here as os.File.Read() will no longer return on close after @@ -139,8 +28,26 @@ type Watcher struct { inotifyFile *os.File watches *watches done chan struct{} // Channel for sending a "quit message" to the reader goroutine - closeMu sync.Mutex + doneMu sync.Mutex doneResp chan struct{} // Channel to respond to Close + + // Store rename cookies in an array, with the index wrapping to 0. Almost + // all of the time what we get is a MOVED_FROM to set the cookie and the + // next event inotify sends will be MOVED_TO to read it. However, this is + // not guaranteed – as described in inotify(7) – and we may get other events + // between the two MOVED_* events (including other MOVED_* ones). + // + // A second issue is that moving a file outside the watched directory will + // trigger a MOVED_FROM to set the cookie, but we never see the MOVED_TO to + // read and delete it. So just storing it in a map would slowly leak memory. + // + // Doing it like this gives us a simple fast LRU-cache that won't allocate. + // Ten items should be more than enough for our purpose, and a loop over + // such a short array is faster than a map access anyway (not that it hugely + // matters since we're talking about hundreds of ns at the most, but still). + cookies [10]koekje + cookieIndex uint8 + cookiesMu sync.Mutex } type ( @@ -150,9 +57,14 @@ type ( path map[string]uint32 // pathname → wd } watch struct { - wd uint32 // Watch descriptor (as returned by the inotify_add_watch() syscall) - flags uint32 // inotify flags of this watch (see inotify(7) for the list of valid flags) - path string // Watch path. + wd uint32 // Watch descriptor (as returned by the inotify_add_watch() syscall) + flags uint32 // inotify flags of this watch (see inotify(7) for the list of valid flags) + path string // Watch path. + recurse bool // Recursion with ./...? + } + koekje struct { + cookie uint32 + path string } ) @@ -179,23 +91,45 @@ func (w *watches) add(ww *watch) { func (w *watches) remove(wd uint32) { w.mu.Lock() defer w.mu.Unlock() - delete(w.path, w.wd[wd].path) + watch := w.wd[wd] // Could have had Remove() called. See #616. + if watch == nil { + return + } + delete(w.path, watch.path) delete(w.wd, wd) } -func (w *watches) removePath(path string) (uint32, bool) { +func (w *watches) removePath(path string) ([]uint32, error) { w.mu.Lock() defer w.mu.Unlock() + path, recurse := recursivePath(path) wd, ok := w.path[path] if !ok { - return 0, false + return nil, fmt.Errorf("%w: %s", ErrNonExistentWatch, path) + } + + watch := w.wd[wd] + if recurse && !watch.recurse { + return nil, fmt.Errorf("can't use /... with non-recursive watch %q", path) } delete(w.path, path) delete(w.wd, wd) + if !watch.recurse { + return []uint32{wd}, nil + } - return wd, true + wds := make([]uint32, 0, 8) + wds = append(wds, wd) + for p, rwd := range w.path { + if filepath.HasPrefix(p, path) { + delete(w.path, p) + delete(w.wd, rwd) + wds = append(wds, rwd) + } + } + return wds, nil } func (w *watches) byPath(path string) *watch { @@ -236,20 +170,11 @@ func (w *watches) updatePath(path string, f func(*watch) (*watch, error)) error return nil } -// NewWatcher creates a new Watcher. -func NewWatcher() (*Watcher, error) { - return NewBufferedWatcher(0) +func newBackend(ev chan Event, errs chan error) (backend, error) { + return newBufferedBackend(0, ev, errs) } -// NewBufferedWatcher creates a new Watcher with a buffered Watcher.Events -// channel. -// -// The main use case for this is situations with a very large number of events -// where the kernel buffer size can't be increased (e.g. due to lack of -// permissions). An unbuffered Watcher will perform better for almost all use -// cases, and whenever possible you will be better off increasing the kernel -// buffers instead of adding a large userspace buffer. -func NewBufferedWatcher(sz uint) (*Watcher, error) { +func newBufferedBackend(sz uint, ev chan Event, errs chan error) (backend, error) { // Need to set nonblocking mode for SetDeadline to work, otherwise blocking // I/O operations won't terminate on close. fd, errno := unix.InotifyInit1(unix.IN_CLOEXEC | unix.IN_NONBLOCK) @@ -257,12 +182,12 @@ func NewBufferedWatcher(sz uint) (*Watcher, error) { return nil, errno } - w := &Watcher{ + w := &inotify{ + Events: ev, + Errors: errs, fd: fd, inotifyFile: os.NewFile(uintptr(fd), ""), watches: newWatches(), - Events: make(chan Event, sz), - Errors: make(chan error), done: make(chan struct{}), doneResp: make(chan struct{}), } @@ -272,26 +197,29 @@ func NewBufferedWatcher(sz uint) (*Watcher, error) { } // Returns true if the event was sent, or false if watcher is closed. -func (w *Watcher) sendEvent(e Event) bool { +func (w *inotify) sendEvent(e Event) bool { select { - case w.Events <- e: - return true case <-w.done: return false + case w.Events <- e: + return true } } // Returns true if the error was sent, or false if watcher is closed. -func (w *Watcher) sendError(err error) bool { - select { - case w.Errors <- err: +func (w *inotify) sendError(err error) bool { + if err == nil { return true + } + select { case <-w.done: return false + case w.Errors <- err: + return true } } -func (w *Watcher) isClosed() bool { +func (w *inotify) isClosed() bool { select { case <-w.done: return true @@ -300,15 +228,14 @@ func (w *Watcher) isClosed() bool { } } -// Close removes all watches and closes the Events channel. -func (w *Watcher) Close() error { - w.closeMu.Lock() +func (w *inotify) Close() error { + w.doneMu.Lock() if w.isClosed() { - w.closeMu.Unlock() + w.doneMu.Unlock() return nil } close(w.done) - w.closeMu.Unlock() + w.doneMu.Unlock() // Causes any blocking reads to return with an error, provided the file // still supports deadline operations. @@ -323,78 +250,104 @@ func (w *Watcher) Close() error { return nil } -// Add starts monitoring the path for changes. -// -// A path can only be watched once; watching it more than once is a no-op and will -// not return an error. Paths that do not yet exist on the filesystem cannot be -// watched. -// -// A watch will be automatically removed if the watched path is deleted or -// renamed. The exception is the Windows backend, which doesn't remove the -// watcher on renames. -// -// Notifications on network filesystems (NFS, SMB, FUSE, etc.) or special -// filesystems (/proc, /sys, etc.) generally don't work. -// -// Returns [ErrClosed] if [Watcher.Close] was called. -// -// See [Watcher.AddWith] for a version that allows adding options. -// -// # Watching directories -// -// All files in a directory are monitored, including new files that are created -// after the watcher is started. Subdirectories are not watched (i.e. it's -// non-recursive). -// -// # Watching files -// -// Watching individual files (rather than directories) is generally not -// recommended as many programs (especially editors) update files atomically: it -// will write to a temporary file which is then moved to to destination, -// overwriting the original (or some variant thereof). The watcher on the -// original file is now lost, as that no longer exists. -// -// The upshot of this is that a power failure or crash won't leave a -// half-written file. -// -// Watch the parent directory and use Event.Name to filter out files you're not -// interested in. There is an example of this in cmd/fsnotify/file.go. -func (w *Watcher) Add(name string) error { return w.AddWith(name) } - -// AddWith is like [Watcher.Add], but allows adding options. When using Add() -// the defaults described below are used. -// -// Possible options are: -// -// - [WithBufferSize] sets the buffer size for the Windows backend; no-op on -// other platforms. The default is 64K (65536 bytes). -func (w *Watcher) AddWith(name string, opts ...addOpt) error { +func (w *inotify) Add(name string) error { return w.AddWith(name) } + +func (w *inotify) AddWith(path string, opts ...addOpt) error { if w.isClosed() { return ErrClosed } + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s AddWith(%q)\n", + time.Now().Format("15:04:05.000000000"), path) + } + + with := getOptions(opts...) + if !w.xSupports(with.op) { + return fmt.Errorf("%w: %s", xErrUnsupported, with.op) + } - name = filepath.Clean(name) - _ = getOptions(opts...) + path, recurse := recursivePath(path) + if recurse { + return filepath.WalkDir(path, func(root string, d fs.DirEntry, err error) error { + if err != nil { + return err + } + if !d.IsDir() { + if root == path { + return fmt.Errorf("fsnotify: not a directory: %q", path) + } + return nil + } - var flags uint32 = unix.IN_MOVED_TO | unix.IN_MOVED_FROM | - unix.IN_CREATE | unix.IN_ATTRIB | unix.IN_MODIFY | - unix.IN_MOVE_SELF | unix.IN_DELETE | unix.IN_DELETE_SELF + // Send a Create event when adding new directory from a recursive + // watch; this is for "mkdir -p one/two/three". Usually all those + // directories will be created before we can set up watchers on the + // subdirectories, so only "one" would be sent as a Create event and + // not "one/two" and "one/two/three" (inotifywait -r has the same + // problem). + if with.sendCreate && root != path { + w.sendEvent(Event{Name: root, Op: Create}) + } + + return w.add(root, with, true) + }) + } - return w.watches.updatePath(name, func(existing *watch) (*watch, error) { + return w.add(path, with, false) +} + +func (w *inotify) add(path string, with withOpts, recurse bool) error { + var flags uint32 + if with.noFollow { + flags |= unix.IN_DONT_FOLLOW + } + if with.op.Has(Create) { + flags |= unix.IN_CREATE + } + if with.op.Has(Write) { + flags |= unix.IN_MODIFY + } + if with.op.Has(Remove) { + flags |= unix.IN_DELETE | unix.IN_DELETE_SELF + } + if with.op.Has(Rename) { + flags |= unix.IN_MOVED_TO | unix.IN_MOVED_FROM | unix.IN_MOVE_SELF + } + if with.op.Has(Chmod) { + flags |= unix.IN_ATTRIB + } + if with.op.Has(xUnportableOpen) { + flags |= unix.IN_OPEN + } + if with.op.Has(xUnportableRead) { + flags |= unix.IN_ACCESS + } + if with.op.Has(xUnportableCloseWrite) { + flags |= unix.IN_CLOSE_WRITE + } + if with.op.Has(xUnportableCloseRead) { + flags |= unix.IN_CLOSE_NOWRITE + } + return w.register(path, flags, recurse) +} + +func (w *inotify) register(path string, flags uint32, recurse bool) error { + return w.watches.updatePath(path, func(existing *watch) (*watch, error) { if existing != nil { flags |= existing.flags | unix.IN_MASK_ADD } - wd, err := unix.InotifyAddWatch(w.fd, name, flags) + wd, err := unix.InotifyAddWatch(w.fd, path, flags) if wd == -1 { return nil, err } if existing == nil { return &watch{ - wd: uint32(wd), - path: name, - flags: flags, + wd: uint32(wd), + path: path, + flags: flags, + recurse: recurse, }, nil } @@ -404,49 +357,44 @@ func (w *Watcher) AddWith(name string, opts ...addOpt) error { }) } -// Remove stops monitoring the path for changes. -// -// Directories are always removed non-recursively. For example, if you added -// /tmp/dir and /tmp/dir/subdir then you will need to remove both. -// -// Removing a path that has not yet been added returns [ErrNonExistentWatch]. -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) Remove(name string) error { +func (w *inotify) Remove(name string) error { if w.isClosed() { return nil } + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s Remove(%q)\n", + time.Now().Format("15:04:05.000000000"), name) + } return w.remove(filepath.Clean(name)) } -func (w *Watcher) remove(name string) error { - wd, ok := w.watches.removePath(name) - if !ok { - return fmt.Errorf("%w: %s", ErrNonExistentWatch, name) - } - - success, errno := unix.InotifyRmWatch(w.fd, wd) - if success == -1 { - // TODO: Perhaps it's not helpful to return an error here in every case; - // The only two possible errors are: - // - // - EBADF, which happens when w.fd is not a valid file descriptor - // of any kind. - // - EINVAL, which is when fd is not an inotify descriptor or wd - // is not a valid watch descriptor. Watch descriptors are - // invalidated when they are removed explicitly or implicitly; - // explicitly by inotify_rm_watch, implicitly when the file they - // are watching is deleted. - return errno +func (w *inotify) remove(name string) error { + wds, err := w.watches.removePath(name) + if err != nil { + return err + } + + for _, wd := range wds { + _, err := unix.InotifyRmWatch(w.fd, wd) + if err != nil { + // TODO: Perhaps it's not helpful to return an error here in every + // case; the only two possible errors are: + // + // EBADF, which happens when w.fd is not a valid file descriptor of + // any kind. + // + // EINVAL, which is when fd is not an inotify descriptor or wd is + // not a valid watch descriptor. Watch descriptors are invalidated + // when they are removed explicitly or implicitly; explicitly by + // inotify_rm_watch, implicitly when the file they are watching is + // deleted. + return err + } } return nil } -// WatchList returns all paths explicitly added with [Watcher.Add] (and are not -// yet removed). -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) WatchList() []string { +func (w *inotify) WatchList() []string { if w.isClosed() { return nil } @@ -463,7 +411,7 @@ func (w *Watcher) WatchList() []string { // readEvents reads from the inotify file descriptor, converts the // received events into Event objects and sends them via the Events channel -func (w *Watcher) readEvents() { +func (w *inotify) readEvents() { defer func() { close(w.doneResp) close(w.Errors) @@ -506,15 +454,17 @@ func (w *Watcher) readEvents() { continue } - var offset uint32 // We don't know how many events we just read into the buffer // While the offset points to at least one whole event... + var offset uint32 for offset <= uint32(n-unix.SizeofInotifyEvent) { var ( // Point "raw" to the event in the buffer raw = (*unix.InotifyEvent)(unsafe.Pointer(&buf[offset])) mask = uint32(raw.Mask) nameLen = uint32(raw.Len) + // Move to the next event in the buffer + next = func() { offset += unix.SizeofInotifyEvent + nameLen } ) if mask&unix.IN_Q_OVERFLOW != 0 { @@ -523,21 +473,53 @@ func (w *Watcher) readEvents() { } } - // If the event happened to the watched directory or the watched file, the kernel - // doesn't append the filename to the event, but we would like to always fill the - // the "Name" field with a valid filename. We retrieve the path of the watch from - // the "paths" map. + /// If the event happened to the watched directory or the watched + /// file, the kernel doesn't append the filename to the event, but + /// we would like to always fill the the "Name" field with a valid + /// filename. We retrieve the path of the watch from the "paths" + /// map. watch := w.watches.byWd(uint32(raw.Wd)) + /// Can be nil if Remove() was called in another goroutine for this + /// path inbetween reading the events from the kernel and reading + /// the internal state. Not much we can do about it, so just skip. + /// See #616. + if watch == nil { + next() + continue + } + + name := watch.path + if nameLen > 0 { + /// Point "bytes" at the first byte of the filename + bytes := (*[unix.PathMax]byte)(unsafe.Pointer(&buf[offset+unix.SizeofInotifyEvent]))[:nameLen:nameLen] + /// The filename is padded with NULL bytes. TrimRight() gets rid of those. + name += "/" + strings.TrimRight(string(bytes[0:nameLen]), "\000") + } + + if debug { + internal.Debug(name, raw.Mask, raw.Cookie) + } + + if mask&unix.IN_IGNORED != 0 { //&& event.Op != 0 + next() + continue + } // inotify will automatically remove the watch on deletes; just need // to clean our state here. - if watch != nil && mask&unix.IN_DELETE_SELF == unix.IN_DELETE_SELF { + if mask&unix.IN_DELETE_SELF == unix.IN_DELETE_SELF { w.watches.remove(watch.wd) } + // We can't really update the state when a watched path is moved; // only IN_MOVE_SELF is sent and not IN_MOVED_{FROM,TO}. So remove // the watch. - if watch != nil && mask&unix.IN_MOVE_SELF == unix.IN_MOVE_SELF { + if mask&unix.IN_MOVE_SELF == unix.IN_MOVE_SELF { + if watch.recurse { + next() // Do nothing + continue + } + err := w.remove(watch.path) if err != nil && !errors.Is(err, ErrNonExistentWatch) { if !w.sendError(err) { @@ -546,34 +528,69 @@ func (w *Watcher) readEvents() { } } - var name string - if watch != nil { - name = watch.path - } - if nameLen > 0 { - // Point "bytes" at the first byte of the filename - bytes := (*[unix.PathMax]byte)(unsafe.Pointer(&buf[offset+unix.SizeofInotifyEvent]))[:nameLen:nameLen] - // The filename is padded with NULL bytes. TrimRight() gets rid of those. - name += "/" + strings.TrimRight(string(bytes[0:nameLen]), "\000") + /// Skip if we're watching both this path and the parent; the parent + /// will already send a delete so no need to do it twice. + if mask&unix.IN_DELETE_SELF != 0 { + if _, ok := w.watches.path[filepath.Dir(watch.path)]; ok { + next() + continue + } } - event := w.newEvent(name, mask) + ev := w.newEvent(name, mask, raw.Cookie) + // Need to update watch path for recurse. + if watch.recurse { + isDir := mask&unix.IN_ISDIR == unix.IN_ISDIR + /// New directory created: set up watch on it. + if isDir && ev.Has(Create) { + err := w.register(ev.Name, watch.flags, true) + if !w.sendError(err) { + return + } - // Send the events that are not ignored on the events channel - if mask&unix.IN_IGNORED == 0 { - if !w.sendEvent(event) { - return + // This was a directory rename, so we need to update all + // the children. + // + // TODO: this is of course pretty slow; we should use a + // better data structure for storing all of this, e.g. store + // children in the watch. I have some code for this in my + // kqueue refactor we can use in the future. For now I'm + // okay with this as it's not publicly available. + // Correctness first, performance second. + if ev.renamedFrom != "" { + w.watches.mu.Lock() + for k, ww := range w.watches.wd { + if k == watch.wd || ww.path == ev.Name { + continue + } + if strings.HasPrefix(ww.path, ev.renamedFrom) { + ww.path = strings.Replace(ww.path, ev.renamedFrom, ev.Name, 1) + w.watches.wd[k] = ww + } + } + w.watches.mu.Unlock() + } } } - // Move to the next event in the buffer - offset += unix.SizeofInotifyEvent + nameLen + /// Send the events that are not ignored on the events channel + if !w.sendEvent(ev) { + return + } + next() } } } -// newEvent returns an platform-independent Event based on an inotify mask. -func (w *Watcher) newEvent(name string, mask uint32) Event { +func (w *inotify) isRecursive(path string) bool { + ww := w.watches.byPath(path) + if ww == nil { // path could be a file, so also check the Dir. + ww = w.watches.byPath(filepath.Dir(path)) + } + return ww != nil && ww.recurse +} + +func (w *inotify) newEvent(name string, mask, cookie uint32) Event { e := Event{Name: name} if mask&unix.IN_CREATE == unix.IN_CREATE || mask&unix.IN_MOVED_TO == unix.IN_MOVED_TO { e.Op |= Create @@ -584,11 +601,58 @@ func (w *Watcher) newEvent(name string, mask uint32) Event { if mask&unix.IN_MODIFY == unix.IN_MODIFY { e.Op |= Write } + if mask&unix.IN_OPEN == unix.IN_OPEN { + e.Op |= xUnportableOpen + } + if mask&unix.IN_ACCESS == unix.IN_ACCESS { + e.Op |= xUnportableRead + } + if mask&unix.IN_CLOSE_WRITE == unix.IN_CLOSE_WRITE { + e.Op |= xUnportableCloseWrite + } + if mask&unix.IN_CLOSE_NOWRITE == unix.IN_CLOSE_NOWRITE { + e.Op |= xUnportableCloseRead + } if mask&unix.IN_MOVE_SELF == unix.IN_MOVE_SELF || mask&unix.IN_MOVED_FROM == unix.IN_MOVED_FROM { e.Op |= Rename } if mask&unix.IN_ATTRIB == unix.IN_ATTRIB { e.Op |= Chmod } + + if cookie != 0 { + if mask&unix.IN_MOVED_FROM == unix.IN_MOVED_FROM { + w.cookiesMu.Lock() + w.cookies[w.cookieIndex] = koekje{cookie: cookie, path: e.Name} + w.cookieIndex++ + if w.cookieIndex > 9 { + w.cookieIndex = 0 + } + w.cookiesMu.Unlock() + } else if mask&unix.IN_MOVED_TO == unix.IN_MOVED_TO { + w.cookiesMu.Lock() + var prev string + for _, c := range w.cookies { + if c.cookie == cookie { + prev = c.path + break + } + } + w.cookiesMu.Unlock() + e.renamedFrom = prev + } + } return e } + +func (w *inotify) xSupports(op Op) bool { + return true // Supports everything. +} + +func (w *inotify) state() { + w.watches.mu.Lock() + defer w.watches.mu.Unlock() + for wd, ww := range w.watches.wd { + fmt.Fprintf(os.Stderr, "%4d: recurse=%t %q\n", wd, ww.recurse, ww.path) + } +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_kqueue.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_kqueue.go index 063a0915a07..d8de5ab76fd 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_kqueue.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_kqueue.go @@ -1,8 +1,4 @@ //go:build freebsd || openbsd || netbsd || dragonfly || darwin -// +build freebsd openbsd netbsd dragonfly darwin - -// Note: the documentation on the Watcher type and methods is generated from -// mkdoc.zsh package fsnotify @@ -11,174 +7,195 @@ import ( "fmt" "os" "path/filepath" + "runtime" "sync" + "time" + "github.com/fsnotify/fsnotify/internal" "golang.org/x/sys/unix" ) -// Watcher watches a set of paths, delivering events on a channel. -// -// A watcher should not be copied (e.g. pass it by pointer, rather than by -// value). -// -// # Linux notes -// -// When a file is removed a Remove event won't be emitted until all file -// descriptors are closed, and deletes will always emit a Chmod. For example: -// -// fp := os.Open("file") -// os.Remove("file") // Triggers Chmod -// fp.Close() // Triggers Remove -// -// This is the event that inotify sends, so not much can be changed about this. -// -// The fs.inotify.max_user_watches sysctl variable specifies the upper limit -// for the number of watches per user, and fs.inotify.max_user_instances -// specifies the maximum number of inotify instances per user. Every Watcher you -// create is an "instance", and every path you add is a "watch". -// -// These are also exposed in /proc as /proc/sys/fs/inotify/max_user_watches and -// /proc/sys/fs/inotify/max_user_instances -// -// To increase them you can use sysctl or write the value to the /proc file: -// -// # Default values on Linux 5.18 -// sysctl fs.inotify.max_user_watches=124983 -// sysctl fs.inotify.max_user_instances=128 -// -// To make the changes persist on reboot edit /etc/sysctl.conf or -// /usr/lib/sysctl.d/50-default.conf (details differ per Linux distro; check -// your distro's documentation): -// -// fs.inotify.max_user_watches=124983 -// fs.inotify.max_user_instances=128 -// -// Reaching the limit will result in a "no space left on device" or "too many open -// files" error. -// -// # kqueue notes (macOS, BSD) -// -// kqueue requires opening a file descriptor for every file that's being watched; -// so if you're watching a directory with five files then that's six file -// descriptors. You will run in to your system's "max open files" limit faster on -// these platforms. -// -// The sysctl variables kern.maxfiles and kern.maxfilesperproc can be used to -// control the maximum number of open files, as well as /etc/login.conf on BSD -// systems. -// -// # Windows notes -// -// Paths can be added as "C:\path\to\dir", but forward slashes -// ("C:/path/to/dir") will also work. -// -// When a watched directory is removed it will always send an event for the -// directory itself, but may not send events for all files in that directory. -// Sometimes it will send events for all times, sometimes it will send no -// events, and often only for some files. -// -// The default ReadDirectoryChangesW() buffer size is 64K, which is the largest -// value that is guaranteed to work with SMB filesystems. If you have many -// events in quick succession this may not be enough, and you will have to use -// [WithBufferSize] to increase the value. -type Watcher struct { - // Events sends the filesystem change events. - // - // fsnotify can send the following events; a "path" here can refer to a - // file, directory, symbolic link, or special file like a FIFO. - // - // fsnotify.Create A new path was created; this may be followed by one - // or more Write events if data also gets written to a - // file. - // - // fsnotify.Remove A path was removed. - // - // fsnotify.Rename A path was renamed. A rename is always sent with the - // old path as Event.Name, and a Create event will be - // sent with the new name. Renames are only sent for - // paths that are currently watched; e.g. moving an - // unmonitored file into a monitored directory will - // show up as just a Create. Similarly, renaming a file - // to outside a monitored directory will show up as - // only a Rename. - // - // fsnotify.Write A file or named pipe was written to. A Truncate will - // also trigger a Write. A single "write action" - // initiated by the user may show up as one or multiple - // writes, depending on when the system syncs things to - // disk. For example when compiling a large Go program - // you may get hundreds of Write events, and you may - // want to wait until you've stopped receiving them - // (see the dedup example in cmd/fsnotify). - // - // Some systems may send Write event for directories - // when the directory content changes. - // - // fsnotify.Chmod Attributes were changed. On Linux this is also sent - // when a file is removed (or more accurately, when a - // link to an inode is removed). On kqueue it's sent - // when a file is truncated. On Windows it's never - // sent. +type kqueue struct { Events chan Event - - // Errors sends any errors. - // - // ErrEventOverflow is used to indicate there are too many events: - // - // - inotify: There are too many queued events (fs.inotify.max_queued_events sysctl) - // - windows: The buffer size is too small; WithBufferSize() can be used to increase it. - // - kqueue, fen: Not used. Errors chan error - done chan struct{} - kq int // File descriptor (as returned by the kqueue() syscall). - closepipe [2]int // Pipe used for closing. - mu sync.Mutex // Protects access to watcher data - watches map[string]int // Watched file descriptors (key: path). - watchesByDir map[string]map[int]struct{} // Watched file descriptors indexed by the parent directory (key: dirname(path)). - userWatches map[string]struct{} // Watches added with Watcher.Add() - dirFlags map[string]uint32 // Watched directories to fflags used in kqueue. - paths map[int]pathInfo // File descriptors to path names for processing kqueue events. - fileExists map[string]struct{} // Keep track of if we know this file exists (to stop duplicate create events). - isClosed bool // Set to true when Close() is first called + kq int // File descriptor (as returned by the kqueue() syscall). + closepipe [2]int // Pipe used for closing kq. + watches *watches + done chan struct{} + doneMu sync.Mutex } -type pathInfo struct { - name string - isDir bool +type ( + watches struct { + mu sync.RWMutex + wd map[int]watch // wd → watch + path map[string]int // pathname → wd + byDir map[string]map[int]struct{} // dirname(path) → wd + seen map[string]struct{} // Keep track of if we know this file exists. + byUser map[string]struct{} // Watches added with Watcher.Add() + } + watch struct { + wd int + name string + linkName string // In case of links; name is the target, and this is the link. + isDir bool + dirFlags uint32 + } +) + +func newWatches() *watches { + return &watches{ + wd: make(map[int]watch), + path: make(map[string]int), + byDir: make(map[string]map[int]struct{}), + seen: make(map[string]struct{}), + byUser: make(map[string]struct{}), + } } -// NewWatcher creates a new Watcher. -func NewWatcher() (*Watcher, error) { - return NewBufferedWatcher(0) +func (w *watches) listPaths(userOnly bool) []string { + w.mu.RLock() + defer w.mu.RUnlock() + + if userOnly { + l := make([]string, 0, len(w.byUser)) + for p := range w.byUser { + l = append(l, p) + } + return l + } + + l := make([]string, 0, len(w.path)) + for p := range w.path { + l = append(l, p) + } + return l } -// NewBufferedWatcher creates a new Watcher with a buffered Watcher.Events -// channel. -// -// The main use case for this is situations with a very large number of events -// where the kernel buffer size can't be increased (e.g. due to lack of -// permissions). An unbuffered Watcher will perform better for almost all use -// cases, and whenever possible you will be better off increasing the kernel -// buffers instead of adding a large userspace buffer. -func NewBufferedWatcher(sz uint) (*Watcher, error) { +func (w *watches) watchesInDir(path string) []string { + w.mu.RLock() + defer w.mu.RUnlock() + + l := make([]string, 0, 4) + for fd := range w.byDir[path] { + info := w.wd[fd] + if _, ok := w.byUser[info.name]; !ok { + l = append(l, info.name) + } + } + return l +} + +// Mark path as added by the user. +func (w *watches) addUserWatch(path string) { + w.mu.Lock() + defer w.mu.Unlock() + w.byUser[path] = struct{}{} +} + +func (w *watches) addLink(path string, fd int) { + w.mu.Lock() + defer w.mu.Unlock() + + w.path[path] = fd + w.seen[path] = struct{}{} +} + +func (w *watches) add(path, linkPath string, fd int, isDir bool) { + w.mu.Lock() + defer w.mu.Unlock() + + w.path[path] = fd + w.wd[fd] = watch{wd: fd, name: path, linkName: linkPath, isDir: isDir} + + parent := filepath.Dir(path) + byDir, ok := w.byDir[parent] + if !ok { + byDir = make(map[int]struct{}, 1) + w.byDir[parent] = byDir + } + byDir[fd] = struct{}{} +} + +func (w *watches) byWd(fd int) (watch, bool) { + w.mu.RLock() + defer w.mu.RUnlock() + info, ok := w.wd[fd] + return info, ok +} + +func (w *watches) byPath(path string) (watch, bool) { + w.mu.RLock() + defer w.mu.RUnlock() + info, ok := w.wd[w.path[path]] + return info, ok +} + +func (w *watches) updateDirFlags(path string, flags uint32) { + w.mu.Lock() + defer w.mu.Unlock() + + fd := w.path[path] + info := w.wd[fd] + info.dirFlags = flags + w.wd[fd] = info +} + +func (w *watches) remove(fd int, path string) bool { + w.mu.Lock() + defer w.mu.Unlock() + + isDir := w.wd[fd].isDir + delete(w.path, path) + delete(w.byUser, path) + + parent := filepath.Dir(path) + delete(w.byDir[parent], fd) + + if len(w.byDir[parent]) == 0 { + delete(w.byDir, parent) + } + + delete(w.wd, fd) + delete(w.seen, path) + return isDir +} + +func (w *watches) markSeen(path string, exists bool) { + w.mu.Lock() + defer w.mu.Unlock() + if exists { + w.seen[path] = struct{}{} + } else { + delete(w.seen, path) + } +} + +func (w *watches) seenBefore(path string) bool { + w.mu.RLock() + defer w.mu.RUnlock() + _, ok := w.seen[path] + return ok +} + +func newBackend(ev chan Event, errs chan error) (backend, error) { + return newBufferedBackend(0, ev, errs) +} + +func newBufferedBackend(sz uint, ev chan Event, errs chan error) (backend, error) { kq, closepipe, err := newKqueue() if err != nil { return nil, err } - w := &Watcher{ - kq: kq, - closepipe: closepipe, - watches: make(map[string]int), - watchesByDir: make(map[string]map[int]struct{}), - dirFlags: make(map[string]uint32), - paths: make(map[int]pathInfo), - fileExists: make(map[string]struct{}), - userWatches: make(map[string]struct{}), - Events: make(chan Event, sz), - Errors: make(chan error), - done: make(chan struct{}), + w := &kqueue{ + Events: ev, + Errors: errs, + kq: kq, + closepipe: closepipe, + done: make(chan struct{}), + watches: newWatches(), } go w.readEvents() @@ -203,6 +220,8 @@ func newKqueue() (kq int, closepipe [2]int, err error) { unix.Close(kq) return kq, closepipe, err } + unix.CloseOnExec(closepipe[0]) + unix.CloseOnExec(closepipe[1]) // Register changes to listen on the closepipe. changes := make([]unix.Kevent_t, 1) @@ -221,166 +240,108 @@ func newKqueue() (kq int, closepipe [2]int, err error) { } // Returns true if the event was sent, or false if watcher is closed. -func (w *Watcher) sendEvent(e Event) bool { +func (w *kqueue) sendEvent(e Event) bool { select { - case w.Events <- e: - return true case <-w.done: return false + case w.Events <- e: + return true } } // Returns true if the error was sent, or false if watcher is closed. -func (w *Watcher) sendError(err error) bool { +func (w *kqueue) sendError(err error) bool { + if err == nil { + return true + } select { + case <-w.done: + return false case w.Errors <- err: return true + } +} + +func (w *kqueue) isClosed() bool { + select { case <-w.done: + return true + default: return false } } -// Close removes all watches and closes the Events channel. -func (w *Watcher) Close() error { - w.mu.Lock() - if w.isClosed { - w.mu.Unlock() +func (w *kqueue) Close() error { + w.doneMu.Lock() + if w.isClosed() { + w.doneMu.Unlock() return nil } - w.isClosed = true + close(w.done) + w.doneMu.Unlock() - // copy paths to remove while locked - pathsToRemove := make([]string, 0, len(w.watches)) - for name := range w.watches { - pathsToRemove = append(pathsToRemove, name) - } - w.mu.Unlock() // Unlock before calling Remove, which also locks + pathsToRemove := w.watches.listPaths(false) for _, name := range pathsToRemove { w.Remove(name) } // Send "quit" message to the reader goroutine. unix.Close(w.closepipe[1]) - close(w.done) - return nil } -// Add starts monitoring the path for changes. -// -// A path can only be watched once; watching it more than once is a no-op and will -// not return an error. Paths that do not yet exist on the filesystem cannot be -// watched. -// -// A watch will be automatically removed if the watched path is deleted or -// renamed. The exception is the Windows backend, which doesn't remove the -// watcher on renames. -// -// Notifications on network filesystems (NFS, SMB, FUSE, etc.) or special -// filesystems (/proc, /sys, etc.) generally don't work. -// -// Returns [ErrClosed] if [Watcher.Close] was called. -// -// See [Watcher.AddWith] for a version that allows adding options. -// -// # Watching directories -// -// All files in a directory are monitored, including new files that are created -// after the watcher is started. Subdirectories are not watched (i.e. it's -// non-recursive). -// -// # Watching files -// -// Watching individual files (rather than directories) is generally not -// recommended as many programs (especially editors) update files atomically: it -// will write to a temporary file which is then moved to to destination, -// overwriting the original (or some variant thereof). The watcher on the -// original file is now lost, as that no longer exists. -// -// The upshot of this is that a power failure or crash won't leave a -// half-written file. -// -// Watch the parent directory and use Event.Name to filter out files you're not -// interested in. There is an example of this in cmd/fsnotify/file.go. -func (w *Watcher) Add(name string) error { return w.AddWith(name) } +func (w *kqueue) Add(name string) error { return w.AddWith(name) } -// AddWith is like [Watcher.Add], but allows adding options. When using Add() -// the defaults described below are used. -// -// Possible options are: -// -// - [WithBufferSize] sets the buffer size for the Windows backend; no-op on -// other platforms. The default is 64K (65536 bytes). -func (w *Watcher) AddWith(name string, opts ...addOpt) error { - _ = getOptions(opts...) +func (w *kqueue) AddWith(name string, opts ...addOpt) error { + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s AddWith(%q)\n", + time.Now().Format("15:04:05.000000000"), name) + } + + with := getOptions(opts...) + if !w.xSupports(with.op) { + return fmt.Errorf("%w: %s", xErrUnsupported, with.op) + } - w.mu.Lock() - w.userWatches[name] = struct{}{} - w.mu.Unlock() _, err := w.addWatch(name, noteAllEvents) - return err + if err != nil { + return err + } + w.watches.addUserWatch(name) + return nil } -// Remove stops monitoring the path for changes. -// -// Directories are always removed non-recursively. For example, if you added -// /tmp/dir and /tmp/dir/subdir then you will need to remove both. -// -// Removing a path that has not yet been added returns [ErrNonExistentWatch]. -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) Remove(name string) error { +func (w *kqueue) Remove(name string) error { + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s Remove(%q)\n", + time.Now().Format("15:04:05.000000000"), name) + } return w.remove(name, true) } -func (w *Watcher) remove(name string, unwatchFiles bool) error { - name = filepath.Clean(name) - w.mu.Lock() - if w.isClosed { - w.mu.Unlock() +func (w *kqueue) remove(name string, unwatchFiles bool) error { + if w.isClosed() { return nil } - watchfd, ok := w.watches[name] - w.mu.Unlock() + + name = filepath.Clean(name) + info, ok := w.watches.byPath(name) if !ok { return fmt.Errorf("%w: %s", ErrNonExistentWatch, name) } - err := w.register([]int{watchfd}, unix.EV_DELETE, 0) + err := w.register([]int{info.wd}, unix.EV_DELETE, 0) if err != nil { return err } - unix.Close(watchfd) - - w.mu.Lock() - isDir := w.paths[watchfd].isDir - delete(w.watches, name) - delete(w.userWatches, name) - - parentName := filepath.Dir(name) - delete(w.watchesByDir[parentName], watchfd) - - if len(w.watchesByDir[parentName]) == 0 { - delete(w.watchesByDir, parentName) - } + unix.Close(info.wd) - delete(w.paths, watchfd) - delete(w.dirFlags, name) - delete(w.fileExists, name) - w.mu.Unlock() + isDir := w.watches.remove(info.wd, name) // Find all watched paths that are in this directory that are not external. if unwatchFiles && isDir { - var pathsToRemove []string - w.mu.Lock() - for fd := range w.watchesByDir[name] { - path := w.paths[fd] - if _, ok := w.userWatches[path.name]; !ok { - pathsToRemove = append(pathsToRemove, path.name) - } - } - w.mu.Unlock() + pathsToRemove := w.watches.watchesInDir(name) for _, name := range pathsToRemove { // Since these are internal, not much sense in propagating error to // the user, as that will just confuse them with an error about a @@ -391,23 +352,11 @@ func (w *Watcher) remove(name string, unwatchFiles bool) error { return nil } -// WatchList returns all paths explicitly added with [Watcher.Add] (and are not -// yet removed). -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) WatchList() []string { - w.mu.Lock() - defer w.mu.Unlock() - if w.isClosed { +func (w *kqueue) WatchList() []string { + if w.isClosed() { return nil } - - entries := make([]string, 0, len(w.userWatches)) - for pathname := range w.userWatches { - entries = append(entries, pathname) - } - - return entries + return w.watches.listPaths(true) } // Watch all events (except NOTE_EXTEND, NOTE_LINK, NOTE_REVOKE) @@ -417,34 +366,26 @@ const noteAllEvents = unix.NOTE_DELETE | unix.NOTE_WRITE | unix.NOTE_ATTRIB | un // described in kevent(2). // // Returns the real path to the file which was added, with symlinks resolved. -func (w *Watcher) addWatch(name string, flags uint32) (string, error) { - var isDir bool - name = filepath.Clean(name) - - w.mu.Lock() - if w.isClosed { - w.mu.Unlock() +func (w *kqueue) addWatch(name string, flags uint32) (string, error) { + if w.isClosed() { return "", ErrClosed } - watchfd, alreadyWatching := w.watches[name] - // We already have a watch, but we can still override flags. - if alreadyWatching { - isDir = w.paths[watchfd].isDir - } - w.mu.Unlock() + name = filepath.Clean(name) + + info, alreadyWatching := w.watches.byPath(name) if !alreadyWatching { fi, err := os.Lstat(name) if err != nil { return "", err } - // Don't watch sockets or named pipes + // Don't watch sockets or named pipes. if (fi.Mode()&os.ModeSocket == os.ModeSocket) || (fi.Mode()&os.ModeNamedPipe == os.ModeNamedPipe) { return "", nil } - // Follow Symlinks. + // Follow symlinks. if fi.Mode()&os.ModeSymlink == os.ModeSymlink { link, err := os.Readlink(name) if err != nil { @@ -455,18 +396,15 @@ func (w *Watcher) addWatch(name string, flags uint32) (string, error) { return "", nil } - w.mu.Lock() - _, alreadyWatching = w.watches[link] - w.mu.Unlock() - + _, alreadyWatching = w.watches.byPath(link) if alreadyWatching { // Add to watches so we don't get spurious Create events later // on when we diff the directories. - w.watches[name] = 0 - w.fileExists[name] = struct{}{} + w.watches.addLink(name, 0) return link, nil } + info.linkName = name name = link fi, err = os.Lstat(name) if err != nil { @@ -477,7 +415,7 @@ func (w *Watcher) addWatch(name string, flags uint32) (string, error) { // Retry on EINTR; open() can return EINTR in practice on macOS. // See #354, and Go issues 11180 and 39237. for { - watchfd, err = unix.Open(name, openMode, 0) + info.wd, err = unix.Open(name, openMode, 0) if err == nil { break } @@ -488,40 +426,25 @@ func (w *Watcher) addWatch(name string, flags uint32) (string, error) { return "", err } - isDir = fi.IsDir() + info.isDir = fi.IsDir() } - err := w.register([]int{watchfd}, unix.EV_ADD|unix.EV_CLEAR|unix.EV_ENABLE, flags) + err := w.register([]int{info.wd}, unix.EV_ADD|unix.EV_CLEAR|unix.EV_ENABLE, flags) if err != nil { - unix.Close(watchfd) + unix.Close(info.wd) return "", err } if !alreadyWatching { - w.mu.Lock() - parentName := filepath.Dir(name) - w.watches[name] = watchfd - - watchesByDir, ok := w.watchesByDir[parentName] - if !ok { - watchesByDir = make(map[int]struct{}, 1) - w.watchesByDir[parentName] = watchesByDir - } - watchesByDir[watchfd] = struct{}{} - w.paths[watchfd] = pathInfo{name: name, isDir: isDir} - w.mu.Unlock() + w.watches.add(name, info.linkName, info.wd, info.isDir) } - if isDir { - // Watch the directory if it has not been watched before, or if it was - // watched before, but perhaps only a NOTE_DELETE (watchDirectoryFiles) - w.mu.Lock() - + // Watch the directory if it has not been watched before, or if it was + // watched before, but perhaps only a NOTE_DELETE (watchDirectoryFiles) + if info.isDir { watchDir := (flags&unix.NOTE_WRITE) == unix.NOTE_WRITE && - (!alreadyWatching || (w.dirFlags[name]&unix.NOTE_WRITE) != unix.NOTE_WRITE) - // Store flags so this watch can be updated later - w.dirFlags[name] = flags - w.mu.Unlock() + (!alreadyWatching || (info.dirFlags&unix.NOTE_WRITE) != unix.NOTE_WRITE) + w.watches.updateDirFlags(name, flags) if watchDir { if err := w.watchDirectoryFiles(name); err != nil { @@ -534,7 +457,7 @@ func (w *Watcher) addWatch(name string, flags uint32) (string, error) { // readEvents reads from kqueue and converts the received kevents into // Event values that it sends down the Events channel. -func (w *Watcher) readEvents() { +func (w *kqueue) readEvents() { defer func() { close(w.Events) close(w.Errors) @@ -543,50 +466,65 @@ func (w *Watcher) readEvents() { }() eventBuffer := make([]unix.Kevent_t, 10) - for closed := false; !closed; { + for { kevents, err := w.read(eventBuffer) // EINTR is okay, the syscall was interrupted before timeout expired. if err != nil && err != unix.EINTR { if !w.sendError(fmt.Errorf("fsnotify.readEvents: %w", err)) { - closed = true + return } - continue } - // Flush the events we received to the Events channel for _, kevent := range kevents { var ( - watchfd = int(kevent.Ident) - mask = uint32(kevent.Fflags) + wd = int(kevent.Ident) + mask = uint32(kevent.Fflags) ) // Shut down the loop when the pipe is closed, but only after all // other events have been processed. - if watchfd == w.closepipe[0] { - closed = true - continue + if wd == w.closepipe[0] { + return } - w.mu.Lock() - path := w.paths[watchfd] - w.mu.Unlock() + path, ok := w.watches.byWd(wd) + if debug { + internal.Debug(path.name, &kevent) + } - event := w.newEvent(path.name, mask) + // On macOS it seems that sometimes an event with Ident=0 is + // delivered, and no other flags/information beyond that, even + // though we never saw such a file descriptor. For example in + // TestWatchSymlink/277 (usually at the end, but sometimes sooner): + // + // fmt.Printf("READ: %2d %#v\n", kevent.Ident, kevent) + // unix.Kevent_t{Ident:0x2a, Filter:-4, Flags:0x25, Fflags:0x2, Data:0, Udata:(*uint8)(nil)} + // unix.Kevent_t{Ident:0x0, Filter:-4, Flags:0x25, Fflags:0x2, Data:0, Udata:(*uint8)(nil)} + // + // The first is a normal event, the second with Ident 0. No error + // flag, no data, no ... nothing. + // + // I read a bit through bsd/kern_event.c from the xnu source, but I + // don't really see an obvious location where this is triggered – + // this doesn't seem intentional, but idk... + // + // Technically fd 0 is a valid descriptor, so only skip it if + // there's no path, and if we're on macOS. + if !ok && kevent.Ident == 0 && runtime.GOOS == "darwin" { + continue + } + + event := w.newEvent(path.name, path.linkName, mask) if event.Has(Rename) || event.Has(Remove) { w.remove(event.Name, false) - w.mu.Lock() - delete(w.fileExists, event.Name) - w.mu.Unlock() + w.watches.markSeen(event.Name, false) } if path.isDir && event.Has(Write) && !event.Has(Remove) { - w.sendDirectoryChangeEvents(event.Name) - } else { - if !w.sendEvent(event) { - closed = true - continue - } + w.dirChange(event.Name) + } else if !w.sendEvent(event) { + return } if event.Has(Remove) { @@ -594,25 +532,34 @@ func (w *Watcher) readEvents() { // mv f1 f2 will delete f2, then create f2. if path.isDir { fileDir := filepath.Clean(event.Name) - w.mu.Lock() - _, found := w.watches[fileDir] - w.mu.Unlock() + _, found := w.watches.byPath(fileDir) if found { - err := w.sendDirectoryChangeEvents(fileDir) - if err != nil { - if !w.sendError(err) { - closed = true - } + // TODO: this branch is never triggered in any test. + // Added in d6220df (2012). + // isDir check added in 8611c35 (2016): https://github.com/fsnotify/fsnotify/pull/111 + // + // I don't really get how this can be triggered either. + // And it wasn't triggered in the patch that added it, + // either. + // + // Original also had a comment: + // make sure the directory exists before we watch for + // changes. When we do a recursive watch and perform + // rm -rf, the parent directory might have gone + // missing, ignore the missing directory and let the + // upcoming delete event remove the watch from the + // parent directory. + err := w.dirChange(fileDir) + if !w.sendError(err) { + return } } } else { - filePath := filepath.Clean(event.Name) - if fi, err := os.Lstat(filePath); err == nil { - err := w.sendFileCreatedEventIfNew(filePath, fi) - if err != nil { - if !w.sendError(err) { - closed = true - } + path := filepath.Clean(event.Name) + if fi, err := os.Lstat(path); err == nil { + err := w.sendCreateIfNew(path, fi) + if !w.sendError(err) { + return } } } @@ -622,8 +569,14 @@ func (w *Watcher) readEvents() { } // newEvent returns an platform-independent Event based on kqueue Fflags. -func (w *Watcher) newEvent(name string, mask uint32) Event { +func (w *kqueue) newEvent(name, linkName string, mask uint32) Event { e := Event{Name: name} + if linkName != "" { + // If the user watched "/path/link" then emit events as "/path/link" + // rather than "/path/target". + e.Name = linkName + } + if mask&unix.NOTE_DELETE == unix.NOTE_DELETE { e.Op |= Remove } @@ -645,8 +598,7 @@ func (w *Watcher) newEvent(name string, mask uint32) Event { } // watchDirectoryFiles to mimic inotify when adding a watch on a directory -func (w *Watcher) watchDirectoryFiles(dirPath string) error { - // Get all files +func (w *kqueue) watchDirectoryFiles(dirPath string) error { files, err := os.ReadDir(dirPath) if err != nil { return err @@ -674,9 +626,7 @@ func (w *Watcher) watchDirectoryFiles(dirPath string) error { } } - w.mu.Lock() - w.fileExists[cleanPath] = struct{}{} - w.mu.Unlock() + w.watches.markSeen(cleanPath, true) } return nil @@ -686,7 +636,7 @@ func (w *Watcher) watchDirectoryFiles(dirPath string) error { // // This functionality is to have the BSD watcher match the inotify, which sends // a create event for files created in a watched directory. -func (w *Watcher) sendDirectoryChangeEvents(dir string) error { +func (w *kqueue) dirChange(dir string) error { files, err := os.ReadDir(dir) if err != nil { // Directory no longer exists: we can ignore this safely. kqueue will @@ -694,61 +644,51 @@ func (w *Watcher) sendDirectoryChangeEvents(dir string) error { if errors.Is(err, os.ErrNotExist) { return nil } - return fmt.Errorf("fsnotify.sendDirectoryChangeEvents: %w", err) + return fmt.Errorf("fsnotify.dirChange: %w", err) } for _, f := range files { fi, err := f.Info() if err != nil { - return fmt.Errorf("fsnotify.sendDirectoryChangeEvents: %w", err) + return fmt.Errorf("fsnotify.dirChange: %w", err) } - err = w.sendFileCreatedEventIfNew(filepath.Join(dir, fi.Name()), fi) + err = w.sendCreateIfNew(filepath.Join(dir, fi.Name()), fi) if err != nil { // Don't need to send an error if this file isn't readable. if errors.Is(err, unix.EACCES) || errors.Is(err, unix.EPERM) { return nil } - return fmt.Errorf("fsnotify.sendDirectoryChangeEvents: %w", err) + return fmt.Errorf("fsnotify.dirChange: %w", err) } } return nil } -// sendFileCreatedEvent sends a create event if the file isn't already being tracked. -func (w *Watcher) sendFileCreatedEventIfNew(filePath string, fi os.FileInfo) (err error) { - w.mu.Lock() - _, doesExist := w.fileExists[filePath] - w.mu.Unlock() - if !doesExist { - if !w.sendEvent(Event{Name: filePath, Op: Create}) { - return +// Send a create event if the file isn't already being tracked, and start +// watching this file. +func (w *kqueue) sendCreateIfNew(path string, fi os.FileInfo) error { + if !w.watches.seenBefore(path) { + if !w.sendEvent(Event{Name: path, Op: Create}) { + return nil } } - // like watchDirectoryFiles (but without doing another ReadDir) - filePath, err = w.internalWatch(filePath, fi) + // Like watchDirectoryFiles, but without doing another ReadDir. + path, err := w.internalWatch(path, fi) if err != nil { return err } - - w.mu.Lock() - w.fileExists[filePath] = struct{}{} - w.mu.Unlock() - + w.watches.markSeen(path, true) return nil } -func (w *Watcher) internalWatch(name string, fi os.FileInfo) (string, error) { +func (w *kqueue) internalWatch(name string, fi os.FileInfo) (string, error) { if fi.IsDir() { // mimic Linux providing delete events for subdirectories, but preserve // the flags used if currently watching subdirectory - w.mu.Lock() - flags := w.dirFlags[name] - w.mu.Unlock() - - flags |= unix.NOTE_DELETE | unix.NOTE_RENAME - return w.addWatch(name, flags) + info, _ := w.watches.byPath(name) + return w.addWatch(name, info.dirFlags|unix.NOTE_DELETE|unix.NOTE_RENAME) } // watch file to mimic Linux inotify @@ -756,7 +696,7 @@ func (w *Watcher) internalWatch(name string, fi os.FileInfo) (string, error) { } // Register events with the queue. -func (w *Watcher) register(fds []int, flags int, fflags uint32) error { +func (w *kqueue) register(fds []int, flags int, fflags uint32) error { changes := make([]unix.Kevent_t, len(fds)) for i, fd := range fds { // SetKevent converts int to the platform-specific types. @@ -773,10 +713,21 @@ func (w *Watcher) register(fds []int, flags int, fflags uint32) error { } // read retrieves pending events, or waits until an event occurs. -func (w *Watcher) read(events []unix.Kevent_t) ([]unix.Kevent_t, error) { +func (w *kqueue) read(events []unix.Kevent_t) ([]unix.Kevent_t, error) { n, err := unix.Kevent(w.kq, nil, events, nil) if err != nil { return nil, err } return events[0:n], nil } + +func (w *kqueue) xSupports(op Op) bool { + if runtime.GOOS == "freebsd" { + //return true // Supports everything. + } + if op.Has(xUnportableOpen) || op.Has(xUnportableRead) || + op.Has(xUnportableCloseWrite) || op.Has(xUnportableCloseRead) { + return false + } + return true +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_other.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_other.go index d34a23c015f..5eb5dbc66f2 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_other.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_other.go @@ -1,205 +1,23 @@ //go:build appengine || (!darwin && !dragonfly && !freebsd && !openbsd && !linux && !netbsd && !solaris && !windows) -// +build appengine !darwin,!dragonfly,!freebsd,!openbsd,!linux,!netbsd,!solaris,!windows - -// Note: the documentation on the Watcher type and methods is generated from -// mkdoc.zsh package fsnotify import "errors" -// Watcher watches a set of paths, delivering events on a channel. -// -// A watcher should not be copied (e.g. pass it by pointer, rather than by -// value). -// -// # Linux notes -// -// When a file is removed a Remove event won't be emitted until all file -// descriptors are closed, and deletes will always emit a Chmod. For example: -// -// fp := os.Open("file") -// os.Remove("file") // Triggers Chmod -// fp.Close() // Triggers Remove -// -// This is the event that inotify sends, so not much can be changed about this. -// -// The fs.inotify.max_user_watches sysctl variable specifies the upper limit -// for the number of watches per user, and fs.inotify.max_user_instances -// specifies the maximum number of inotify instances per user. Every Watcher you -// create is an "instance", and every path you add is a "watch". -// -// These are also exposed in /proc as /proc/sys/fs/inotify/max_user_watches and -// /proc/sys/fs/inotify/max_user_instances -// -// To increase them you can use sysctl or write the value to the /proc file: -// -// # Default values on Linux 5.18 -// sysctl fs.inotify.max_user_watches=124983 -// sysctl fs.inotify.max_user_instances=128 -// -// To make the changes persist on reboot edit /etc/sysctl.conf or -// /usr/lib/sysctl.d/50-default.conf (details differ per Linux distro; check -// your distro's documentation): -// -// fs.inotify.max_user_watches=124983 -// fs.inotify.max_user_instances=128 -// -// Reaching the limit will result in a "no space left on device" or "too many open -// files" error. -// -// # kqueue notes (macOS, BSD) -// -// kqueue requires opening a file descriptor for every file that's being watched; -// so if you're watching a directory with five files then that's six file -// descriptors. You will run in to your system's "max open files" limit faster on -// these platforms. -// -// The sysctl variables kern.maxfiles and kern.maxfilesperproc can be used to -// control the maximum number of open files, as well as /etc/login.conf on BSD -// systems. -// -// # Windows notes -// -// Paths can be added as "C:\path\to\dir", but forward slashes -// ("C:/path/to/dir") will also work. -// -// When a watched directory is removed it will always send an event for the -// directory itself, but may not send events for all files in that directory. -// Sometimes it will send events for all times, sometimes it will send no -// events, and often only for some files. -// -// The default ReadDirectoryChangesW() buffer size is 64K, which is the largest -// value that is guaranteed to work with SMB filesystems. If you have many -// events in quick succession this may not be enough, and you will have to use -// [WithBufferSize] to increase the value. -type Watcher struct { - // Events sends the filesystem change events. - // - // fsnotify can send the following events; a "path" here can refer to a - // file, directory, symbolic link, or special file like a FIFO. - // - // fsnotify.Create A new path was created; this may be followed by one - // or more Write events if data also gets written to a - // file. - // - // fsnotify.Remove A path was removed. - // - // fsnotify.Rename A path was renamed. A rename is always sent with the - // old path as Event.Name, and a Create event will be - // sent with the new name. Renames are only sent for - // paths that are currently watched; e.g. moving an - // unmonitored file into a monitored directory will - // show up as just a Create. Similarly, renaming a file - // to outside a monitored directory will show up as - // only a Rename. - // - // fsnotify.Write A file or named pipe was written to. A Truncate will - // also trigger a Write. A single "write action" - // initiated by the user may show up as one or multiple - // writes, depending on when the system syncs things to - // disk. For example when compiling a large Go program - // you may get hundreds of Write events, and you may - // want to wait until you've stopped receiving them - // (see the dedup example in cmd/fsnotify). - // - // Some systems may send Write event for directories - // when the directory content changes. - // - // fsnotify.Chmod Attributes were changed. On Linux this is also sent - // when a file is removed (or more accurately, when a - // link to an inode is removed). On kqueue it's sent - // when a file is truncated. On Windows it's never - // sent. +type other struct { Events chan Event - - // Errors sends any errors. - // - // ErrEventOverflow is used to indicate there are too many events: - // - // - inotify: There are too many queued events (fs.inotify.max_queued_events sysctl) - // - windows: The buffer size is too small; WithBufferSize() can be used to increase it. - // - kqueue, fen: Not used. Errors chan error } -// NewWatcher creates a new Watcher. -func NewWatcher() (*Watcher, error) { +func newBackend(ev chan Event, errs chan error) (backend, error) { return nil, errors.New("fsnotify not supported on the current platform") } - -// NewBufferedWatcher creates a new Watcher with a buffered Watcher.Events -// channel. -// -// The main use case for this is situations with a very large number of events -// where the kernel buffer size can't be increased (e.g. due to lack of -// permissions). An unbuffered Watcher will perform better for almost all use -// cases, and whenever possible you will be better off increasing the kernel -// buffers instead of adding a large userspace buffer. -func NewBufferedWatcher(sz uint) (*Watcher, error) { return NewWatcher() } - -// Close removes all watches and closes the Events channel. -func (w *Watcher) Close() error { return nil } - -// WatchList returns all paths explicitly added with [Watcher.Add] (and are not -// yet removed). -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) WatchList() []string { return nil } - -// Add starts monitoring the path for changes. -// -// A path can only be watched once; watching it more than once is a no-op and will -// not return an error. Paths that do not yet exist on the filesystem cannot be -// watched. -// -// A watch will be automatically removed if the watched path is deleted or -// renamed. The exception is the Windows backend, which doesn't remove the -// watcher on renames. -// -// Notifications on network filesystems (NFS, SMB, FUSE, etc.) or special -// filesystems (/proc, /sys, etc.) generally don't work. -// -// Returns [ErrClosed] if [Watcher.Close] was called. -// -// See [Watcher.AddWith] for a version that allows adding options. -// -// # Watching directories -// -// All files in a directory are monitored, including new files that are created -// after the watcher is started. Subdirectories are not watched (i.e. it's -// non-recursive). -// -// # Watching files -// -// Watching individual files (rather than directories) is generally not -// recommended as many programs (especially editors) update files atomically: it -// will write to a temporary file which is then moved to to destination, -// overwriting the original (or some variant thereof). The watcher on the -// original file is now lost, as that no longer exists. -// -// The upshot of this is that a power failure or crash won't leave a -// half-written file. -// -// Watch the parent directory and use Event.Name to filter out files you're not -// interested in. There is an example of this in cmd/fsnotify/file.go. -func (w *Watcher) Add(name string) error { return nil } - -// AddWith is like [Watcher.Add], but allows adding options. When using Add() -// the defaults described below are used. -// -// Possible options are: -// -// - [WithBufferSize] sets the buffer size for the Windows backend; no-op on -// other platforms. The default is 64K (65536 bytes). -func (w *Watcher) AddWith(name string, opts ...addOpt) error { return nil } - -// Remove stops monitoring the path for changes. -// -// Directories are always removed non-recursively. For example, if you added -// /tmp/dir and /tmp/dir/subdir then you will need to remove both. -// -// Removing a path that has not yet been added returns [ErrNonExistentWatch]. -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) Remove(name string) error { return nil } +func newBufferedBackend(sz uint, ev chan Event, errs chan error) (backend, error) { + return newBackend(ev, errs) +} +func (w *other) Close() error { return nil } +func (w *other) WatchList() []string { return nil } +func (w *other) Add(name string) error { return nil } +func (w *other) AddWith(name string, opts ...addOpt) error { return nil } +func (w *other) Remove(name string) error { return nil } +func (w *other) xSupports(op Op) bool { return false } diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_windows.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_windows.go index 9bc91e5d613..c54a6308383 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_windows.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/backend_windows.go @@ -1,12 +1,8 @@ //go:build windows -// +build windows // Windows backend based on ReadDirectoryChangesW() // // https://learn.microsoft.com/en-us/windows/win32/api/winbase/nf-winbase-readdirectorychangesw -// -// Note: the documentation on the Watcher type and methods is generated from -// mkdoc.zsh package fsnotify @@ -19,123 +15,15 @@ import ( "runtime" "strings" "sync" + "time" "unsafe" + "github.com/fsnotify/fsnotify/internal" "golang.org/x/sys/windows" ) -// Watcher watches a set of paths, delivering events on a channel. -// -// A watcher should not be copied (e.g. pass it by pointer, rather than by -// value). -// -// # Linux notes -// -// When a file is removed a Remove event won't be emitted until all file -// descriptors are closed, and deletes will always emit a Chmod. For example: -// -// fp := os.Open("file") -// os.Remove("file") // Triggers Chmod -// fp.Close() // Triggers Remove -// -// This is the event that inotify sends, so not much can be changed about this. -// -// The fs.inotify.max_user_watches sysctl variable specifies the upper limit -// for the number of watches per user, and fs.inotify.max_user_instances -// specifies the maximum number of inotify instances per user. Every Watcher you -// create is an "instance", and every path you add is a "watch". -// -// These are also exposed in /proc as /proc/sys/fs/inotify/max_user_watches and -// /proc/sys/fs/inotify/max_user_instances -// -// To increase them you can use sysctl or write the value to the /proc file: -// -// # Default values on Linux 5.18 -// sysctl fs.inotify.max_user_watches=124983 -// sysctl fs.inotify.max_user_instances=128 -// -// To make the changes persist on reboot edit /etc/sysctl.conf or -// /usr/lib/sysctl.d/50-default.conf (details differ per Linux distro; check -// your distro's documentation): -// -// fs.inotify.max_user_watches=124983 -// fs.inotify.max_user_instances=128 -// -// Reaching the limit will result in a "no space left on device" or "too many open -// files" error. -// -// # kqueue notes (macOS, BSD) -// -// kqueue requires opening a file descriptor for every file that's being watched; -// so if you're watching a directory with five files then that's six file -// descriptors. You will run in to your system's "max open files" limit faster on -// these platforms. -// -// The sysctl variables kern.maxfiles and kern.maxfilesperproc can be used to -// control the maximum number of open files, as well as /etc/login.conf on BSD -// systems. -// -// # Windows notes -// -// Paths can be added as "C:\path\to\dir", but forward slashes -// ("C:/path/to/dir") will also work. -// -// When a watched directory is removed it will always send an event for the -// directory itself, but may not send events for all files in that directory. -// Sometimes it will send events for all times, sometimes it will send no -// events, and often only for some files. -// -// The default ReadDirectoryChangesW() buffer size is 64K, which is the largest -// value that is guaranteed to work with SMB filesystems. If you have many -// events in quick succession this may not be enough, and you will have to use -// [WithBufferSize] to increase the value. -type Watcher struct { - // Events sends the filesystem change events. - // - // fsnotify can send the following events; a "path" here can refer to a - // file, directory, symbolic link, or special file like a FIFO. - // - // fsnotify.Create A new path was created; this may be followed by one - // or more Write events if data also gets written to a - // file. - // - // fsnotify.Remove A path was removed. - // - // fsnotify.Rename A path was renamed. A rename is always sent with the - // old path as Event.Name, and a Create event will be - // sent with the new name. Renames are only sent for - // paths that are currently watched; e.g. moving an - // unmonitored file into a monitored directory will - // show up as just a Create. Similarly, renaming a file - // to outside a monitored directory will show up as - // only a Rename. - // - // fsnotify.Write A file or named pipe was written to. A Truncate will - // also trigger a Write. A single "write action" - // initiated by the user may show up as one or multiple - // writes, depending on when the system syncs things to - // disk. For example when compiling a large Go program - // you may get hundreds of Write events, and you may - // want to wait until you've stopped receiving them - // (see the dedup example in cmd/fsnotify). - // - // Some systems may send Write event for directories - // when the directory content changes. - // - // fsnotify.Chmod Attributes were changed. On Linux this is also sent - // when a file is removed (or more accurately, when a - // link to an inode is removed). On kqueue it's sent - // when a file is truncated. On Windows it's never - // sent. +type readDirChangesW struct { Events chan Event - - // Errors sends any errors. - // - // ErrEventOverflow is used to indicate there are too many events: - // - // - inotify: There are too many queued events (fs.inotify.max_queued_events sysctl) - // - windows: The buffer size is too small; WithBufferSize() can be used to increase it. - // - kqueue, fen: Not used. Errors chan error port windows.Handle // Handle to completion port @@ -147,48 +35,40 @@ type Watcher struct { closed bool // Set to true when Close() is first called } -// NewWatcher creates a new Watcher. -func NewWatcher() (*Watcher, error) { - return NewBufferedWatcher(50) +func newBackend(ev chan Event, errs chan error) (backend, error) { + return newBufferedBackend(50, ev, errs) } -// NewBufferedWatcher creates a new Watcher with a buffered Watcher.Events -// channel. -// -// The main use case for this is situations with a very large number of events -// where the kernel buffer size can't be increased (e.g. due to lack of -// permissions). An unbuffered Watcher will perform better for almost all use -// cases, and whenever possible you will be better off increasing the kernel -// buffers instead of adding a large userspace buffer. -func NewBufferedWatcher(sz uint) (*Watcher, error) { +func newBufferedBackend(sz uint, ev chan Event, errs chan error) (backend, error) { port, err := windows.CreateIoCompletionPort(windows.InvalidHandle, 0, 0, 0) if err != nil { return nil, os.NewSyscallError("CreateIoCompletionPort", err) } - w := &Watcher{ + w := &readDirChangesW{ + Events: ev, + Errors: errs, port: port, watches: make(watchMap), input: make(chan *input, 1), - Events: make(chan Event, sz), - Errors: make(chan error), quit: make(chan chan<- error, 1), } go w.readEvents() return w, nil } -func (w *Watcher) isClosed() bool { +func (w *readDirChangesW) isClosed() bool { w.mu.Lock() defer w.mu.Unlock() return w.closed } -func (w *Watcher) sendEvent(name string, mask uint64) bool { +func (w *readDirChangesW) sendEvent(name, renamedFrom string, mask uint64) bool { if mask == 0 { return false } event := w.newEvent(name, uint32(mask)) + event.renamedFrom = renamedFrom select { case ch := <-w.quit: w.quit <- ch @@ -198,17 +78,19 @@ func (w *Watcher) sendEvent(name string, mask uint64) bool { } // Returns true if the error was sent, or false if watcher is closed. -func (w *Watcher) sendError(err error) bool { +func (w *readDirChangesW) sendError(err error) bool { + if err == nil { + return true + } select { case w.Errors <- err: return true case <-w.quit: + return false } - return false } -// Close removes all watches and closes the Events channel. -func (w *Watcher) Close() error { +func (w *readDirChangesW) Close() error { if w.isClosed() { return nil } @@ -226,57 +108,21 @@ func (w *Watcher) Close() error { return <-ch } -// Add starts monitoring the path for changes. -// -// A path can only be watched once; watching it more than once is a no-op and will -// not return an error. Paths that do not yet exist on the filesystem cannot be -// watched. -// -// A watch will be automatically removed if the watched path is deleted or -// renamed. The exception is the Windows backend, which doesn't remove the -// watcher on renames. -// -// Notifications on network filesystems (NFS, SMB, FUSE, etc.) or special -// filesystems (/proc, /sys, etc.) generally don't work. -// -// Returns [ErrClosed] if [Watcher.Close] was called. -// -// See [Watcher.AddWith] for a version that allows adding options. -// -// # Watching directories -// -// All files in a directory are monitored, including new files that are created -// after the watcher is started. Subdirectories are not watched (i.e. it's -// non-recursive). -// -// # Watching files -// -// Watching individual files (rather than directories) is generally not -// recommended as many programs (especially editors) update files atomically: it -// will write to a temporary file which is then moved to to destination, -// overwriting the original (or some variant thereof). The watcher on the -// original file is now lost, as that no longer exists. -// -// The upshot of this is that a power failure or crash won't leave a -// half-written file. -// -// Watch the parent directory and use Event.Name to filter out files you're not -// interested in. There is an example of this in cmd/fsnotify/file.go. -func (w *Watcher) Add(name string) error { return w.AddWith(name) } +func (w *readDirChangesW) Add(name string) error { return w.AddWith(name) } -// AddWith is like [Watcher.Add], but allows adding options. When using Add() -// the defaults described below are used. -// -// Possible options are: -// -// - [WithBufferSize] sets the buffer size for the Windows backend; no-op on -// other platforms. The default is 64K (65536 bytes). -func (w *Watcher) AddWith(name string, opts ...addOpt) error { +func (w *readDirChangesW) AddWith(name string, opts ...addOpt) error { if w.isClosed() { return ErrClosed } + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s AddWith(%q)\n", + time.Now().Format("15:04:05.000000000"), filepath.ToSlash(name)) + } with := getOptions(opts...) + if !w.xSupports(with.op) { + return fmt.Errorf("%w: %s", xErrUnsupported, with.op) + } if with.bufsize < 4096 { return fmt.Errorf("fsnotify.WithBufferSize: buffer size cannot be smaller than 4096 bytes") } @@ -295,18 +141,14 @@ func (w *Watcher) AddWith(name string, opts ...addOpt) error { return <-in.reply } -// Remove stops monitoring the path for changes. -// -// Directories are always removed non-recursively. For example, if you added -// /tmp/dir and /tmp/dir/subdir then you will need to remove both. -// -// Removing a path that has not yet been added returns [ErrNonExistentWatch]. -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) Remove(name string) error { +func (w *readDirChangesW) Remove(name string) error { if w.isClosed() { return nil } + if debug { + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s Remove(%q)\n", + time.Now().Format("15:04:05.000000000"), filepath.ToSlash(name)) + } in := &input{ op: opRemoveWatch, @@ -320,11 +162,7 @@ func (w *Watcher) Remove(name string) error { return <-in.reply } -// WatchList returns all paths explicitly added with [Watcher.Add] (and are not -// yet removed). -// -// Returns nil if [Watcher.Close] was called. -func (w *Watcher) WatchList() []string { +func (w *readDirChangesW) WatchList() []string { if w.isClosed() { return nil } @@ -335,7 +173,13 @@ func (w *Watcher) WatchList() []string { entries := make([]string, 0, len(w.watches)) for _, entry := range w.watches { for _, watchEntry := range entry { - entries = append(entries, watchEntry.path) + for name := range watchEntry.names { + entries = append(entries, filepath.Join(watchEntry.path, name)) + } + // the directory itself is being watched + if watchEntry.mask != 0 { + entries = append(entries, watchEntry.path) + } } } @@ -361,7 +205,7 @@ const ( sysFSIGNORED = 0x8000 ) -func (w *Watcher) newEvent(name string, mask uint32) Event { +func (w *readDirChangesW) newEvent(name string, mask uint32) Event { e := Event{Name: name} if mask&sysFSCREATE == sysFSCREATE || mask&sysFSMOVEDTO == sysFSMOVEDTO { e.Op |= Create @@ -417,7 +261,7 @@ type ( watchMap map[uint32]indexMap ) -func (w *Watcher) wakeupReader() error { +func (w *readDirChangesW) wakeupReader() error { err := windows.PostQueuedCompletionStatus(w.port, 0, 0, nil) if err != nil { return os.NewSyscallError("PostQueuedCompletionStatus", err) @@ -425,7 +269,7 @@ func (w *Watcher) wakeupReader() error { return nil } -func (w *Watcher) getDir(pathname string) (dir string, err error) { +func (w *readDirChangesW) getDir(pathname string) (dir string, err error) { attr, err := windows.GetFileAttributes(windows.StringToUTF16Ptr(pathname)) if err != nil { return "", os.NewSyscallError("GetFileAttributes", err) @@ -439,7 +283,7 @@ func (w *Watcher) getDir(pathname string) (dir string, err error) { return } -func (w *Watcher) getIno(path string) (ino *inode, err error) { +func (w *readDirChangesW) getIno(path string) (ino *inode, err error) { h, err := windows.CreateFile(windows.StringToUTF16Ptr(path), windows.FILE_LIST_DIRECTORY, windows.FILE_SHARE_READ|windows.FILE_SHARE_WRITE|windows.FILE_SHARE_DELETE, @@ -482,9 +326,8 @@ func (m watchMap) set(ino *inode, watch *watch) { } // Must run within the I/O thread. -func (w *Watcher) addWatch(pathname string, flags uint64, bufsize int) error { - //pathname, recurse := recursivePath(pathname) - recurse := false +func (w *readDirChangesW) addWatch(pathname string, flags uint64, bufsize int) error { + pathname, recurse := recursivePath(pathname) dir, err := w.getDir(pathname) if err != nil { @@ -538,7 +381,7 @@ func (w *Watcher) addWatch(pathname string, flags uint64, bufsize int) error { } // Must run within the I/O thread. -func (w *Watcher) remWatch(pathname string) error { +func (w *readDirChangesW) remWatch(pathname string) error { pathname, recurse := recursivePath(pathname) dir, err := w.getDir(pathname) @@ -566,11 +409,11 @@ func (w *Watcher) remWatch(pathname string) error { return fmt.Errorf("%w: %s", ErrNonExistentWatch, pathname) } if pathname == dir { - w.sendEvent(watch.path, watch.mask&sysFSIGNORED) + w.sendEvent(watch.path, "", watch.mask&sysFSIGNORED) watch.mask = 0 } else { name := filepath.Base(pathname) - w.sendEvent(filepath.Join(watch.path, name), watch.names[name]&sysFSIGNORED) + w.sendEvent(filepath.Join(watch.path, name), "", watch.names[name]&sysFSIGNORED) delete(watch.names, name) } @@ -578,23 +421,23 @@ func (w *Watcher) remWatch(pathname string) error { } // Must run within the I/O thread. -func (w *Watcher) deleteWatch(watch *watch) { +func (w *readDirChangesW) deleteWatch(watch *watch) { for name, mask := range watch.names { if mask&provisional == 0 { - w.sendEvent(filepath.Join(watch.path, name), mask&sysFSIGNORED) + w.sendEvent(filepath.Join(watch.path, name), "", mask&sysFSIGNORED) } delete(watch.names, name) } if watch.mask != 0 { if watch.mask&provisional == 0 { - w.sendEvent(watch.path, watch.mask&sysFSIGNORED) + w.sendEvent(watch.path, "", watch.mask&sysFSIGNORED) } watch.mask = 0 } } // Must run within the I/O thread. -func (w *Watcher) startRead(watch *watch) error { +func (w *readDirChangesW) startRead(watch *watch) error { err := windows.CancelIo(watch.ino.handle) if err != nil { w.sendError(os.NewSyscallError("CancelIo", err)) @@ -624,7 +467,7 @@ func (w *Watcher) startRead(watch *watch) error { err := os.NewSyscallError("ReadDirectoryChanges", rdErr) if rdErr == windows.ERROR_ACCESS_DENIED && watch.mask&provisional == 0 { // Watched directory was probably removed - w.sendEvent(watch.path, watch.mask&sysFSDELETESELF) + w.sendEvent(watch.path, "", watch.mask&sysFSDELETESELF) err = nil } w.deleteWatch(watch) @@ -637,7 +480,7 @@ func (w *Watcher) startRead(watch *watch) error { // readEvents reads from the I/O completion port, converts the // received events into Event objects and sends them via the Events channel. // Entry point to the I/O thread. -func (w *Watcher) readEvents() { +func (w *readDirChangesW) readEvents() { var ( n uint32 key uintptr @@ -700,7 +543,7 @@ func (w *Watcher) readEvents() { } case windows.ERROR_ACCESS_DENIED: // Watched directory was probably removed - w.sendEvent(watch.path, watch.mask&sysFSDELETESELF) + w.sendEvent(watch.path, "", watch.mask&sysFSDELETESELF) w.deleteWatch(watch) w.startRead(watch) continue @@ -733,6 +576,10 @@ func (w *Watcher) readEvents() { name := windows.UTF16ToString(buf) fullname := filepath.Join(watch.path, name) + if debug { + internal.Debug(fullname, raw.Action) + } + var mask uint64 switch raw.Action { case windows.FILE_ACTION_REMOVED: @@ -761,21 +608,22 @@ func (w *Watcher) readEvents() { } } - sendNameEvent := func() { - w.sendEvent(fullname, watch.names[name]&mask) - } if raw.Action != windows.FILE_ACTION_RENAMED_NEW_NAME { - sendNameEvent() + w.sendEvent(fullname, "", watch.names[name]&mask) } if raw.Action == windows.FILE_ACTION_REMOVED { - w.sendEvent(fullname, watch.names[name]&sysFSIGNORED) + w.sendEvent(fullname, "", watch.names[name]&sysFSIGNORED) delete(watch.names, name) } - w.sendEvent(fullname, watch.mask&w.toFSnotifyFlags(raw.Action)) + if watch.rename != "" && raw.Action == windows.FILE_ACTION_RENAMED_NEW_NAME { + w.sendEvent(fullname, filepath.Join(watch.path, watch.rename), watch.mask&w.toFSnotifyFlags(raw.Action)) + } else { + w.sendEvent(fullname, "", watch.mask&w.toFSnotifyFlags(raw.Action)) + } + if raw.Action == windows.FILE_ACTION_RENAMED_NEW_NAME { - fullname = filepath.Join(watch.path, watch.rename) - sendNameEvent() + w.sendEvent(filepath.Join(watch.path, watch.rename), "", watch.names[name]&mask) } // Move to the next event in the buffer @@ -787,8 +635,7 @@ func (w *Watcher) readEvents() { // Error! if offset >= n { //lint:ignore ST1005 Windows should be capitalized - w.sendError(errors.New( - "Windows system assumed buffer larger than it is, events have likely been missed")) + w.sendError(errors.New("Windows system assumed buffer larger than it is, events have likely been missed")) break } } @@ -799,7 +646,7 @@ func (w *Watcher) readEvents() { } } -func (w *Watcher) toWindowsFlags(mask uint64) uint32 { +func (w *readDirChangesW) toWindowsFlags(mask uint64) uint32 { var m uint32 if mask&sysFSMODIFY != 0 { m |= windows.FILE_NOTIFY_CHANGE_LAST_WRITE @@ -810,7 +657,7 @@ func (w *Watcher) toWindowsFlags(mask uint64) uint32 { return m } -func (w *Watcher) toFSnotifyFlags(action uint32) uint64 { +func (w *readDirChangesW) toFSnotifyFlags(action uint32) uint64 { switch action { case windows.FILE_ACTION_ADDED: return sysFSCREATE @@ -825,3 +672,11 @@ func (w *Watcher) toFSnotifyFlags(action uint32) uint64 { } return 0 } + +func (w *readDirChangesW) xSupports(op Op) bool { + if op.Has(xUnportableOpen) || op.Has(xUnportableRead) || + op.Has(xUnportableCloseWrite) || op.Has(xUnportableCloseRead) { + return false + } + return true +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/fsnotify.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/fsnotify.go index 24c99cc4999..0760efe9160 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/fsnotify.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/fsnotify.go @@ -3,19 +3,146 @@ // // Currently supported systems: // -// Linux 2.6.32+ via inotify -// BSD, macOS via kqueue -// Windows via ReadDirectoryChangesW -// illumos via FEN +// - Linux via inotify +// - BSD, macOS via kqueue +// - Windows via ReadDirectoryChangesW +// - illumos via FEN +// +// # FSNOTIFY_DEBUG +// +// Set the FSNOTIFY_DEBUG environment variable to "1" to print debug messages to +// stderr. This can be useful to track down some problems, especially in cases +// where fsnotify is used as an indirect dependency. +// +// Every event will be printed as soon as there's something useful to print, +// with as little processing from fsnotify. +// +// Example output: +// +// FSNOTIFY_DEBUG: 11:34:23.633087586 256:IN_CREATE → "/tmp/file-1" +// FSNOTIFY_DEBUG: 11:34:23.633202319 4:IN_ATTRIB → "/tmp/file-1" +// FSNOTIFY_DEBUG: 11:34:28.989728764 512:IN_DELETE → "/tmp/file-1" package fsnotify import ( "errors" "fmt" + "os" "path/filepath" "strings" ) +// Watcher watches a set of paths, delivering events on a channel. +// +// A watcher should not be copied (e.g. pass it by pointer, rather than by +// value). +// +// # Linux notes +// +// When a file is removed a Remove event won't be emitted until all file +// descriptors are closed, and deletes will always emit a Chmod. For example: +// +// fp := os.Open("file") +// os.Remove("file") // Triggers Chmod +// fp.Close() // Triggers Remove +// +// This is the event that inotify sends, so not much can be changed about this. +// +// The fs.inotify.max_user_watches sysctl variable specifies the upper limit +// for the number of watches per user, and fs.inotify.max_user_instances +// specifies the maximum number of inotify instances per user. Every Watcher you +// create is an "instance", and every path you add is a "watch". +// +// These are also exposed in /proc as /proc/sys/fs/inotify/max_user_watches and +// /proc/sys/fs/inotify/max_user_instances +// +// To increase them you can use sysctl or write the value to the /proc file: +// +// # Default values on Linux 5.18 +// sysctl fs.inotify.max_user_watches=124983 +// sysctl fs.inotify.max_user_instances=128 +// +// To make the changes persist on reboot edit /etc/sysctl.conf or +// /usr/lib/sysctl.d/50-default.conf (details differ per Linux distro; check +// your distro's documentation): +// +// fs.inotify.max_user_watches=124983 +// fs.inotify.max_user_instances=128 +// +// Reaching the limit will result in a "no space left on device" or "too many open +// files" error. +// +// # kqueue notes (macOS, BSD) +// +// kqueue requires opening a file descriptor for every file that's being watched; +// so if you're watching a directory with five files then that's six file +// descriptors. You will run in to your system's "max open files" limit faster on +// these platforms. +// +// The sysctl variables kern.maxfiles and kern.maxfilesperproc can be used to +// control the maximum number of open files, as well as /etc/login.conf on BSD +// systems. +// +// # Windows notes +// +// Paths can be added as "C:\\path\\to\\dir", but forward slashes +// ("C:/path/to/dir") will also work. +// +// When a watched directory is removed it will always send an event for the +// directory itself, but may not send events for all files in that directory. +// Sometimes it will send events for all files, sometimes it will send no +// events, and often only for some files. +// +// The default ReadDirectoryChangesW() buffer size is 64K, which is the largest +// value that is guaranteed to work with SMB filesystems. If you have many +// events in quick succession this may not be enough, and you will have to use +// [WithBufferSize] to increase the value. +type Watcher struct { + b backend + + // Events sends the filesystem change events. + // + // fsnotify can send the following events; a "path" here can refer to a + // file, directory, symbolic link, or special file like a FIFO. + // + // fsnotify.Create A new path was created; this may be followed by one + // or more Write events if data also gets written to a + // file. + // + // fsnotify.Remove A path was removed. + // + // fsnotify.Rename A path was renamed. A rename is always sent with the + // old path as Event.Name, and a Create event will be + // sent with the new name. Renames are only sent for + // paths that are currently watched; e.g. moving an + // unmonitored file into a monitored directory will + // show up as just a Create. Similarly, renaming a file + // to outside a monitored directory will show up as + // only a Rename. + // + // fsnotify.Write A file or named pipe was written to. A Truncate will + // also trigger a Write. A single "write action" + // initiated by the user may show up as one or multiple + // writes, depending on when the system syncs things to + // disk. For example when compiling a large Go program + // you may get hundreds of Write events, and you may + // want to wait until you've stopped receiving them + // (see the dedup example in cmd/fsnotify). + // + // Some systems may send Write event for directories + // when the directory content changes. + // + // fsnotify.Chmod Attributes were changed. On Linux this is also sent + // when a file is removed (or more accurately, when a + // link to an inode is removed). On kqueue it's sent + // when a file is truncated. On Windows it's never + // sent. + Events chan Event + + // Errors sends any errors. + Errors chan error +} + // Event represents a file system notification. type Event struct { // Path to the file or directory. @@ -30,6 +157,16 @@ type Event struct { // This is a bitmask and some systems may send multiple operations at once. // Use the Event.Has() method instead of comparing with ==. Op Op + + // Create events will have this set to the old path if it's a rename. This + // only works when both the source and destination are watched. It's not + // reliable when watching individual files, only directories. + // + // For example "mv /tmp/file /tmp/rename" will emit: + // + // Event{Op: Rename, Name: "/tmp/file"} + // Event{Op: Create, Name: "/tmp/rename", RenamedFrom: "/tmp/file"} + renamedFrom string } // Op describes a set of file operations. @@ -50,7 +187,7 @@ const ( // example "remove to trash" is often a rename). Remove - // The path was renamed to something else; any watched on it will be + // The path was renamed to something else; any watches on it will be // removed. Rename @@ -60,15 +197,155 @@ const ( // get triggered very frequently by some software. For example, Spotlight // indexing on macOS, anti-virus software, backup software, etc. Chmod + + // File descriptor was opened. + // + // Only works on Linux and FreeBSD. + xUnportableOpen + + // File was read from. + // + // Only works on Linux and FreeBSD. + xUnportableRead + + // File opened for writing was closed. + // + // Only works on Linux and FreeBSD. + // + // The advantage of using this over Write is that it's more reliable than + // waiting for Write events to stop. It's also faster (if you're not + // listening to Write events): copying a file of a few GB can easily + // generate tens of thousands of Write events in a short span of time. + xUnportableCloseWrite + + // File opened for reading was closed. + // + // Only works on Linux and FreeBSD. + xUnportableCloseRead ) -// Common errors that can be reported. var ( + // ErrNonExistentWatch is used when Remove() is called on a path that's not + // added. ErrNonExistentWatch = errors.New("fsnotify: can't remove non-existent watch") - ErrEventOverflow = errors.New("fsnotify: queue or buffer overflow") - ErrClosed = errors.New("fsnotify: watcher already closed") + + // ErrClosed is used when trying to operate on a closed Watcher. + ErrClosed = errors.New("fsnotify: watcher already closed") + + // ErrEventOverflow is reported from the Errors channel when there are too + // many events: + // + // - inotify: inotify returns IN_Q_OVERFLOW – because there are too + // many queued events (the fs.inotify.max_queued_events + // sysctl can be used to increase this). + // - windows: The buffer size is too small; WithBufferSize() can be used to increase it. + // - kqueue, fen: Not used. + ErrEventOverflow = errors.New("fsnotify: queue or buffer overflow") + + // ErrUnsupported is returned by AddWith() when WithOps() specified an + // Unportable event that's not supported on this platform. + xErrUnsupported = errors.New("fsnotify: not supported with this backend") ) +// NewWatcher creates a new Watcher. +func NewWatcher() (*Watcher, error) { + ev, errs := make(chan Event), make(chan error) + b, err := newBackend(ev, errs) + if err != nil { + return nil, err + } + return &Watcher{b: b, Events: ev, Errors: errs}, nil +} + +// NewBufferedWatcher creates a new Watcher with a buffered Watcher.Events +// channel. +// +// The main use case for this is situations with a very large number of events +// where the kernel buffer size can't be increased (e.g. due to lack of +// permissions). An unbuffered Watcher will perform better for almost all use +// cases, and whenever possible you will be better off increasing the kernel +// buffers instead of adding a large userspace buffer. +func NewBufferedWatcher(sz uint) (*Watcher, error) { + ev, errs := make(chan Event), make(chan error) + b, err := newBufferedBackend(sz, ev, errs) + if err != nil { + return nil, err + } + return &Watcher{b: b, Events: ev, Errors: errs}, nil +} + +// Add starts monitoring the path for changes. +// +// A path can only be watched once; watching it more than once is a no-op and will +// not return an error. Paths that do not yet exist on the filesystem cannot be +// watched. +// +// A watch will be automatically removed if the watched path is deleted or +// renamed. The exception is the Windows backend, which doesn't remove the +// watcher on renames. +// +// Notifications on network filesystems (NFS, SMB, FUSE, etc.) or special +// filesystems (/proc, /sys, etc.) generally don't work. +// +// Returns [ErrClosed] if [Watcher.Close] was called. +// +// See [Watcher.AddWith] for a version that allows adding options. +// +// # Watching directories +// +// All files in a directory are monitored, including new files that are created +// after the watcher is started. Subdirectories are not watched (i.e. it's +// non-recursive). +// +// # Watching files +// +// Watching individual files (rather than directories) is generally not +// recommended as many programs (especially editors) update files atomically: it +// will write to a temporary file which is then moved to destination, +// overwriting the original (or some variant thereof). The watcher on the +// original file is now lost, as that no longer exists. +// +// The upshot of this is that a power failure or crash won't leave a +// half-written file. +// +// Watch the parent directory and use Event.Name to filter out files you're not +// interested in. There is an example of this in cmd/fsnotify/file.go. +func (w *Watcher) Add(path string) error { return w.b.Add(path) } + +// AddWith is like [Watcher.Add], but allows adding options. When using Add() +// the defaults described below are used. +// +// Possible options are: +// +// - [WithBufferSize] sets the buffer size for the Windows backend; no-op on +// other platforms. The default is 64K (65536 bytes). +func (w *Watcher) AddWith(path string, opts ...addOpt) error { return w.b.AddWith(path, opts...) } + +// Remove stops monitoring the path for changes. +// +// Directories are always removed non-recursively. For example, if you added +// /tmp/dir and /tmp/dir/subdir then you will need to remove both. +// +// Removing a path that has not yet been added returns [ErrNonExistentWatch]. +// +// Returns nil if [Watcher.Close] was called. +func (w *Watcher) Remove(path string) error { return w.b.Remove(path) } + +// Close removes all watches and closes the Events channel. +func (w *Watcher) Close() error { return w.b.Close() } + +// WatchList returns all paths explicitly added with [Watcher.Add] (and are not +// yet removed). +// +// Returns nil if [Watcher.Close] was called. +func (w *Watcher) WatchList() []string { return w.b.WatchList() } + +// Supports reports if all the listed operations are supported by this platform. +// +// Create, Write, Remove, Rename, and Chmod are always supported. It can only +// return false for an Op starting with Unportable. +func (w *Watcher) xSupports(op Op) bool { return w.b.xSupports(op) } + func (o Op) String() string { var b strings.Builder if o.Has(Create) { @@ -80,6 +357,18 @@ func (o Op) String() string { if o.Has(Write) { b.WriteString("|WRITE") } + if o.Has(xUnportableOpen) { + b.WriteString("|OPEN") + } + if o.Has(xUnportableRead) { + b.WriteString("|READ") + } + if o.Has(xUnportableCloseWrite) { + b.WriteString("|CLOSE_WRITE") + } + if o.Has(xUnportableCloseRead) { + b.WriteString("|CLOSE_READ") + } if o.Has(Rename) { b.WriteString("|RENAME") } @@ -100,24 +389,48 @@ func (e Event) Has(op Op) bool { return e.Op.Has(op) } // String returns a string representation of the event with their path. func (e Event) String() string { + if e.renamedFrom != "" { + return fmt.Sprintf("%-13s %q ← %q", e.Op.String(), e.Name, e.renamedFrom) + } return fmt.Sprintf("%-13s %q", e.Op.String(), e.Name) } type ( + backend interface { + Add(string) error + AddWith(string, ...addOpt) error + Remove(string) error + WatchList() []string + Close() error + xSupports(Op) bool + } addOpt func(opt *withOpts) withOpts struct { - bufsize int + bufsize int + op Op + noFollow bool + sendCreate bool } ) +var debug = func() bool { + // Check for exactly "1" (rather than mere existence) so we can add + // options/flags in the future. I don't know if we ever want that, but it's + // nice to leave the option open. + return os.Getenv("FSNOTIFY_DEBUG") == "1" +}() + var defaultOpts = withOpts{ bufsize: 65536, // 64K + op: Create | Write | Remove | Rename | Chmod, } func getOptions(opts ...addOpt) withOpts { with := defaultOpts for _, o := range opts { - o(&with) + if o != nil { + o(&with) + } } return with } @@ -136,9 +449,44 @@ func WithBufferSize(bytes int) addOpt { return func(opt *withOpts) { opt.bufsize = bytes } } +// WithOps sets which operations to listen for. The default is [Create], +// [Write], [Remove], [Rename], and [Chmod]. +// +// Excluding operations you're not interested in can save quite a bit of CPU +// time; in some use cases there may be hundreds of thousands of useless Write +// or Chmod operations per second. +// +// This can also be used to add unportable operations not supported by all +// platforms; unportable operations all start with "Unportable": +// [UnportableOpen], [UnportableRead], [UnportableCloseWrite], and +// [UnportableCloseRead]. +// +// AddWith returns an error when using an unportable operation that's not +// supported. Use [Watcher.Support] to check for support. +func withOps(op Op) addOpt { + return func(opt *withOpts) { opt.op = op } +} + +// WithNoFollow disables following symlinks, so the symlinks themselves are +// watched. +func withNoFollow() addOpt { + return func(opt *withOpts) { opt.noFollow = true } +} + +// "Internal" option for recursive watches on inotify. +func withCreate() addOpt { + return func(opt *withOpts) { opt.sendCreate = true } +} + +var enableRecurse = false + // Check if this path is recursive (ends with "/..." or "\..."), and return the // path with the /... stripped. func recursivePath(path string) (string, bool) { + path = filepath.Clean(path) + if !enableRecurse { // Only enabled in tests for now. + return path, false + } if filepath.Base(path) == "..." { return filepath.Dir(path), true } diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/darwin.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/darwin.go new file mode 100644 index 00000000000..b0eab10090d --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/darwin.go @@ -0,0 +1,39 @@ +//go:build darwin + +package internal + +import ( + "syscall" + + "golang.org/x/sys/unix" +) + +var ( + SyscallEACCES = syscall.EACCES + UnixEACCES = unix.EACCES +) + +var maxfiles uint64 + +// Go 1.19 will do this automatically: https://go-review.googlesource.com/c/go/+/393354/ +func SetRlimit() { + var l syscall.Rlimit + err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &l) + if err == nil && l.Cur != l.Max { + l.Cur = l.Max + syscall.Setrlimit(syscall.RLIMIT_NOFILE, &l) + } + maxfiles = l.Cur + + if n, err := syscall.SysctlUint32("kern.maxfiles"); err == nil && uint64(n) < maxfiles { + maxfiles = uint64(n) + } + + if n, err := syscall.SysctlUint32("kern.maxfilesperproc"); err == nil && uint64(n) < maxfiles { + maxfiles = uint64(n) + } +} + +func Maxfiles() uint64 { return maxfiles } +func Mkfifo(path string, mode uint32) error { return unix.Mkfifo(path, mode) } +func Mknod(path string, mode uint32, dev int) error { return unix.Mknod(path, mode, dev) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_darwin.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_darwin.go new file mode 100644 index 00000000000..928319fb09a --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_darwin.go @@ -0,0 +1,57 @@ +package internal + +import "golang.org/x/sys/unix" + +var names = []struct { + n string + m uint32 +}{ + {"NOTE_ABSOLUTE", unix.NOTE_ABSOLUTE}, + {"NOTE_ATTRIB", unix.NOTE_ATTRIB}, + {"NOTE_BACKGROUND", unix.NOTE_BACKGROUND}, + {"NOTE_CHILD", unix.NOTE_CHILD}, + {"NOTE_CRITICAL", unix.NOTE_CRITICAL}, + {"NOTE_DELETE", unix.NOTE_DELETE}, + {"NOTE_EXEC", unix.NOTE_EXEC}, + {"NOTE_EXIT", unix.NOTE_EXIT}, + {"NOTE_EXITSTATUS", unix.NOTE_EXITSTATUS}, + {"NOTE_EXIT_CSERROR", unix.NOTE_EXIT_CSERROR}, + {"NOTE_EXIT_DECRYPTFAIL", unix.NOTE_EXIT_DECRYPTFAIL}, + {"NOTE_EXIT_DETAIL", unix.NOTE_EXIT_DETAIL}, + {"NOTE_EXIT_DETAIL_MASK", unix.NOTE_EXIT_DETAIL_MASK}, + {"NOTE_EXIT_MEMORY", unix.NOTE_EXIT_MEMORY}, + {"NOTE_EXIT_REPARENTED", unix.NOTE_EXIT_REPARENTED}, + {"NOTE_EXTEND", unix.NOTE_EXTEND}, + {"NOTE_FFAND", unix.NOTE_FFAND}, + {"NOTE_FFCOPY", unix.NOTE_FFCOPY}, + {"NOTE_FFCTRLMASK", unix.NOTE_FFCTRLMASK}, + {"NOTE_FFLAGSMASK", unix.NOTE_FFLAGSMASK}, + {"NOTE_FFNOP", unix.NOTE_FFNOP}, + {"NOTE_FFOR", unix.NOTE_FFOR}, + {"NOTE_FORK", unix.NOTE_FORK}, + {"NOTE_FUNLOCK", unix.NOTE_FUNLOCK}, + {"NOTE_LEEWAY", unix.NOTE_LEEWAY}, + {"NOTE_LINK", unix.NOTE_LINK}, + {"NOTE_LOWAT", unix.NOTE_LOWAT}, + {"NOTE_MACHTIME", unix.NOTE_MACHTIME}, + {"NOTE_MACH_CONTINUOUS_TIME", unix.NOTE_MACH_CONTINUOUS_TIME}, + {"NOTE_NONE", unix.NOTE_NONE}, + {"NOTE_NSECONDS", unix.NOTE_NSECONDS}, + {"NOTE_OOB", unix.NOTE_OOB}, + //{"NOTE_PCTRLMASK", unix.NOTE_PCTRLMASK}, -0x100000 (?!) + {"NOTE_PDATAMASK", unix.NOTE_PDATAMASK}, + {"NOTE_REAP", unix.NOTE_REAP}, + {"NOTE_RENAME", unix.NOTE_RENAME}, + {"NOTE_REVOKE", unix.NOTE_REVOKE}, + {"NOTE_SECONDS", unix.NOTE_SECONDS}, + {"NOTE_SIGNAL", unix.NOTE_SIGNAL}, + {"NOTE_TRACK", unix.NOTE_TRACK}, + {"NOTE_TRACKERR", unix.NOTE_TRACKERR}, + {"NOTE_TRIGGER", unix.NOTE_TRIGGER}, + {"NOTE_USECONDS", unix.NOTE_USECONDS}, + {"NOTE_VM_ERROR", unix.NOTE_VM_ERROR}, + {"NOTE_VM_PRESSURE", unix.NOTE_VM_PRESSURE}, + {"NOTE_VM_PRESSURE_SUDDEN_TERMINATE", unix.NOTE_VM_PRESSURE_SUDDEN_TERMINATE}, + {"NOTE_VM_PRESSURE_TERMINATE", unix.NOTE_VM_PRESSURE_TERMINATE}, + {"NOTE_WRITE", unix.NOTE_WRITE}, +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_dragonfly.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_dragonfly.go new file mode 100644 index 00000000000..3186b0c3491 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_dragonfly.go @@ -0,0 +1,33 @@ +package internal + +import "golang.org/x/sys/unix" + +var names = []struct { + n string + m uint32 +}{ + {"NOTE_ATTRIB", unix.NOTE_ATTRIB}, + {"NOTE_CHILD", unix.NOTE_CHILD}, + {"NOTE_DELETE", unix.NOTE_DELETE}, + {"NOTE_EXEC", unix.NOTE_EXEC}, + {"NOTE_EXIT", unix.NOTE_EXIT}, + {"NOTE_EXTEND", unix.NOTE_EXTEND}, + {"NOTE_FFAND", unix.NOTE_FFAND}, + {"NOTE_FFCOPY", unix.NOTE_FFCOPY}, + {"NOTE_FFCTRLMASK", unix.NOTE_FFCTRLMASK}, + {"NOTE_FFLAGSMASK", unix.NOTE_FFLAGSMASK}, + {"NOTE_FFNOP", unix.NOTE_FFNOP}, + {"NOTE_FFOR", unix.NOTE_FFOR}, + {"NOTE_FORK", unix.NOTE_FORK}, + {"NOTE_LINK", unix.NOTE_LINK}, + {"NOTE_LOWAT", unix.NOTE_LOWAT}, + {"NOTE_OOB", unix.NOTE_OOB}, + {"NOTE_PCTRLMASK", unix.NOTE_PCTRLMASK}, + {"NOTE_PDATAMASK", unix.NOTE_PDATAMASK}, + {"NOTE_RENAME", unix.NOTE_RENAME}, + {"NOTE_REVOKE", unix.NOTE_REVOKE}, + {"NOTE_TRACK", unix.NOTE_TRACK}, + {"NOTE_TRACKERR", unix.NOTE_TRACKERR}, + {"NOTE_TRIGGER", unix.NOTE_TRIGGER}, + {"NOTE_WRITE", unix.NOTE_WRITE}, +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_freebsd.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_freebsd.go new file mode 100644 index 00000000000..f69fdb930f5 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_freebsd.go @@ -0,0 +1,42 @@ +package internal + +import "golang.org/x/sys/unix" + +var names = []struct { + n string + m uint32 +}{ + {"NOTE_ABSTIME", unix.NOTE_ABSTIME}, + {"NOTE_ATTRIB", unix.NOTE_ATTRIB}, + {"NOTE_CHILD", unix.NOTE_CHILD}, + {"NOTE_CLOSE", unix.NOTE_CLOSE}, + {"NOTE_CLOSE_WRITE", unix.NOTE_CLOSE_WRITE}, + {"NOTE_DELETE", unix.NOTE_DELETE}, + {"NOTE_EXEC", unix.NOTE_EXEC}, + {"NOTE_EXIT", unix.NOTE_EXIT}, + {"NOTE_EXTEND", unix.NOTE_EXTEND}, + {"NOTE_FFAND", unix.NOTE_FFAND}, + {"NOTE_FFCOPY", unix.NOTE_FFCOPY}, + {"NOTE_FFCTRLMASK", unix.NOTE_FFCTRLMASK}, + {"NOTE_FFLAGSMASK", unix.NOTE_FFLAGSMASK}, + {"NOTE_FFNOP", unix.NOTE_FFNOP}, + {"NOTE_FFOR", unix.NOTE_FFOR}, + {"NOTE_FILE_POLL", unix.NOTE_FILE_POLL}, + {"NOTE_FORK", unix.NOTE_FORK}, + {"NOTE_LINK", unix.NOTE_LINK}, + {"NOTE_LOWAT", unix.NOTE_LOWAT}, + {"NOTE_MSECONDS", unix.NOTE_MSECONDS}, + {"NOTE_NSECONDS", unix.NOTE_NSECONDS}, + {"NOTE_OPEN", unix.NOTE_OPEN}, + {"NOTE_PCTRLMASK", unix.NOTE_PCTRLMASK}, + {"NOTE_PDATAMASK", unix.NOTE_PDATAMASK}, + {"NOTE_READ", unix.NOTE_READ}, + {"NOTE_RENAME", unix.NOTE_RENAME}, + {"NOTE_REVOKE", unix.NOTE_REVOKE}, + {"NOTE_SECONDS", unix.NOTE_SECONDS}, + {"NOTE_TRACK", unix.NOTE_TRACK}, + {"NOTE_TRACKERR", unix.NOTE_TRACKERR}, + {"NOTE_TRIGGER", unix.NOTE_TRIGGER}, + {"NOTE_USECONDS", unix.NOTE_USECONDS}, + {"NOTE_WRITE", unix.NOTE_WRITE}, +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_kqueue.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_kqueue.go new file mode 100644 index 00000000000..607e683bd73 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_kqueue.go @@ -0,0 +1,32 @@ +//go:build freebsd || openbsd || netbsd || dragonfly || darwin + +package internal + +import ( + "fmt" + "os" + "strings" + "time" + + "golang.org/x/sys/unix" +) + +func Debug(name string, kevent *unix.Kevent_t) { + mask := uint32(kevent.Fflags) + + var ( + l []string + unknown = mask + ) + for _, n := range names { + if mask&n.m == n.m { + l = append(l, n.n) + unknown ^= n.m + } + } + if unknown > 0 { + l = append(l, fmt.Sprintf("0x%x", unknown)) + } + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s %10d:%-60s → %q\n", + time.Now().Format("15:04:05.000000000"), mask, strings.Join(l, " | "), name) +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_linux.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_linux.go new file mode 100644 index 00000000000..35c734be431 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_linux.go @@ -0,0 +1,56 @@ +package internal + +import ( + "fmt" + "os" + "strings" + "time" + + "golang.org/x/sys/unix" +) + +func Debug(name string, mask, cookie uint32) { + names := []struct { + n string + m uint32 + }{ + {"IN_ACCESS", unix.IN_ACCESS}, + {"IN_ATTRIB", unix.IN_ATTRIB}, + {"IN_CLOSE", unix.IN_CLOSE}, + {"IN_CLOSE_NOWRITE", unix.IN_CLOSE_NOWRITE}, + {"IN_CLOSE_WRITE", unix.IN_CLOSE_WRITE}, + {"IN_CREATE", unix.IN_CREATE}, + {"IN_DELETE", unix.IN_DELETE}, + {"IN_DELETE_SELF", unix.IN_DELETE_SELF}, + {"IN_IGNORED", unix.IN_IGNORED}, + {"IN_ISDIR", unix.IN_ISDIR}, + {"IN_MODIFY", unix.IN_MODIFY}, + {"IN_MOVE", unix.IN_MOVE}, + {"IN_MOVED_FROM", unix.IN_MOVED_FROM}, + {"IN_MOVED_TO", unix.IN_MOVED_TO}, + {"IN_MOVE_SELF", unix.IN_MOVE_SELF}, + {"IN_OPEN", unix.IN_OPEN}, + {"IN_Q_OVERFLOW", unix.IN_Q_OVERFLOW}, + {"IN_UNMOUNT", unix.IN_UNMOUNT}, + } + + var ( + l []string + unknown = mask + ) + for _, n := range names { + if mask&n.m == n.m { + l = append(l, n.n) + unknown ^= n.m + } + } + if unknown > 0 { + l = append(l, fmt.Sprintf("0x%x", unknown)) + } + var c string + if cookie > 0 { + c = fmt.Sprintf("(cookie: %d) ", cookie) + } + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s %-30s → %s%q\n", + time.Now().Format("15:04:05.000000000"), strings.Join(l, "|"), c, name) +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_netbsd.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_netbsd.go new file mode 100644 index 00000000000..e5b3b6f6943 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_netbsd.go @@ -0,0 +1,25 @@ +package internal + +import "golang.org/x/sys/unix" + +var names = []struct { + n string + m uint32 +}{ + {"NOTE_ATTRIB", unix.NOTE_ATTRIB}, + {"NOTE_CHILD", unix.NOTE_CHILD}, + {"NOTE_DELETE", unix.NOTE_DELETE}, + {"NOTE_EXEC", unix.NOTE_EXEC}, + {"NOTE_EXIT", unix.NOTE_EXIT}, + {"NOTE_EXTEND", unix.NOTE_EXTEND}, + {"NOTE_FORK", unix.NOTE_FORK}, + {"NOTE_LINK", unix.NOTE_LINK}, + {"NOTE_LOWAT", unix.NOTE_LOWAT}, + {"NOTE_PCTRLMASK", unix.NOTE_PCTRLMASK}, + {"NOTE_PDATAMASK", unix.NOTE_PDATAMASK}, + {"NOTE_RENAME", unix.NOTE_RENAME}, + {"NOTE_REVOKE", unix.NOTE_REVOKE}, + {"NOTE_TRACK", unix.NOTE_TRACK}, + {"NOTE_TRACKERR", unix.NOTE_TRACKERR}, + {"NOTE_WRITE", unix.NOTE_WRITE}, +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_openbsd.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_openbsd.go new file mode 100644 index 00000000000..1dd455bc5a4 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_openbsd.go @@ -0,0 +1,28 @@ +package internal + +import "golang.org/x/sys/unix" + +var names = []struct { + n string + m uint32 +}{ + {"NOTE_ATTRIB", unix.NOTE_ATTRIB}, + // {"NOTE_CHANGE", unix.NOTE_CHANGE}, // Not on 386? + {"NOTE_CHILD", unix.NOTE_CHILD}, + {"NOTE_DELETE", unix.NOTE_DELETE}, + {"NOTE_EOF", unix.NOTE_EOF}, + {"NOTE_EXEC", unix.NOTE_EXEC}, + {"NOTE_EXIT", unix.NOTE_EXIT}, + {"NOTE_EXTEND", unix.NOTE_EXTEND}, + {"NOTE_FORK", unix.NOTE_FORK}, + {"NOTE_LINK", unix.NOTE_LINK}, + {"NOTE_LOWAT", unix.NOTE_LOWAT}, + {"NOTE_PCTRLMASK", unix.NOTE_PCTRLMASK}, + {"NOTE_PDATAMASK", unix.NOTE_PDATAMASK}, + {"NOTE_RENAME", unix.NOTE_RENAME}, + {"NOTE_REVOKE", unix.NOTE_REVOKE}, + {"NOTE_TRACK", unix.NOTE_TRACK}, + {"NOTE_TRACKERR", unix.NOTE_TRACKERR}, + {"NOTE_TRUNCATE", unix.NOTE_TRUNCATE}, + {"NOTE_WRITE", unix.NOTE_WRITE}, +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_solaris.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_solaris.go new file mode 100644 index 00000000000..f1b2e73bd5b --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_solaris.go @@ -0,0 +1,45 @@ +package internal + +import ( + "fmt" + "os" + "strings" + "time" + + "golang.org/x/sys/unix" +) + +func Debug(name string, mask int32) { + names := []struct { + n string + m int32 + }{ + {"FILE_ACCESS", unix.FILE_ACCESS}, + {"FILE_MODIFIED", unix.FILE_MODIFIED}, + {"FILE_ATTRIB", unix.FILE_ATTRIB}, + {"FILE_TRUNC", unix.FILE_TRUNC}, + {"FILE_NOFOLLOW", unix.FILE_NOFOLLOW}, + {"FILE_DELETE", unix.FILE_DELETE}, + {"FILE_RENAME_TO", unix.FILE_RENAME_TO}, + {"FILE_RENAME_FROM", unix.FILE_RENAME_FROM}, + {"UNMOUNTED", unix.UNMOUNTED}, + {"MOUNTEDOVER", unix.MOUNTEDOVER}, + {"FILE_EXCEPTION", unix.FILE_EXCEPTION}, + } + + var ( + l []string + unknown = mask + ) + for _, n := range names { + if mask&n.m == n.m { + l = append(l, n.n) + unknown ^= n.m + } + } + if unknown > 0 { + l = append(l, fmt.Sprintf("0x%x", unknown)) + } + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s %10d:%-30s → %q\n", + time.Now().Format("15:04:05.000000000"), mask, strings.Join(l, " | "), name) +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_windows.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_windows.go new file mode 100644 index 00000000000..52bf4ce53b5 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/debug_windows.go @@ -0,0 +1,40 @@ +package internal + +import ( + "fmt" + "os" + "path/filepath" + "strings" + "time" + + "golang.org/x/sys/windows" +) + +func Debug(name string, mask uint32) { + names := []struct { + n string + m uint32 + }{ + {"FILE_ACTION_ADDED", windows.FILE_ACTION_ADDED}, + {"FILE_ACTION_REMOVED", windows.FILE_ACTION_REMOVED}, + {"FILE_ACTION_MODIFIED", windows.FILE_ACTION_MODIFIED}, + {"FILE_ACTION_RENAMED_OLD_NAME", windows.FILE_ACTION_RENAMED_OLD_NAME}, + {"FILE_ACTION_RENAMED_NEW_NAME", windows.FILE_ACTION_RENAMED_NEW_NAME}, + } + + var ( + l []string + unknown = mask + ) + for _, n := range names { + if mask&n.m == n.m { + l = append(l, n.n) + unknown ^= n.m + } + } + if unknown > 0 { + l = append(l, fmt.Sprintf("0x%x", unknown)) + } + fmt.Fprintf(os.Stderr, "FSNOTIFY_DEBUG: %s %-65s → %q\n", + time.Now().Format("15:04:05.000000000"), strings.Join(l, " | "), filepath.ToSlash(name)) +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/freebsd.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/freebsd.go new file mode 100644 index 00000000000..547df1df84b --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/freebsd.go @@ -0,0 +1,31 @@ +//go:build freebsd + +package internal + +import ( + "syscall" + + "golang.org/x/sys/unix" +) + +var ( + SyscallEACCES = syscall.EACCES + UnixEACCES = unix.EACCES +) + +var maxfiles uint64 + +func SetRlimit() { + // Go 1.19 will do this automatically: https://go-review.googlesource.com/c/go/+/393354/ + var l syscall.Rlimit + err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &l) + if err == nil && l.Cur != l.Max { + l.Cur = l.Max + syscall.Setrlimit(syscall.RLIMIT_NOFILE, &l) + } + maxfiles = uint64(l.Cur) +} + +func Maxfiles() uint64 { return maxfiles } +func Mkfifo(path string, mode uint32) error { return unix.Mkfifo(path, mode) } +func Mknod(path string, mode uint32, dev int) error { return unix.Mknod(path, mode, uint64(dev)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/internal.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/internal.go new file mode 100644 index 00000000000..7daa45e19ee --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/internal.go @@ -0,0 +1,2 @@ +// Package internal contains some helpers. +package internal diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix.go new file mode 100644 index 00000000000..30976ce9739 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix.go @@ -0,0 +1,31 @@ +//go:build !windows && !darwin && !freebsd + +package internal + +import ( + "syscall" + + "golang.org/x/sys/unix" +) + +var ( + SyscallEACCES = syscall.EACCES + UnixEACCES = unix.EACCES +) + +var maxfiles uint64 + +func SetRlimit() { + // Go 1.19 will do this automatically: https://go-review.googlesource.com/c/go/+/393354/ + var l syscall.Rlimit + err := syscall.Getrlimit(syscall.RLIMIT_NOFILE, &l) + if err == nil && l.Cur != l.Max { + l.Cur = l.Max + syscall.Setrlimit(syscall.RLIMIT_NOFILE, &l) + } + maxfiles = uint64(l.Cur) +} + +func Maxfiles() uint64 { return maxfiles } +func Mkfifo(path string, mode uint32) error { return unix.Mkfifo(path, mode) } +func Mknod(path string, mode uint32, dev int) error { return unix.Mknod(path, mode, dev) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix2.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix2.go new file mode 100644 index 00000000000..37dfeddc289 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/unix2.go @@ -0,0 +1,7 @@ +//go:build !windows + +package internal + +func HasPrivilegesForSymlink() bool { + return true +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/windows.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/windows.go new file mode 100644 index 00000000000..a72c6495490 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/internal/windows.go @@ -0,0 +1,41 @@ +//go:build windows + +package internal + +import ( + "errors" + + "golang.org/x/sys/windows" +) + +// Just a dummy. +var ( + SyscallEACCES = errors.New("dummy") + UnixEACCES = errors.New("dummy") +) + +func SetRlimit() {} +func Maxfiles() uint64 { return 1<<64 - 1 } +func Mkfifo(path string, mode uint32) error { return errors.New("no FIFOs on Windows") } +func Mknod(path string, mode uint32, dev int) error { return errors.New("no device nodes on Windows") } + +func HasPrivilegesForSymlink() bool { + var sid *windows.SID + err := windows.AllocateAndInitializeSid( + &windows.SECURITY_NT_AUTHORITY, + 2, + windows.SECURITY_BUILTIN_DOMAIN_RID, + windows.DOMAIN_ALIAS_RID_ADMINS, + 0, 0, 0, 0, 0, 0, + &sid) + if err != nil { + return false + } + defer windows.FreeSid(sid) + token := windows.Token(0) + member, err := token.IsMember(sid) + if err != nil { + return false + } + return member || token.IsElevated() +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/mkdoc.zsh b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/mkdoc.zsh deleted file mode 100644 index 99012ae6539..00000000000 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/mkdoc.zsh +++ /dev/null @@ -1,259 +0,0 @@ -#!/usr/bin/env zsh -[ "${ZSH_VERSION:-}" = "" ] && echo >&2 "Only works with zsh" && exit 1 -setopt err_exit no_unset pipefail extended_glob - -# Simple script to update the godoc comments on all watchers so you don't need -# to update the same comment 5 times. - -watcher=$(</tmp/x - print -r -- $cmt >>/tmp/x - tail -n+$(( end + 1 )) $file >>/tmp/x - mv /tmp/x $file - done -} - -set-cmt '^type Watcher struct ' $watcher -set-cmt '^func NewWatcher(' $new -set-cmt '^func NewBufferedWatcher(' $newbuffered -set-cmt '^func (w \*Watcher) Add(' $add -set-cmt '^func (w \*Watcher) AddWith(' $addwith -set-cmt '^func (w \*Watcher) Remove(' $remove -set-cmt '^func (w \*Watcher) Close(' $close -set-cmt '^func (w \*Watcher) WatchList(' $watchlist -set-cmt '^[[:space:]]*Events *chan Event$' $events -set-cmt '^[[:space:]]*Errors *chan error$' $errors diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_bsd.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_bsd.go index 4322b0b8855..f65e8fe3edc 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_bsd.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_bsd.go @@ -1,5 +1,4 @@ //go:build freebsd || openbsd || netbsd || dragonfly -// +build freebsd openbsd netbsd dragonfly package fsnotify diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_darwin.go b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_darwin.go index 5da5ffa78fe..a29fc7aab62 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_darwin.go +++ b/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/system_darwin.go @@ -1,5 +1,4 @@ //go:build darwin -// +build darwin package fsnotify diff --git a/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/internal/function/func.go b/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/internal/function/func.go index d127d436230..def01a6be30 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/internal/function/func.go +++ b/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/internal/function/func.go @@ -19,6 +19,7 @@ const ( tbFunc // func(T) bool ttbFunc // func(T, T) bool + ttiFunc // func(T, T) int trbFunc // func(T, R) bool tibFunc // func(T, I) bool trFunc // func(T) R @@ -28,11 +29,13 @@ const ( Transformer = trFunc // func(T) R ValueFilter = ttbFunc // func(T, T) bool Less = ttbFunc // func(T, T) bool + Compare = ttiFunc // func(T, T) int ValuePredicate = tbFunc // func(T) bool KeyValuePredicate = trbFunc // func(T, R) bool ) var boolType = reflect.TypeOf(true) +var intType = reflect.TypeOf(0) // IsType reports whether the reflect.Type is of the specified function type. func IsType(t reflect.Type, ft funcType) bool { @@ -49,6 +52,10 @@ func IsType(t reflect.Type, ft funcType) bool { if ni == 2 && no == 1 && t.In(0) == t.In(1) && t.Out(0) == boolType { return true } + case ttiFunc: // func(T, T) int + if ni == 2 && no == 1 && t.In(0) == t.In(1) && t.Out(0) == intType { + return true + } case trbFunc: // func(T, R) bool if ni == 2 && no == 1 && t.Out(0) == boolType { return true diff --git a/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/options.go b/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/options.go index 754496f3b3f..ba3fce81ff1 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/options.go +++ b/cluster-api/providers/vsphere/vendor/github.com/google/go-cmp/cmp/options.go @@ -232,7 +232,15 @@ func (validator) apply(s *state, vx, vy reflect.Value) { if t := s.curPath.Index(-2).Type(); t.Name() != "" { // Named type with unexported fields. name = fmt.Sprintf("%q.%v", t.PkgPath(), t.Name()) // e.g., "path/to/package".MyType - if _, ok := reflect.New(t).Interface().(error); ok { + isProtoMessage := func(t reflect.Type) bool { + m, ok := reflect.PointerTo(t).MethodByName("ProtoReflect") + return ok && m.Type.NumIn() == 1 && m.Type.NumOut() == 1 && + m.Type.Out(0).PkgPath() == "google.golang.org/protobuf/reflect/protoreflect" && + m.Type.Out(0).Name() == "Message" + } + if isProtoMessage(t) { + help = `consider using "google.golang.org/protobuf/testing/protocmp".Transform to compare proto.Message types` + } else if _, ok := reflect.New(t).Interface().(error); ok { help = "consider using cmpopts.EquateErrors to compare error values" } else if t.Comparable() { help = "consider using cmpopts.EquateComparable to compare comparable Go types" diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/CHANGELOG.md b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/CHANGELOG.md index a20d997cdd9..890d8922285 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/CHANGELOG.md +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/CHANGELOG.md @@ -1,3 +1,24 @@ +## 1.37.0 + +### Features +- add To/ToNot/NotTo aliases for AsyncAssertion [5666f98] + +## 1.36.3 + +### Maintenance + +- bump all the things [adb8b49] +- chore: replace `interface{}` with `any` [7613216] +- Bump google.golang.org/protobuf from 1.36.1 to 1.36.5 (#822) [9fe5259] +- remove spurious "toolchain" from go.mod (#819) [a0e85b9] +- Bump golang.org/x/net from 0.33.0 to 0.35.0 (#823) [604a8b1] +- Bump activesupport from 6.0.6.1 to 6.1.7.5 in /docs (#772) [36fbc84] +- Bump github-pages from 231 to 232 in /docs (#778) [ced70d7] +- Bump rexml from 3.2.6 to 3.3.9 in /docs (#788) [c8b4a07] +- Bump github.com/onsi/ginkgo/v2 from 2.22.1 to 2.22.2 (#812) [06431b9] +- Bump webrick from 1.8.1 to 1.9.1 in /docs (#800) [b55a92d] +- Fix typos (#813) [a1d518b] + ## 1.36.2 ### Maintenance @@ -322,7 +343,7 @@ Require Go 1.22+ ### Features -Introducting [gcustom](https://onsi.github.io/gomega/#gcustom-a-convenient-mechanism-for-buildling-custom-matchers) - a convenient mechanism for building custom matchers. +Introducing [gcustom](https://onsi.github.io/gomega/#gcustom-a-convenient-mechanism-for-buildling-custom-matchers) - a convenient mechanism for building custom matchers. This is an RC release for `gcustom`. The external API may be tweaked in response to feedback however it is expected to remain mostly stable. @@ -461,7 +482,7 @@ These improvements are all documented in [Gomega's docs](https://onsi.github.io/ - Fix max number of samples in experiments on non-64-bit systems. (#528) [1c84497] - Remove dependency on ginkgo v1.16.4 (#530) [4dea8d5] - Fix for Go 1.18 (#532) [56d2a29] -- Document precendence of timeouts (#533) [b607941] +- Document precedence of timeouts (#533) [b607941] ## 1.18.1 @@ -478,7 +499,7 @@ These improvements are all documented in [Gomega's docs](https://onsi.github.io/ ## Fixes - Gomega now uses ioutil for Go 1.15 and lower (#492) - official support is only for the most recent two major versions of Go but this will unblock users who need to stay on older unsupported versions of Go. [c29c1c0] -## Maintenace +## Maintenance - Remove Travis workflow (#491) [72e6040] - Upgrade to Ginkgo 2.0.0 GA [f383637] - chore: fix description of HaveField matcher (#487) [2b4b2c0] @@ -726,7 +747,7 @@ Improvements: - Added `BeSent` which attempts to send a value down a channel and fails if the attempt blocks. Can be paired with `Eventually` to safely send a value down a channel with a timeout. - `Ω`, `Expect`, `Eventually`, and `Consistently` now immediately `panic` if there is no registered fail handler. This is always a mistake that can hide failing tests. -- `Receive()` no longer errors when passed a closed channel, it's perfectly fine to attempt to read from a closed channel so Ω(c).Should(Receive()) always fails and Ω(c).ShoudlNot(Receive()) always passes with a closed channel. +- `Receive()` no longer errors when passed a closed channel, it's perfectly fine to attempt to read from a closed channel so Ω(c).Should(Receive()) always fails and Ω(c).ShouldNot(Receive()) always passes with a closed channel. - Added `HavePrefix` and `HaveSuffix` matchers. - `ghttp` can now handle concurrent requests. - Added `Succeed` which allows one to write `Ω(MyFunction()).Should(Succeed())`. @@ -736,7 +757,7 @@ Improvements: - `ghttp` servers can take an `io.Writer`. `ghttp` will write a line to the writer when each request arrives. - Added `WithTransform` matcher to allow munging input data before feeding into the relevant matcher - Added boolean `And`, `Or`, and `Not` matchers to allow creating composite matchers -- Added `gbytes.TimeoutCloser`, `gbytes.TimeoutReader`, and `gbytes.TimeoutWriter` - these are convenience wrappers that timeout if the underlying Closer/Reader/Writer does not return within the alloted time. +- Added `gbytes.TimeoutCloser`, `gbytes.TimeoutReader`, and `gbytes.TimeoutWriter` - these are convenience wrappers that timeout if the underlying Closer/Reader/Writer does not return within the allotted time. - Added `gbytes.BufferReader` - this constructs a `gbytes.Buffer` that asynchronously reads the passed-in `io.Reader` into its buffer. Bug Fixes: @@ -781,7 +802,7 @@ New Matchers: Updated Matchers: -- `Receive` matcher can take a matcher as an argument and passes only if the channel under test receives an objet that satisfies the passed-in matcher. +- `Receive` matcher can take a matcher as an argument and passes only if the channel under test receives an object that satisfies the passed-in matcher. - Matchers that implement `MatchMayChangeInTheFuture(actual interface{}) bool` can inform `Eventually` and/or `Consistently` when a match has no chance of changing status in the future. For example, `Receive` returns `false` when a channel is closed. Misc: diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/format/format.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/format/format.go index 6c1680638bf..96f04b21045 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/format/format.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/format/format.go @@ -57,7 +57,7 @@ var Indent = " " var longFormThreshold = 20 -// GomegaStringer allows for custom formating of objects for gomega. +// GomegaStringer allows for custom formatting of objects for gomega. type GomegaStringer interface { // GomegaString will be used to custom format an object. // It does not follow UseStringerRepresentation value and will always be called regardless. @@ -73,7 +73,7 @@ If the CustomFormatter does not want to handle the object it should return ("", Strings returned by CustomFormatters are not truncated */ -type CustomFormatter func(value interface{}) (string, bool) +type CustomFormatter func(value any) (string, bool) type CustomFormatterKey uint var customFormatterKey CustomFormatterKey = 1 @@ -125,7 +125,7 @@ If expected is omitted, then the message looks like: */ -func Message(actual interface{}, message string, expected ...interface{}) string { +func Message(actual any, message string, expected ...any) string { if len(expected) == 0 { return fmt.Sprintf("Expected\n%s\n%s", Object(actual, 1), message) } @@ -255,7 +255,7 @@ recursing into the object. Set PrintContextObjects to true to print the content of objects implementing context.Context */ -func Object(object interface{}, indentation uint) string { +func Object(object any, indentation uint) string { indent := strings.Repeat(Indent, int(indentation)) value := reflect.ValueOf(object) commonRepresentation := "" @@ -392,7 +392,7 @@ func formatValue(value reflect.Value, indentation uint) string { } } -func formatString(object interface{}, indentation uint) string { +func formatString(object any, indentation uint) string { if indentation == 1 { s := fmt.Sprintf("%s", object) components := strings.Split(s, "\n") diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/gomega_dsl.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/gomega_dsl.go index 9a028f3f366..a491a64be77 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/gomega_dsl.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/gomega_dsl.go @@ -22,7 +22,7 @@ import ( "github.com/onsi/gomega/types" ) -const GOMEGA_VERSION = "1.36.2" +const GOMEGA_VERSION = "1.37.0" const nilGomegaPanic = `You are trying to make an assertion, but haven't registered Gomega's fail handler. If you're using Ginkgo then you probably forgot to put your assertion in an It(). @@ -191,7 +191,7 @@ func ensureDefaultGomegaIsConfigured() { // Will succeed only if `MyAmazingThing()` returns `(3, nil)` // // Ω and Expect are identical -func Ω(actual interface{}, extra ...interface{}) Assertion { +func Ω(actual any, extra ...any) Assertion { ensureDefaultGomegaIsConfigured() return Default.Ω(actual, extra...) } @@ -217,7 +217,7 @@ func Ω(actual interface{}, extra ...interface{}) Assertion { // Will succeed only if `MyAmazingThing()` returns `(3, nil)` // // Expect and Ω are identical -func Expect(actual interface{}, extra ...interface{}) Assertion { +func Expect(actual any, extra ...any) Assertion { ensureDefaultGomegaIsConfigured() return Default.Expect(actual, extra...) } @@ -233,7 +233,7 @@ func Expect(actual interface{}, extra ...interface{}) Assertion { // This is most useful in helper functions that make assertions. If you want Gomega's // error message to refer to the calling line in the test (as opposed to the line in the helper function) // set the first argument of `ExpectWithOffset` appropriately. -func ExpectWithOffset(offset int, actual interface{}, extra ...interface{}) Assertion { +func ExpectWithOffset(offset int, actual any, extra ...any) Assertion { ensureDefaultGomegaIsConfigured() return Default.ExpectWithOffset(offset, actual, extra...) } @@ -319,19 +319,19 @@ you an also use Eventually().WithContext(ctx) to pass in the context. Passed-in Eventually(client.FetchCount).WithContext(ctx).WithArguments("/users").Should(BeNumerically(">=", 17)) }, SpecTimeout(time.Second)) -Either way the context pasesd to Eventually is also passed to the underlying function. Now, when Ginkgo cancels the context both the FetchCount client and Gomega will be informed and can exit. +Either way the context passed to Eventually is also passed to the underlying function. Now, when Ginkgo cancels the context both the FetchCount client and Gomega will be informed and can exit. By default, when a context is passed to Eventually *without* an explicit timeout, Gomega will rely solely on the context's cancellation to determine when to stop polling. If you want to specify a timeout in addition to the context you can do so using the .WithTimeout() method. For example: Eventually(client.FetchCount).WithContext(ctx).WithTimeout(10*time.Second).Should(BeNumerically(">=", 17)) -now either the context cacnellation or the timeout will cause Eventually to stop polling. +now either the context cancellation or the timeout will cause Eventually to stop polling. If, instead, you would like to opt out of this behavior and have Gomega's default timeouts govern Eventuallys that take a context you can call: EnforceDefaultTimeoutsWhenUsingContexts() -in the DSL (or on a Gomega instance). Now all calls to Eventually that take a context will fail if eitehr the context is cancelled or the default timeout elapses. +in the DSL (or on a Gomega instance). Now all calls to Eventually that take a context will fail if either the context is cancelled or the default timeout elapses. **Category 3: Making assertions _in_ the function passed into Eventually** @@ -390,7 +390,7 @@ is equivalent to Eventually(...).WithTimeout(10*time.Second).WithPolling(2*time.Second).WithContext(ctx).Should(...) */ -func Eventually(actualOrCtx interface{}, args ...interface{}) AsyncAssertion { +func Eventually(actualOrCtx any, args ...any) AsyncAssertion { ensureDefaultGomegaIsConfigured() return Default.Eventually(actualOrCtx, args...) } @@ -404,7 +404,7 @@ func Eventually(actualOrCtx interface{}, args ...interface{}) AsyncAssertion { // `EventuallyWithOffset` specifying a timeout interval (and an optional polling interval) are // the same as `Eventually(...).WithOffset(...).WithTimeout` or // `Eventually(...).WithOffset(...).WithTimeout(...).WithPolling`. -func EventuallyWithOffset(offset int, actualOrCtx interface{}, args ...interface{}) AsyncAssertion { +func EventuallyWithOffset(offset int, actualOrCtx any, args ...any) AsyncAssertion { ensureDefaultGomegaIsConfigured() return Default.EventuallyWithOffset(offset, actualOrCtx, args...) } @@ -424,7 +424,7 @@ Consistently is useful in cases where you want to assert that something *does no This will block for 200 milliseconds and repeatedly check the channel and ensure nothing has been received. */ -func Consistently(actualOrCtx interface{}, args ...interface{}) AsyncAssertion { +func Consistently(actualOrCtx any, args ...any) AsyncAssertion { ensureDefaultGomegaIsConfigured() return Default.Consistently(actualOrCtx, args...) } @@ -435,13 +435,13 @@ func Consistently(actualOrCtx interface{}, args ...interface{}) AsyncAssertion { // // `ConsistentlyWithOffset` is the same as `Consistently(...).WithOffset` and // optional `WithTimeout` and `WithPolling`. -func ConsistentlyWithOffset(offset int, actualOrCtx interface{}, args ...interface{}) AsyncAssertion { +func ConsistentlyWithOffset(offset int, actualOrCtx any, args ...any) AsyncAssertion { ensureDefaultGomegaIsConfigured() return Default.ConsistentlyWithOffset(offset, actualOrCtx, args...) } /* -StopTrying can be used to signal to Eventually and Consistentlythat they should abort and stop trying. This always results in a failure of the assertion - and the failure message is the content of the StopTrying signal. +StopTrying can be used to signal to Eventually and Consistently that they should abort and stop trying. This always results in a failure of the assertion - and the failure message is the content of the StopTrying signal. You can send the StopTrying signal by either returning StopTrying("message") as an error from your passed-in function _or_ by calling StopTrying("message").Now() to trigger a panic and end execution. diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/assertion.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/assertion.go index 08356a610bb..cc846e7ce7a 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/assertion.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/assertion.go @@ -9,19 +9,19 @@ import ( ) type Assertion struct { - actuals []interface{} // actual value plus all extra values - actualIndex int // value to pass to the matcher - vet vetinari // the vet to call before calling Gomega matcher + actuals []any // actual value plus all extra values + actualIndex int // value to pass to the matcher + vet vetinari // the vet to call before calling Gomega matcher offset int g *Gomega } // ...obligatory discworld reference, as "vetineer" doesn't sound ... quite right. -type vetinari func(assertion *Assertion, optionalDescription ...interface{}) bool +type vetinari func(assertion *Assertion, optionalDescription ...any) bool -func NewAssertion(actualInput interface{}, g *Gomega, offset int, extra ...interface{}) *Assertion { +func NewAssertion(actualInput any, g *Gomega, offset int, extra ...any) *Assertion { return &Assertion{ - actuals: append([]interface{}{actualInput}, extra...), + actuals: append([]any{actualInput}, extra...), actualIndex: 0, vet: (*Assertion).vetActuals, offset: offset, @@ -44,37 +44,37 @@ func (assertion *Assertion) Error() types.Assertion { } } -func (assertion *Assertion) Should(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *Assertion) Should(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Assertion", optionalDescription...) return assertion.vet(assertion, optionalDescription...) && assertion.match(matcher, true, optionalDescription...) } -func (assertion *Assertion) ShouldNot(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *Assertion) ShouldNot(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Assertion", optionalDescription...) return assertion.vet(assertion, optionalDescription...) && assertion.match(matcher, false, optionalDescription...) } -func (assertion *Assertion) To(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *Assertion) To(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Assertion", optionalDescription...) return assertion.vet(assertion, optionalDescription...) && assertion.match(matcher, true, optionalDescription...) } -func (assertion *Assertion) ToNot(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *Assertion) ToNot(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Assertion", optionalDescription...) return assertion.vet(assertion, optionalDescription...) && assertion.match(matcher, false, optionalDescription...) } -func (assertion *Assertion) NotTo(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *Assertion) NotTo(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Assertion", optionalDescription...) return assertion.vet(assertion, optionalDescription...) && assertion.match(matcher, false, optionalDescription...) } -func (assertion *Assertion) buildDescription(optionalDescription ...interface{}) string { +func (assertion *Assertion) buildDescription(optionalDescription ...any) string { switch len(optionalDescription) { case 0: return "" @@ -86,7 +86,7 @@ func (assertion *Assertion) buildDescription(optionalDescription ...interface{}) return fmt.Sprintf(optionalDescription[0].(string), optionalDescription[1:]...) + "\n" } -func (assertion *Assertion) match(matcher types.GomegaMatcher, desiredMatch bool, optionalDescription ...interface{}) bool { +func (assertion *Assertion) match(matcher types.GomegaMatcher, desiredMatch bool, optionalDescription ...any) bool { actualInput := assertion.actuals[assertion.actualIndex] matches, err := matcher.Match(actualInput) assertion.g.THelper() @@ -113,7 +113,7 @@ func (assertion *Assertion) match(matcher types.GomegaMatcher, desiredMatch bool // vetActuals vets the actual values, with the (optional) exception of a // specific value, such as the first value in case non-error assertions, or the // last value in case of Error()-based assertions. -func (assertion *Assertion) vetActuals(optionalDescription ...interface{}) bool { +func (assertion *Assertion) vetActuals(optionalDescription ...any) bool { success, message := vetActuals(assertion.actuals, assertion.actualIndex) if success { return true @@ -129,7 +129,7 @@ func (assertion *Assertion) vetActuals(optionalDescription ...interface{}) bool // the final error value is non-zero. Otherwise, it doesn't vet the actual // values, as these are allowed to take on any values unless there is a non-zero // error value. -func (assertion *Assertion) vetError(optionalDescription ...interface{}) bool { +func (assertion *Assertion) vetError(optionalDescription ...any) bool { if err := assertion.actuals[assertion.actualIndex]; err != nil { // Go error result idiom: all other actual values must be zero values. return assertion.vetActuals(optionalDescription...) @@ -139,7 +139,7 @@ func (assertion *Assertion) vetError(optionalDescription ...interface{}) bool { // vetActuals vets a slice of actual values, optionally skipping a particular // value slice element, such as the first or last value slice element. -func vetActuals(actuals []interface{}, skipIndex int) (bool, string) { +func vetActuals(actuals []any, skipIndex int) (bool, string) { for i, actual := range actuals { if i == skipIndex { continue diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/async_assertion.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/async_assertion.go index 8b4cd1f5b79..a3a646e4ad0 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/async_assertion.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/async_assertion.go @@ -69,8 +69,8 @@ type AsyncAssertion struct { asyncType AsyncAssertionType actualIsFunc bool - actual interface{} - argsToForward []interface{} + actual any + argsToForward []any timeoutInterval time.Duration pollingInterval time.Duration @@ -80,7 +80,7 @@ type AsyncAssertion struct { g *Gomega } -func NewAsyncAssertion(asyncType AsyncAssertionType, actualInput interface{}, g *Gomega, timeoutInterval time.Duration, pollingInterval time.Duration, mustPassRepeatedly int, ctx context.Context, offset int) *AsyncAssertion { +func NewAsyncAssertion(asyncType AsyncAssertionType, actualInput any, g *Gomega, timeoutInterval time.Duration, pollingInterval time.Duration, mustPassRepeatedly int, ctx context.Context, offset int) *AsyncAssertion { out := &AsyncAssertion{ asyncType: asyncType, timeoutInterval: timeoutInterval, @@ -129,7 +129,7 @@ func (assertion *AsyncAssertion) WithContext(ctx context.Context) types.AsyncAss return assertion } -func (assertion *AsyncAssertion) WithArguments(argsToForward ...interface{}) types.AsyncAssertion { +func (assertion *AsyncAssertion) WithArguments(argsToForward ...any) types.AsyncAssertion { assertion.argsToForward = argsToForward return assertion } @@ -139,19 +139,31 @@ func (assertion *AsyncAssertion) MustPassRepeatedly(count int) types.AsyncAssert return assertion } -func (assertion *AsyncAssertion) Should(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *AsyncAssertion) Should(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Asynchronous assertion", optionalDescription...) return assertion.match(matcher, true, optionalDescription...) } -func (assertion *AsyncAssertion) ShouldNot(matcher types.GomegaMatcher, optionalDescription ...interface{}) bool { +func (assertion *AsyncAssertion) To(matcher types.GomegaMatcher, optionalDescription ...any) bool { + return assertion.Should(matcher, optionalDescription...) +} + +func (assertion *AsyncAssertion) ShouldNot(matcher types.GomegaMatcher, optionalDescription ...any) bool { assertion.g.THelper() vetOptionalDescription("Asynchronous assertion", optionalDescription...) return assertion.match(matcher, false, optionalDescription...) } -func (assertion *AsyncAssertion) buildDescription(optionalDescription ...interface{}) string { +func (assertion *AsyncAssertion) ToNot(matcher types.GomegaMatcher, optionalDescription ...any) bool { + return assertion.ShouldNot(matcher, optionalDescription...) +} + +func (assertion *AsyncAssertion) NotTo(matcher types.GomegaMatcher, optionalDescription ...any) bool { + return assertion.ShouldNot(matcher, optionalDescription...) +} + +func (assertion *AsyncAssertion) buildDescription(optionalDescription ...any) string { switch len(optionalDescription) { case 0: return "" @@ -163,7 +175,7 @@ func (assertion *AsyncAssertion) buildDescription(optionalDescription ...interfa return fmt.Sprintf(optionalDescription[0].(string), optionalDescription[1:]...) + "\n" } -func (assertion *AsyncAssertion) processReturnValues(values []reflect.Value) (interface{}, error) { +func (assertion *AsyncAssertion) processReturnValues(values []reflect.Value) (any, error) { if len(values) == 0 { return nil, &asyncPolledActualError{ message: fmt.Sprintf("The function passed to %s did not return any values", assertion.asyncType), @@ -224,7 +236,7 @@ func (assertion *AsyncAssertion) argumentMismatchError(t reflect.Type, numProvid if numProvided == 1 { have = "has" } - return fmt.Errorf(`The function passed to %s has signature %s takes %d arguments but %d %s been provided. Please use %s().WithArguments() to pass the corect set of arguments. + return fmt.Errorf(`The function passed to %s has signature %s takes %d arguments but %d %s been provided. Please use %s().WithArguments() to pass the correct set of arguments. You can learn more at https://onsi.github.io/gomega/#eventually `, assertion.asyncType, t, t.NumIn(), numProvided, have, assertion.asyncType) @@ -237,9 +249,9 @@ You can learn more at https://onsi.github.io/gomega/#eventually `, assertion.asyncType, reason) } -func (assertion *AsyncAssertion) buildActualPoller() (func() (interface{}, error), error) { +func (assertion *AsyncAssertion) buildActualPoller() (func() (any, error), error) { if !assertion.actualIsFunc { - return func() (interface{}, error) { return assertion.actual, nil }, nil + return func() (any, error) { return assertion.actual, nil }, nil } actualValue := reflect.ValueOf(assertion.actual) actualType := reflect.TypeOf(assertion.actual) @@ -301,7 +313,7 @@ func (assertion *AsyncAssertion) buildActualPoller() (func() (interface{}, error return nil, assertion.invalidMustPassRepeatedlyError("parameter can't be < 1") } - return func() (actual interface{}, err error) { + return func() (actual any, err error) { var values []reflect.Value assertionFailure = nil defer func() { @@ -354,14 +366,14 @@ func (assertion *AsyncAssertion) afterPolling() <-chan time.Time { } } -func (assertion *AsyncAssertion) matcherSaysStopTrying(matcher types.GomegaMatcher, value interface{}) bool { +func (assertion *AsyncAssertion) matcherSaysStopTrying(matcher types.GomegaMatcher, value any) bool { if assertion.actualIsFunc || types.MatchMayChangeInTheFuture(matcher, value) { return false } return true } -func (assertion *AsyncAssertion) pollMatcher(matcher types.GomegaMatcher, value interface{}) (matches bool, err error) { +func (assertion *AsyncAssertion) pollMatcher(matcher types.GomegaMatcher, value any) (matches bool, err error) { defer func() { if e := recover(); e != nil { if _, isAsyncError := AsPollingSignalError(e); isAsyncError { @@ -377,13 +389,13 @@ func (assertion *AsyncAssertion) pollMatcher(matcher types.GomegaMatcher, value return } -func (assertion *AsyncAssertion) match(matcher types.GomegaMatcher, desiredMatch bool, optionalDescription ...interface{}) bool { +func (assertion *AsyncAssertion) match(matcher types.GomegaMatcher, desiredMatch bool, optionalDescription ...any) bool { timer := time.Now() timeout := assertion.afterTimeout() lock := sync.Mutex{} var matches, hasLastValidActual bool - var actual, lastValidActual interface{} + var actual, lastValidActual any var actualErr, matcherErr error var oracleMatcherSaysStop bool diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/duration_bundle.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/duration_bundle.go index 2e026c336f2..1019deb88e4 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/duration_bundle.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/duration_bundle.go @@ -49,7 +49,7 @@ func durationFromEnv(key string, defaultDuration time.Duration) time.Duration { return duration } -func toDuration(input interface{}) (time.Duration, error) { +func toDuration(input any) (time.Duration, error) { duration, ok := input.(time.Duration) if ok { return duration, nil diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/gomega.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/gomega.go index c6e2fcc0ed4..66dfe7d0411 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/gomega.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/gomega.go @@ -40,45 +40,45 @@ func (g *Gomega) ConfigureWithT(t types.GomegaTestingT) *Gomega { return g } -func (g *Gomega) Ω(actual interface{}, extra ...interface{}) types.Assertion { +func (g *Gomega) Ω(actual any, extra ...any) types.Assertion { return g.ExpectWithOffset(0, actual, extra...) } -func (g *Gomega) Expect(actual interface{}, extra ...interface{}) types.Assertion { +func (g *Gomega) Expect(actual any, extra ...any) types.Assertion { return g.ExpectWithOffset(0, actual, extra...) } -func (g *Gomega) ExpectWithOffset(offset int, actual interface{}, extra ...interface{}) types.Assertion { +func (g *Gomega) ExpectWithOffset(offset int, actual any, extra ...any) types.Assertion { return NewAssertion(actual, g, offset, extra...) } -func (g *Gomega) Eventually(actualOrCtx interface{}, args ...interface{}) types.AsyncAssertion { +func (g *Gomega) Eventually(actualOrCtx any, args ...any) types.AsyncAssertion { return g.makeAsyncAssertion(AsyncAssertionTypeEventually, 0, actualOrCtx, args...) } -func (g *Gomega) EventuallyWithOffset(offset int, actualOrCtx interface{}, args ...interface{}) types.AsyncAssertion { +func (g *Gomega) EventuallyWithOffset(offset int, actualOrCtx any, args ...any) types.AsyncAssertion { return g.makeAsyncAssertion(AsyncAssertionTypeEventually, offset, actualOrCtx, args...) } -func (g *Gomega) Consistently(actualOrCtx interface{}, args ...interface{}) types.AsyncAssertion { +func (g *Gomega) Consistently(actualOrCtx any, args ...any) types.AsyncAssertion { return g.makeAsyncAssertion(AsyncAssertionTypeConsistently, 0, actualOrCtx, args...) } -func (g *Gomega) ConsistentlyWithOffset(offset int, actualOrCtx interface{}, args ...interface{}) types.AsyncAssertion { +func (g *Gomega) ConsistentlyWithOffset(offset int, actualOrCtx any, args ...any) types.AsyncAssertion { return g.makeAsyncAssertion(AsyncAssertionTypeConsistently, offset, actualOrCtx, args...) } -func (g *Gomega) makeAsyncAssertion(asyncAssertionType AsyncAssertionType, offset int, actualOrCtx interface{}, args ...interface{}) types.AsyncAssertion { +func (g *Gomega) makeAsyncAssertion(asyncAssertionType AsyncAssertionType, offset int, actualOrCtx any, args ...any) types.AsyncAssertion { baseOffset := 3 timeoutInterval := -time.Duration(1) pollingInterval := -time.Duration(1) - intervals := []interface{}{} + intervals := []any{} var ctx context.Context actual := actualOrCtx startingIndex := 0 if _, isCtx := actualOrCtx.(context.Context); isCtx && len(args) > 0 { - // the first argument is a context, we should accept it as the context _only if_ it is **not** the only argumnent **and** the second argument is not a parseable duration + // the first argument is a context, we should accept it as the context _only if_ it is **not** the only argument **and** the second argument is not a parseable duration // this is due to an unfortunate ambiguity in early version of Gomega in which multi-type durations are allowed after the actual if _, err := toDuration(args[0]); err != nil { ctx = actualOrCtx.(context.Context) diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/polling_signal_error.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/polling_signal_error.go index 3a4f7ddd90c..450c4033301 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/polling_signal_error.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/polling_signal_error.go @@ -100,7 +100,7 @@ func (s *PollingSignalErrorImpl) TryAgainDuration() time.Duration { return s.duration } -func AsPollingSignalError(actual interface{}) (*PollingSignalErrorImpl, bool) { +func AsPollingSignalError(actual any) (*PollingSignalErrorImpl, bool) { if actual == nil { return nil, false } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/vetoptdesc.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/vetoptdesc.go index f2958764171..b748de41f11 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/vetoptdesc.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/internal/vetoptdesc.go @@ -10,7 +10,7 @@ import ( // Gomega matcher at the beginning it panics. This allows for rendering Gomega // matchers as part of an optional Description, as long as they're not in the // first slot. -func vetOptionalDescription(assertion string, optionalDescription ...interface{}) { +func vetOptionalDescription(assertion string, optionalDescription ...any) { if len(optionalDescription) == 0 { return } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers.go index 7ef27dc9c95..10b6693fd63 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers.go @@ -12,7 +12,7 @@ import ( // Equal uses reflect.DeepEqual to compare actual with expected. Equal is strict about // types when performing comparisons. // It is an error for both actual and expected to be nil. Use BeNil() instead. -func Equal(expected interface{}) types.GomegaMatcher { +func Equal(expected any) types.GomegaMatcher { return &matchers.EqualMatcher{ Expected: expected, } @@ -22,7 +22,7 @@ func Equal(expected interface{}) types.GomegaMatcher { // This is done by converting actual to have the type of expected before // attempting equality with reflect.DeepEqual. // It is an error for actual and expected to be nil. Use BeNil() instead. -func BeEquivalentTo(expected interface{}) types.GomegaMatcher { +func BeEquivalentTo(expected any) types.GomegaMatcher { return &matchers.BeEquivalentToMatcher{ Expected: expected, } @@ -31,7 +31,7 @@ func BeEquivalentTo(expected interface{}) types.GomegaMatcher { // BeComparableTo uses gocmp.Equal from github.com/google/go-cmp (instead of reflect.DeepEqual) to perform a deep comparison. // You can pass cmp.Option as options. // It is an error for actual and expected to be nil. Use BeNil() instead. -func BeComparableTo(expected interface{}, opts ...cmp.Option) types.GomegaMatcher { +func BeComparableTo(expected any, opts ...cmp.Option) types.GomegaMatcher { return &matchers.BeComparableToMatcher{ Expected: expected, Options: opts, @@ -41,7 +41,7 @@ func BeComparableTo(expected interface{}, opts ...cmp.Option) types.GomegaMatche // BeIdenticalTo uses the == operator to compare actual with expected. // BeIdenticalTo is strict about types when performing comparisons. // It is an error for both actual and expected to be nil. Use BeNil() instead. -func BeIdenticalTo(expected interface{}) types.GomegaMatcher { +func BeIdenticalTo(expected any) types.GomegaMatcher { return &matchers.BeIdenticalToMatcher{ Expected: expected, } @@ -139,7 +139,7 @@ func Succeed() types.GomegaMatcher { // Error interface // // The optional second argument is a description of the error function, if used. This is required when passing a function but is ignored in all other cases. -func MatchError(expected interface{}, functionErrorDescription ...any) types.GomegaMatcher { +func MatchError(expected any, functionErrorDescription ...any) types.GomegaMatcher { return &matchers.MatchErrorMatcher{ Expected: expected, FuncErrDescription: functionErrorDescription, @@ -202,11 +202,11 @@ func BeClosed() types.GomegaMatcher { // Expect(myThing.IsValid()).Should(BeTrue()) // // Finally, if you want to match the received object as well as get the actual received value into a variable, so you can reason further about the value received, -// you can pass a pointer to a variable of the approriate type first, and second a matcher: +// you can pass a pointer to a variable of the appropriate type first, and second a matcher: // // var myThing thing // Eventually(thingChan).Should(Receive(&myThing, ContainSubstring("bar"))) -func Receive(args ...interface{}) types.GomegaMatcher { +func Receive(args ...any) types.GomegaMatcher { return &matchers.ReceiveMatcher{ Args: args, } @@ -224,7 +224,7 @@ func Receive(args ...interface{}) types.GomegaMatcher { // // Of course, the value is actually sent to the channel. The point of `BeSent` is less to make an assertion about the availability of the channel (which is typically an implementation detail that your test should not be concerned with). // Rather, the point of `BeSent` is to make it possible to easily and expressively write tests that can timeout on blocked channel sends. -func BeSent(arg interface{}) types.GomegaMatcher { +func BeSent(arg any) types.GomegaMatcher { return &matchers.BeSentMatcher{ Arg: arg, } @@ -233,7 +233,7 @@ func BeSent(arg interface{}) types.GomegaMatcher { // MatchRegexp succeeds if actual is a string or stringer that matches the // passed-in regexp. Optional arguments can be provided to construct a regexp // via fmt.Sprintf(). -func MatchRegexp(regexp string, args ...interface{}) types.GomegaMatcher { +func MatchRegexp(regexp string, args ...any) types.GomegaMatcher { return &matchers.MatchRegexpMatcher{ Regexp: regexp, Args: args, @@ -243,7 +243,7 @@ func MatchRegexp(regexp string, args ...interface{}) types.GomegaMatcher { // ContainSubstring succeeds if actual is a string or stringer that contains the // passed-in substring. Optional arguments can be provided to construct the substring // via fmt.Sprintf(). -func ContainSubstring(substr string, args ...interface{}) types.GomegaMatcher { +func ContainSubstring(substr string, args ...any) types.GomegaMatcher { return &matchers.ContainSubstringMatcher{ Substr: substr, Args: args, @@ -253,7 +253,7 @@ func ContainSubstring(substr string, args ...interface{}) types.GomegaMatcher { // HavePrefix succeeds if actual is a string or stringer that contains the // passed-in string as a prefix. Optional arguments can be provided to construct // via fmt.Sprintf(). -func HavePrefix(prefix string, args ...interface{}) types.GomegaMatcher { +func HavePrefix(prefix string, args ...any) types.GomegaMatcher { return &matchers.HavePrefixMatcher{ Prefix: prefix, Args: args, @@ -263,7 +263,7 @@ func HavePrefix(prefix string, args ...interface{}) types.GomegaMatcher { // HaveSuffix succeeds if actual is a string or stringer that contains the // passed-in string as a suffix. Optional arguments can be provided to construct // via fmt.Sprintf(). -func HaveSuffix(suffix string, args ...interface{}) types.GomegaMatcher { +func HaveSuffix(suffix string, args ...any) types.GomegaMatcher { return &matchers.HaveSuffixMatcher{ Suffix: suffix, Args: args, @@ -273,7 +273,7 @@ func HaveSuffix(suffix string, args ...interface{}) types.GomegaMatcher { // MatchJSON succeeds if actual is a string or stringer of JSON that matches // the expected JSON. The JSONs are decoded and the resulting objects are compared via // reflect.DeepEqual so things like key-ordering and whitespace shouldn't matter. -func MatchJSON(json interface{}) types.GomegaMatcher { +func MatchJSON(json any) types.GomegaMatcher { return &matchers.MatchJSONMatcher{ JSONToMatch: json, } @@ -282,7 +282,7 @@ func MatchJSON(json interface{}) types.GomegaMatcher { // MatchXML succeeds if actual is a string or stringer of XML that matches // the expected XML. The XMLs are decoded and the resulting objects are compared via // reflect.DeepEqual so things like whitespaces shouldn't matter. -func MatchXML(xml interface{}) types.GomegaMatcher { +func MatchXML(xml any) types.GomegaMatcher { return &matchers.MatchXMLMatcher{ XMLToMatch: xml, } @@ -291,7 +291,7 @@ func MatchXML(xml interface{}) types.GomegaMatcher { // MatchYAML succeeds if actual is a string or stringer of YAML that matches // the expected YAML. The YAML's are decoded and the resulting objects are compared via // reflect.DeepEqual so things like key-ordering and whitespace shouldn't matter. -func MatchYAML(yaml interface{}) types.GomegaMatcher { +func MatchYAML(yaml any) types.GomegaMatcher { return &matchers.MatchYAMLMatcher{ YAMLToMatch: yaml, } @@ -338,7 +338,7 @@ func BeZero() types.GomegaMatcher { // // var findings []string // Expect([]string{"Foo", "FooBar"}).Should(ContainElement(ContainSubString("Bar", &findings))) -func ContainElement(element interface{}, result ...interface{}) types.GomegaMatcher { +func ContainElement(element any, result ...any) types.GomegaMatcher { return &matchers.ContainElementMatcher{ Element: element, Result: result, @@ -358,7 +358,7 @@ func ContainElement(element interface{}, result ...interface{}) types.GomegaMatc // Expect(2).Should(BeElementOf(1, 2)) // // Actual must be typed. -func BeElementOf(elements ...interface{}) types.GomegaMatcher { +func BeElementOf(elements ...any) types.GomegaMatcher { return &matchers.BeElementOfMatcher{ Elements: elements, } @@ -368,7 +368,7 @@ func BeElementOf(elements ...interface{}) types.GomegaMatcher { // BeKeyOf() always uses Equal() to perform the match between actual and the map keys. // // Expect("foo").Should(BeKeyOf(map[string]bool{"foo": true, "bar": false})) -func BeKeyOf(element interface{}) types.GomegaMatcher { +func BeKeyOf(element any) types.GomegaMatcher { return &matchers.BeKeyOfMatcher{ Map: element, } @@ -388,14 +388,14 @@ func BeKeyOf(element interface{}) types.GomegaMatcher { // // Expect([]string{"Foo", "FooBar"}).Should(ConsistOf([]string{"FooBar", "Foo"})) // -// Note that Go's type system does not allow you to write this as ConsistOf([]string{"FooBar", "Foo"}...) as []string and []interface{} are different types - hence the need for this special rule. -func ConsistOf(elements ...interface{}) types.GomegaMatcher { +// Note that Go's type system does not allow you to write this as ConsistOf([]string{"FooBar", "Foo"}...) as []string and []any are different types - hence the need for this special rule. +func ConsistOf(elements ...any) types.GomegaMatcher { return &matchers.ConsistOfMatcher{ Elements: elements, } } -// HaveExactElements succeeds if actual contains elements that precisely match the elemets passed into the matcher. The ordering of the elements does matter. +// HaveExactElements succeeds if actual contains elements that precisely match the elements passed into the matcher. The ordering of the elements does matter. // By default HaveExactElements() uses Equal() to match the elements, however custom matchers can be passed in instead. Here are some examples: // // Expect([]string{"Foo", "FooBar"}).Should(HaveExactElements("Foo", "FooBar")) @@ -403,7 +403,7 @@ func ConsistOf(elements ...interface{}) types.GomegaMatcher { // Expect([]string{"Foo", "FooBar"}).Should(HaveExactElements(ContainSubstring("Foo"), ContainSubstring("Foo"))) // // Actual must be an array or slice. -func HaveExactElements(elements ...interface{}) types.GomegaMatcher { +func HaveExactElements(elements ...any) types.GomegaMatcher { return &matchers.HaveExactElementsMatcher{ Elements: elements, } @@ -417,7 +417,7 @@ func HaveExactElements(elements ...interface{}) types.GomegaMatcher { // // Actual must be an array, slice or map. // For maps, ContainElements searches through the map's values. -func ContainElements(elements ...interface{}) types.GomegaMatcher { +func ContainElements(elements ...any) types.GomegaMatcher { return &matchers.ContainElementsMatcher{ Elements: elements, } @@ -432,7 +432,7 @@ func ContainElements(elements ...interface{}) types.GomegaMatcher { // // Actual must be an array, slice or map. // For maps, HaveEach searches through the map's values. -func HaveEach(element interface{}) types.GomegaMatcher { +func HaveEach(element any) types.GomegaMatcher { return &matchers.HaveEachMatcher{ Element: element, } @@ -443,7 +443,7 @@ func HaveEach(element interface{}) types.GomegaMatcher { // matcher can be passed in instead: // // Expect(map[string]string{"Foo": "Bar", "BazFoo": "Duck"}).Should(HaveKey(MatchRegexp(`.+Foo$`))) -func HaveKey(key interface{}) types.GomegaMatcher { +func HaveKey(key any) types.GomegaMatcher { return &matchers.HaveKeyMatcher{ Key: key, } @@ -455,7 +455,7 @@ func HaveKey(key interface{}) types.GomegaMatcher { // // Expect(map[string]string{"Foo": "Bar", "BazFoo": "Duck"}).Should(HaveKeyWithValue("Foo", "Bar")) // Expect(map[string]string{"Foo": "Bar", "BazFoo": "Duck"}).Should(HaveKeyWithValue(MatchRegexp(`.+Foo$`), "Bar")) -func HaveKeyWithValue(key interface{}, value interface{}) types.GomegaMatcher { +func HaveKeyWithValue(key any, value any) types.GomegaMatcher { return &matchers.HaveKeyWithValueMatcher{ Key: key, Value: value, @@ -483,7 +483,7 @@ func HaveKeyWithValue(key interface{}, value interface{}) types.GomegaMatcher { // Expect(book).To(HaveField("Title", ContainSubstring("Les")) // Expect(book).To(HaveField("Author.FirstName", Equal("Victor")) // Expect(book).To(HaveField("Author.DOB.Year()", BeNumerically("<", 1900)) -func HaveField(field string, expected interface{}) types.GomegaMatcher { +func HaveField(field string, expected any) types.GomegaMatcher { return &matchers.HaveFieldMatcher{ Field: field, Expected: expected, @@ -535,7 +535,7 @@ func HaveValue(matcher types.GomegaMatcher) types.GomegaMatcher { // Expect(1.0).Should(BeNumerically(">=", 1.0)) // Expect(1.0).Should(BeNumerically("<", 3)) // Expect(1.0).Should(BeNumerically("<=", 1.0)) -func BeNumerically(comparator string, compareTo ...interface{}) types.GomegaMatcher { +func BeNumerically(comparator string, compareTo ...any) types.GomegaMatcher { return &matchers.BeNumericallyMatcher{ Comparator: comparator, CompareTo: compareTo, @@ -562,7 +562,7 @@ func BeTemporally(comparator string, compareTo time.Time, threshold ...time.Dura // Expect(5).Should(BeAssignableToTypeOf(-1)) // different values same type // Expect("foo").Should(BeAssignableToTypeOf("bar")) // different values same type // Expect(struct{ Foo string }{}).Should(BeAssignableToTypeOf(struct{ Foo string }{})) -func BeAssignableToTypeOf(expected interface{}) types.GomegaMatcher { +func BeAssignableToTypeOf(expected any) types.GomegaMatcher { return &matchers.AssignableToTypeOfMatcher{ Expected: expected, } @@ -581,7 +581,7 @@ func Panic() types.GomegaMatcher { // matcher can be passed in instead: // // Expect(fn).Should(PanicWith(MatchRegexp(`.+Foo$`))) -func PanicWith(expected interface{}) types.GomegaMatcher { +func PanicWith(expected any) types.GomegaMatcher { return &matchers.PanicMatcher{Expected: expected} } @@ -610,7 +610,7 @@ func BeADirectory() types.GomegaMatcher { // Expect(resp).Should(HaveHTTPStatus(http.StatusOK)) // asserts that resp.StatusCode == 200 // Expect(resp).Should(HaveHTTPStatus("404 Not Found")) // asserts that resp.Status == "404 Not Found" // Expect(resp).Should(HaveHTTPStatus(http.StatusOK, http.StatusNoContent)) // asserts that resp.StatusCode == 200 || resp.StatusCode == 204 -func HaveHTTPStatus(expected ...interface{}) types.GomegaMatcher { +func HaveHTTPStatus(expected ...any) types.GomegaMatcher { return &matchers.HaveHTTPStatusMatcher{Expected: expected} } @@ -618,7 +618,7 @@ func HaveHTTPStatus(expected ...interface{}) types.GomegaMatcher { // Actual must be either a *http.Response or *httptest.ResponseRecorder. // Expected must be a string header name, followed by a header value which // can be a string, or another matcher. -func HaveHTTPHeaderWithValue(header string, value interface{}) types.GomegaMatcher { +func HaveHTTPHeaderWithValue(header string, value any) types.GomegaMatcher { return &matchers.HaveHTTPHeaderWithValueMatcher{ Header: header, Value: value, @@ -628,7 +628,7 @@ func HaveHTTPHeaderWithValue(header string, value interface{}) types.GomegaMatch // HaveHTTPBody matches if the body matches. // Actual must be either a *http.Response or *httptest.ResponseRecorder. // Expected must be either a string, []byte, or other matcher -func HaveHTTPBody(expected interface{}) types.GomegaMatcher { +func HaveHTTPBody(expected any) types.GomegaMatcher { return &matchers.HaveHTTPBodyMatcher{Expected: expected} } @@ -687,15 +687,15 @@ func Not(matcher types.GomegaMatcher) types.GomegaMatcher { // Expect(1).To(WithTransform(failingplus1, Equal(2))) // // And(), Or(), Not() and WithTransform() allow matchers to be composed into complex expressions. -func WithTransform(transform interface{}, matcher types.GomegaMatcher) types.GomegaMatcher { +func WithTransform(transform any, matcher types.GomegaMatcher) types.GomegaMatcher { return matchers.NewWithTransformMatcher(transform, matcher) } // Satisfy matches the actual value against the `predicate` function. -// The given predicate must be a function of one paramter that returns bool. +// The given predicate must be a function of one parameter that returns bool. // // var isEven = func(i int) bool { return i%2 == 0 } // Expect(2).To(Satisfy(isEven)) -func Satisfy(predicate interface{}) types.GomegaMatcher { +func Satisfy(predicate any) types.GomegaMatcher { return matchers.NewSatisfyMatcher(predicate) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/and.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/and.go index 6bd826adc5c..db48e90b376 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/and.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/and.go @@ -14,7 +14,7 @@ type AndMatcher struct { firstFailedMatcher types.GomegaMatcher } -func (m *AndMatcher) Match(actual interface{}) (success bool, err error) { +func (m *AndMatcher) Match(actual any) (success bool, err error) { m.firstFailedMatcher = nil for _, matcher := range m.Matchers { success, err := matcher.Match(actual) @@ -26,16 +26,16 @@ func (m *AndMatcher) Match(actual interface{}) (success bool, err error) { return true, nil } -func (m *AndMatcher) FailureMessage(actual interface{}) (message string) { +func (m *AndMatcher) FailureMessage(actual any) (message string) { return m.firstFailedMatcher.FailureMessage(actual) } -func (m *AndMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (m *AndMatcher) NegatedFailureMessage(actual any) (message string) { // not the most beautiful list of matchers, but not bad either... return format.Message(actual, fmt.Sprintf("To not satisfy all of these matchers: %s", m.Matchers)) } -func (m *AndMatcher) MatchMayChangeInTheFuture(actual interface{}) bool { +func (m *AndMatcher) MatchMayChangeInTheFuture(actual any) bool { /* Example with 3 matchers: A, B, C diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/assignable_to_type_of_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/assignable_to_type_of_matcher.go index be483952018..a100e5c07e8 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/assignable_to_type_of_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/assignable_to_type_of_matcher.go @@ -10,10 +10,10 @@ import ( ) type AssignableToTypeOfMatcher struct { - Expected interface{} + Expected any } -func (matcher *AssignableToTypeOfMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *AssignableToTypeOfMatcher) Match(actual any) (success bool, err error) { if actual == nil && matcher.Expected == nil { return false, fmt.Errorf("Refusing to compare to .\nBe explicit and use BeNil() instead. This is to avoid mistakes where both sides of an assertion are erroneously uninitialized.") } else if matcher.Expected == nil { @@ -28,10 +28,10 @@ func (matcher *AssignableToTypeOfMatcher) Match(actual interface{}) (success boo return actualType.AssignableTo(expectedType), nil } -func (matcher *AssignableToTypeOfMatcher) FailureMessage(actual interface{}) string { +func (matcher *AssignableToTypeOfMatcher) FailureMessage(actual any) string { return format.Message(actual, fmt.Sprintf("to be assignable to the type: %T", matcher.Expected)) } -func (matcher *AssignableToTypeOfMatcher) NegatedFailureMessage(actual interface{}) string { +func (matcher *AssignableToTypeOfMatcher) NegatedFailureMessage(actual any) string { return format.Message(actual, fmt.Sprintf("not to be assignable to the type: %T", matcher.Expected)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_directory.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_directory.go index 93d4497c705..1d823604842 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_directory.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_directory.go @@ -24,11 +24,11 @@ func (t notADirectoryError) Error() string { } type BeADirectoryMatcher struct { - expected interface{} + expected any err error } -func (matcher *BeADirectoryMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeADirectoryMatcher) Match(actual any) (success bool, err error) { actualFilename, ok := actual.(string) if !ok { return false, fmt.Errorf("BeADirectoryMatcher matcher expects a file path") @@ -47,10 +47,10 @@ func (matcher *BeADirectoryMatcher) Match(actual interface{}) (success bool, err return true, nil } -func (matcher *BeADirectoryMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeADirectoryMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, fmt.Sprintf("to be a directory: %s", matcher.err)) } -func (matcher *BeADirectoryMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeADirectoryMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not be a directory") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_regular_file.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_regular_file.go index 8fefc4deb7a..3e53d6285b5 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_regular_file.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_a_regular_file.go @@ -24,11 +24,11 @@ func (t notARegularFileError) Error() string { } type BeARegularFileMatcher struct { - expected interface{} + expected any err error } -func (matcher *BeARegularFileMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeARegularFileMatcher) Match(actual any) (success bool, err error) { actualFilename, ok := actual.(string) if !ok { return false, fmt.Errorf("BeARegularFileMatcher matcher expects a file path") @@ -47,10 +47,10 @@ func (matcher *BeARegularFileMatcher) Match(actual interface{}) (success bool, e return true, nil } -func (matcher *BeARegularFileMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeARegularFileMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, fmt.Sprintf("to be a regular file: %s", matcher.err)) } -func (matcher *BeARegularFileMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeARegularFileMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not be a regular file") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_an_existing_file.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_an_existing_file.go index e2bdd28113b..04f156db394 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_an_existing_file.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_an_existing_file.go @@ -10,10 +10,10 @@ import ( ) type BeAnExistingFileMatcher struct { - expected interface{} + expected any } -func (matcher *BeAnExistingFileMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeAnExistingFileMatcher) Match(actual any) (success bool, err error) { actualFilename, ok := actual.(string) if !ok { return false, fmt.Errorf("BeAnExistingFileMatcher matcher expects a file path") @@ -31,10 +31,10 @@ func (matcher *BeAnExistingFileMatcher) Match(actual interface{}) (success bool, return true, nil } -func (matcher *BeAnExistingFileMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeAnExistingFileMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to exist") } -func (matcher *BeAnExistingFileMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeAnExistingFileMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to exist") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_closed_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_closed_matcher.go index f13c24490f8..4319dde4551 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_closed_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_closed_matcher.go @@ -12,7 +12,7 @@ import ( type BeClosedMatcher struct { } -func (matcher *BeClosedMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeClosedMatcher) Match(actual any) (success bool, err error) { if !isChan(actual) { return false, fmt.Errorf("BeClosed matcher expects a channel. Got:\n%s", format.Object(actual, 1)) } @@ -39,10 +39,10 @@ func (matcher *BeClosedMatcher) Match(actual interface{}) (success bool, err err return closed, nil } -func (matcher *BeClosedMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeClosedMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be closed") } -func (matcher *BeClosedMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeClosedMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "to be open") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_comparable_to_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_comparable_to_matcher.go index 4e3897858c7..532fc374491 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_comparable_to_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_comparable_to_matcher.go @@ -9,11 +9,11 @@ import ( ) type BeComparableToMatcher struct { - Expected interface{} + Expected any Options cmp.Options } -func (matcher *BeComparableToMatcher) Match(actual interface{}) (success bool, matchErr error) { +func (matcher *BeComparableToMatcher) Match(actual any) (success bool, matchErr error) { if actual == nil && matcher.Expected == nil { return false, fmt.Errorf("Refusing to compare to .\nBe explicit and use BeNil() instead. This is to avoid mistakes where both sides of an assertion are erroneously uninitialized.") } @@ -40,10 +40,10 @@ func (matcher *BeComparableToMatcher) Match(actual interface{}) (success bool, m return cmp.Equal(actual, matcher.Expected, matcher.Options...), nil } -func (matcher *BeComparableToMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeComparableToMatcher) FailureMessage(actual any) (message string) { return fmt.Sprint("Expected object to be comparable, diff: ", cmp.Diff(actual, matcher.Expected, matcher.Options...)) } -func (matcher *BeComparableToMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeComparableToMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be comparable to", matcher.Expected) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_element_of_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_element_of_matcher.go index 9ee75a5d511..406fe54843b 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_element_of_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_element_of_matcher.go @@ -10,10 +10,10 @@ import ( ) type BeElementOfMatcher struct { - Elements []interface{} + Elements []any } -func (matcher *BeElementOfMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeElementOfMatcher) Match(actual any) (success bool, err error) { if reflect.TypeOf(actual) == nil { return false, fmt.Errorf("BeElement matcher expects actual to be typed") } @@ -34,10 +34,10 @@ func (matcher *BeElementOfMatcher) Match(actual interface{}) (success bool, err return false, lastError } -func (matcher *BeElementOfMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeElementOfMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be an element of", presentable(matcher.Elements)) } -func (matcher *BeElementOfMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeElementOfMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be an element of", presentable(matcher.Elements)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_empty_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_empty_matcher.go index bd7f0b96e7f..e9e0644f32e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_empty_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_empty_matcher.go @@ -13,7 +13,7 @@ import ( type BeEmptyMatcher struct { } -func (matcher *BeEmptyMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeEmptyMatcher) Match(actual any) (success bool, err error) { // short-circuit the iterator case, as we only need to see the first // element, if any. if miter.IsIter(actual) { @@ -34,10 +34,10 @@ func (matcher *BeEmptyMatcher) Match(actual interface{}) (success bool, err erro return length == 0, nil } -func (matcher *BeEmptyMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeEmptyMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be empty") } -func (matcher *BeEmptyMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeEmptyMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be empty") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_equivalent_to_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_equivalent_to_matcher.go index 263627f4083..37b3080ba77 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_equivalent_to_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_equivalent_to_matcher.go @@ -10,10 +10,10 @@ import ( ) type BeEquivalentToMatcher struct { - Expected interface{} + Expected any } -func (matcher *BeEquivalentToMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeEquivalentToMatcher) Match(actual any) (success bool, err error) { if actual == nil && matcher.Expected == nil { return false, fmt.Errorf("Both actual and expected must not be nil.") } @@ -27,10 +27,10 @@ func (matcher *BeEquivalentToMatcher) Match(actual interface{}) (success bool, e return reflect.DeepEqual(convertedActual, matcher.Expected), nil } -func (matcher *BeEquivalentToMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeEquivalentToMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be equivalent to", matcher.Expected) } -func (matcher *BeEquivalentToMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeEquivalentToMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be equivalent to", matcher.Expected) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_false_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_false_matcher.go index 8ee2b1c51e7..55e869515af 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_false_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_false_matcher.go @@ -12,7 +12,7 @@ type BeFalseMatcher struct { Reason string } -func (matcher *BeFalseMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeFalseMatcher) Match(actual any) (success bool, err error) { if !isBool(actual) { return false, fmt.Errorf("Expected a boolean. Got:\n%s", format.Object(actual, 1)) } @@ -20,7 +20,7 @@ func (matcher *BeFalseMatcher) Match(actual interface{}) (success bool, err erro return actual == false, nil } -func (matcher *BeFalseMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeFalseMatcher) FailureMessage(actual any) (message string) { if matcher.Reason == "" { return format.Message(actual, "to be false") } else { @@ -28,7 +28,7 @@ func (matcher *BeFalseMatcher) FailureMessage(actual interface{}) (message strin } } -func (matcher *BeFalseMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeFalseMatcher) NegatedFailureMessage(actual any) (message string) { if matcher.Reason == "" { return format.Message(actual, "not to be false") } else { diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_identical_to.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_identical_to.go index 631ce11e33b..579aa41b313 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_identical_to.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_identical_to.go @@ -10,10 +10,10 @@ import ( ) type BeIdenticalToMatcher struct { - Expected interface{} + Expected any } -func (matcher *BeIdenticalToMatcher) Match(actual interface{}) (success bool, matchErr error) { +func (matcher *BeIdenticalToMatcher) Match(actual any) (success bool, matchErr error) { if actual == nil && matcher.Expected == nil { return false, fmt.Errorf("Refusing to compare to .\nBe explicit and use BeNil() instead. This is to avoid mistakes where both sides of an assertion are erroneously uninitialized.") } @@ -30,10 +30,10 @@ func (matcher *BeIdenticalToMatcher) Match(actual interface{}) (success bool, ma return actual == matcher.Expected, nil } -func (matcher *BeIdenticalToMatcher) FailureMessage(actual interface{}) string { +func (matcher *BeIdenticalToMatcher) FailureMessage(actual any) string { return format.Message(actual, "to be identical to", matcher.Expected) } -func (matcher *BeIdenticalToMatcher) NegatedFailureMessage(actual interface{}) string { +func (matcher *BeIdenticalToMatcher) NegatedFailureMessage(actual any) string { return format.Message(actual, "not to be identical to", matcher.Expected) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_key_of_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_key_of_matcher.go index 449a291ef9a..3fff3df784b 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_key_of_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_key_of_matcher.go @@ -8,10 +8,10 @@ import ( ) type BeKeyOfMatcher struct { - Map interface{} + Map any } -func (matcher *BeKeyOfMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeKeyOfMatcher) Match(actual any) (success bool, err error) { if !isMap(matcher.Map) { return false, fmt.Errorf("BeKeyOf matcher needs expected to be a map type") } @@ -36,10 +36,10 @@ func (matcher *BeKeyOfMatcher) Match(actual interface{}) (success bool, err erro return false, lastError } -func (matcher *BeKeyOfMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeKeyOfMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be a key of", presentable(valuesOf(matcher.Map))) } -func (matcher *BeKeyOfMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeKeyOfMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be a key of", presentable(valuesOf(matcher.Map))) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_nil_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_nil_matcher.go index 551d99d7474..cab37f4f957 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_nil_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_nil_matcher.go @@ -7,14 +7,14 @@ import "github.com/onsi/gomega/format" type BeNilMatcher struct { } -func (matcher *BeNilMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeNilMatcher) Match(actual any) (success bool, err error) { return isNil(actual), nil } -func (matcher *BeNilMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeNilMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be nil") } -func (matcher *BeNilMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeNilMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be nil") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_numerically_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_numerically_matcher.go index 100735de325..7e6ce154e1e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_numerically_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_numerically_matcher.go @@ -11,18 +11,18 @@ import ( type BeNumericallyMatcher struct { Comparator string - CompareTo []interface{} + CompareTo []any } -func (matcher *BeNumericallyMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeNumericallyMatcher) FailureMessage(actual any) (message string) { return matcher.FormatFailureMessage(actual, false) } -func (matcher *BeNumericallyMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeNumericallyMatcher) NegatedFailureMessage(actual any) (message string) { return matcher.FormatFailureMessage(actual, true) } -func (matcher *BeNumericallyMatcher) FormatFailureMessage(actual interface{}, negated bool) (message string) { +func (matcher *BeNumericallyMatcher) FormatFailureMessage(actual any, negated bool) (message string) { if len(matcher.CompareTo) == 1 { message = fmt.Sprintf("to be %s", matcher.Comparator) } else { @@ -34,7 +34,7 @@ func (matcher *BeNumericallyMatcher) FormatFailureMessage(actual interface{}, ne return format.Message(actual, message, matcher.CompareTo[0]) } -func (matcher *BeNumericallyMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeNumericallyMatcher) Match(actual any) (success bool, err error) { if len(matcher.CompareTo) == 0 || len(matcher.CompareTo) > 2 { return false, fmt.Errorf("BeNumerically requires 1 or 2 CompareTo arguments. Got:\n%s", format.Object(matcher.CompareTo, 1)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_sent_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_sent_matcher.go index cf582a3fcbd..14ffbf6c4c0 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_sent_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_sent_matcher.go @@ -10,11 +10,11 @@ import ( ) type BeSentMatcher struct { - Arg interface{} + Arg any channelClosed bool } -func (matcher *BeSentMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeSentMatcher) Match(actual any) (success bool, err error) { if !isChan(actual) { return false, fmt.Errorf("BeSent expects a channel. Got:\n%s", format.Object(actual, 1)) } @@ -56,15 +56,15 @@ func (matcher *BeSentMatcher) Match(actual interface{}) (success bool, err error return didSend, nil } -func (matcher *BeSentMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeSentMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to send:", matcher.Arg) } -func (matcher *BeSentMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeSentMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to send:", matcher.Arg) } -func (matcher *BeSentMatcher) MatchMayChangeInTheFuture(actual interface{}) bool { +func (matcher *BeSentMatcher) MatchMayChangeInTheFuture(actual any) bool { if !isChan(actual) { return false } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_temporally_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_temporally_matcher.go index dec4db024e4..edb647c6f22 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_temporally_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_temporally_matcher.go @@ -15,17 +15,17 @@ type BeTemporallyMatcher struct { Threshold []time.Duration } -func (matcher *BeTemporallyMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeTemporallyMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, fmt.Sprintf("to be %s", matcher.Comparator), matcher.CompareTo) } -func (matcher *BeTemporallyMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeTemporallyMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, fmt.Sprintf("not to be %s", matcher.Comparator), matcher.CompareTo) } -func (matcher *BeTemporallyMatcher) Match(actual interface{}) (bool, error) { +func (matcher *BeTemporallyMatcher) Match(actual any) (bool, error) { // predicate to test for time.Time type - isTime := func(t interface{}) bool { + isTime := func(t any) bool { _, ok := t.(time.Time) return ok } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_true_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_true_matcher.go index 3576aac884e..a010bec5ad6 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_true_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_true_matcher.go @@ -12,7 +12,7 @@ type BeTrueMatcher struct { Reason string } -func (matcher *BeTrueMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeTrueMatcher) Match(actual any) (success bool, err error) { if !isBool(actual) { return false, fmt.Errorf("Expected a boolean. Got:\n%s", format.Object(actual, 1)) } @@ -20,7 +20,7 @@ func (matcher *BeTrueMatcher) Match(actual interface{}) (success bool, err error return actual.(bool), nil } -func (matcher *BeTrueMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeTrueMatcher) FailureMessage(actual any) (message string) { if matcher.Reason == "" { return format.Message(actual, "to be true") } else { @@ -28,7 +28,7 @@ func (matcher *BeTrueMatcher) FailureMessage(actual interface{}) (message string } } -func (matcher *BeTrueMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeTrueMatcher) NegatedFailureMessage(actual any) (message string) { if matcher.Reason == "" { return format.Message(actual, "not to be true") } else { diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_zero_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_zero_matcher.go index 26196f168f4..f5f5d7f7d77 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_zero_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/be_zero_matcher.go @@ -9,7 +9,7 @@ import ( type BeZeroMatcher struct { } -func (matcher *BeZeroMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *BeZeroMatcher) Match(actual any) (success bool, err error) { if actual == nil { return true, nil } @@ -19,10 +19,10 @@ func (matcher *BeZeroMatcher) Match(actual interface{}) (success bool, err error } -func (matcher *BeZeroMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *BeZeroMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to be zero-valued") } -func (matcher *BeZeroMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *BeZeroMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to be zero-valued") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/consist_of.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/consist_of.go index a111881825b..05c751b6649 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/consist_of.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/consist_of.go @@ -12,12 +12,12 @@ import ( ) type ConsistOfMatcher struct { - Elements []interface{} - missingElements []interface{} - extraElements []interface{} + Elements []any + missingElements []any + extraElements []any } -func (matcher *ConsistOfMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *ConsistOfMatcher) Match(actual any) (success bool, err error) { if !isArrayOrSlice(actual) && !isMap(actual) && !miter.IsIter(actual) { return false, fmt.Errorf("ConsistOf matcher expects an array/slice/map/iter.Seq/iter.Seq2. Got:\n%s", format.Object(actual, 1)) } @@ -35,19 +35,19 @@ func (matcher *ConsistOfMatcher) Match(actual interface{}) (success bool, err er return true, nil } - var missingMatchers []interface{} + var missingMatchers []any matcher.extraElements, missingMatchers = bipartiteGraph.FreeLeftRight(edges) matcher.missingElements = equalMatchersToElements(missingMatchers) return false, nil } -func neighbours(value, matcher interface{}) (bool, error) { +func neighbours(value, matcher any) (bool, error) { match, err := matcher.(omegaMatcher).Match(value) return match && err == nil, nil } -func equalMatchersToElements(matchers []interface{}) (elements []interface{}) { +func equalMatchersToElements(matchers []any) (elements []any) { for _, matcher := range matchers { if equalMatcher, ok := matcher.(*EqualMatcher); ok { elements = append(elements, equalMatcher.Expected) @@ -60,7 +60,7 @@ func equalMatchersToElements(matchers []interface{}) (elements []interface{}) { return } -func flatten(elems []interface{}) []interface{} { +func flatten(elems []any) []any { if len(elems) != 1 || !(isArrayOrSlice(elems[0]) || (miter.IsIter(elems[0]) && !miter.IsSeq2(elems[0]))) { @@ -77,14 +77,14 @@ func flatten(elems []interface{}) []interface{} { } value := reflect.ValueOf(elems[0]) - flattened := make([]interface{}, value.Len()) + flattened := make([]any, value.Len()) for i := 0; i < value.Len(); i++ { flattened[i] = value.Index(i).Interface() } return flattened } -func matchers(expectedElems []interface{}) (matchers []interface{}) { +func matchers(expectedElems []any) (matchers []any) { for _, e := range flatten(expectedElems) { if e == nil { matchers = append(matchers, &BeNilMatcher{}) @@ -97,11 +97,11 @@ func matchers(expectedElems []interface{}) (matchers []interface{}) { return } -func presentable(elems []interface{}) interface{} { +func presentable(elems []any) any { elems = flatten(elems) if len(elems) == 0 { - return []interface{}{} + return []any{} } sv := reflect.ValueOf(elems) @@ -125,9 +125,9 @@ func presentable(elems []interface{}) interface{} { return ss.Interface() } -func valuesOf(actual interface{}) []interface{} { +func valuesOf(actual any) []any { value := reflect.ValueOf(actual) - values := []interface{}{} + values := []any{} if miter.IsIter(actual) { if miter.IsSeq2(actual) { miter.IterateKV(actual, func(k, v reflect.Value) bool { @@ -154,7 +154,7 @@ func valuesOf(actual interface{}) []interface{} { return values } -func (matcher *ConsistOfMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *ConsistOfMatcher) FailureMessage(actual any) (message string) { message = format.Message(actual, "to consist of", presentable(matcher.Elements)) message = appendMissingElements(message, matcher.missingElements) if len(matcher.extraElements) > 0 { @@ -164,7 +164,7 @@ func (matcher *ConsistOfMatcher) FailureMessage(actual interface{}) (message str return } -func appendMissingElements(message string, missingElements []interface{}) string { +func appendMissingElements(message string, missingElements []any) string { if len(missingElements) == 0 { return message } @@ -172,6 +172,6 @@ func appendMissingElements(message string, missingElements []interface{}) string format.Object(presentable(missingElements), 1)) } -func (matcher *ConsistOfMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *ConsistOfMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to consist of", presentable(matcher.Elements)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_element_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_element_matcher.go index 830239c7b69..8337a5261c7 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_element_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_element_matcher.go @@ -12,11 +12,11 @@ import ( ) type ContainElementMatcher struct { - Element interface{} - Result []interface{} + Element any + Result []any } -func (matcher *ContainElementMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *ContainElementMatcher) Match(actual any) (success bool, err error) { if !isArrayOrSlice(actual) && !isMap(actual) && !miter.IsIter(actual) { return false, fmt.Errorf("ContainElement matcher expects an array/slice/map/iterator. Got:\n%s", format.Object(actual, 1)) } @@ -132,14 +132,14 @@ func (matcher *ContainElementMatcher) Match(actual interface{}) (success bool, e var lastError error if !miter.IsIter(actual) { - var valueAt func(int) interface{} + var valueAt func(int) any var foundAt func(int) // We're dealing with an array/slice/map, so in all cases we can iterate // over the elements in actual using indices (that can be considered // keys in case of maps). if isMap(actual) { keys := value.MapKeys() - valueAt = func(i int) interface{} { + valueAt = func(i int) any { return value.MapIndex(keys[i]).Interface() } if result.Kind() != reflect.Invalid { @@ -150,7 +150,7 @@ func (matcher *ContainElementMatcher) Match(actual interface{}) (success bool, e } } } else { - valueAt = func(i int) interface{} { + valueAt = func(i int) any { return value.Index(i).Interface() } if result.Kind() != reflect.Invalid { @@ -251,7 +251,7 @@ func (matcher *ContainElementMatcher) Match(actual interface{}) (success bool, e } // pick up any findings the test is interested in as it specified a non-nil - // result reference. However, the expection always is that there are at + // result reference. However, the expectation always is that there are at // least one or multiple findings. So, if a result is expected, but we had // no findings, then this is an error. findings := getFindings() @@ -284,10 +284,10 @@ func (matcher *ContainElementMatcher) Match(actual interface{}) (success bool, e return true, nil } -func (matcher *ContainElementMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *ContainElementMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to contain element matching", matcher.Element) } -func (matcher *ContainElementMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *ContainElementMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to contain element matching", matcher.Element) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_elements_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_elements_matcher.go index d9fcb8b8043..ce3041892b3 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_elements_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_elements_matcher.go @@ -9,11 +9,11 @@ import ( ) type ContainElementsMatcher struct { - Elements []interface{} - missingElements []interface{} + Elements []any + missingElements []any } -func (matcher *ContainElementsMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *ContainElementsMatcher) Match(actual any) (success bool, err error) { if !isArrayOrSlice(actual) && !isMap(actual) && !miter.IsIter(actual) { return false, fmt.Errorf("ContainElements matcher expects an array/slice/map/iter.Seq/iter.Seq2. Got:\n%s", format.Object(actual, 1)) } @@ -35,11 +35,11 @@ func (matcher *ContainElementsMatcher) Match(actual interface{}) (success bool, return false, nil } -func (matcher *ContainElementsMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *ContainElementsMatcher) FailureMessage(actual any) (message string) { message = format.Message(actual, "to contain elements", presentable(matcher.Elements)) return appendMissingElements(message, matcher.missingElements) } -func (matcher *ContainElementsMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *ContainElementsMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to contain elements", presentable(matcher.Elements)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_substring_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_substring_matcher.go index e725f8c2753..d9980ee26b2 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_substring_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/contain_substring_matcher.go @@ -11,10 +11,10 @@ import ( type ContainSubstringMatcher struct { Substr string - Args []interface{} + Args []any } -func (matcher *ContainSubstringMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *ContainSubstringMatcher) Match(actual any) (success bool, err error) { actualString, ok := toString(actual) if !ok { return false, fmt.Errorf("ContainSubstring matcher requires a string or stringer. Got:\n%s", format.Object(actual, 1)) @@ -31,10 +31,10 @@ func (matcher *ContainSubstringMatcher) stringToMatch() string { return stringToMatch } -func (matcher *ContainSubstringMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *ContainSubstringMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to contain substring", matcher.stringToMatch()) } -func (matcher *ContainSubstringMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *ContainSubstringMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to contain substring", matcher.stringToMatch()) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/equal_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/equal_matcher.go index befb7bdfd8f..4ad166157a6 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/equal_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/equal_matcher.go @@ -9,10 +9,10 @@ import ( ) type EqualMatcher struct { - Expected interface{} + Expected any } -func (matcher *EqualMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *EqualMatcher) Match(actual any) (success bool, err error) { if actual == nil && matcher.Expected == nil { return false, fmt.Errorf("Refusing to compare to .\nBe explicit and use BeNil() instead. This is to avoid mistakes where both sides of an assertion are erroneously uninitialized.") } @@ -27,7 +27,7 @@ func (matcher *EqualMatcher) Match(actual interface{}) (success bool, err error) return reflect.DeepEqual(actual, matcher.Expected), nil } -func (matcher *EqualMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *EqualMatcher) FailureMessage(actual any) (message string) { actualString, actualOK := actual.(string) expectedString, expectedOK := matcher.Expected.(string) if actualOK && expectedOK { @@ -37,6 +37,6 @@ func (matcher *EqualMatcher) FailureMessage(actual interface{}) (message string) return format.Message(actual, "to equal", matcher.Expected) } -func (matcher *EqualMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *EqualMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to equal", matcher.Expected) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_cap_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_cap_matcher.go index 9856752f13f..a4fcfc425a6 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_cap_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_cap_matcher.go @@ -12,7 +12,7 @@ type HaveCapMatcher struct { Count int } -func (matcher *HaveCapMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveCapMatcher) Match(actual any) (success bool, err error) { length, ok := capOf(actual) if !ok { return false, fmt.Errorf("HaveCap matcher expects a array/channel/slice. Got:\n%s", format.Object(actual, 1)) @@ -21,10 +21,10 @@ func (matcher *HaveCapMatcher) Match(actual interface{}) (success bool, err erro return length == matcher.Count, nil } -func (matcher *HaveCapMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveCapMatcher) FailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\nto have capacity %d", format.Object(actual, 1), matcher.Count) } -func (matcher *HaveCapMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveCapMatcher) NegatedFailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\nnot to have capacity %d", format.Object(actual, 1), matcher.Count) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_each_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_each_matcher.go index 4111f2b8673..4c45063bd8a 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_each_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_each_matcher.go @@ -9,10 +9,10 @@ import ( ) type HaveEachMatcher struct { - Element interface{} + Element any } -func (matcher *HaveEachMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveEachMatcher) Match(actual any) (success bool, err error) { if !isArrayOrSlice(actual) && !isMap(actual) && !miter.IsIter(actual) { return false, fmt.Errorf("HaveEach matcher expects an array/slice/map/iter.Seq/iter.Seq2. Got:\n%s", format.Object(actual, 1)) @@ -61,14 +61,14 @@ func (matcher *HaveEachMatcher) Match(actual interface{}) (success bool, err err format.Object(actual, 1)) } - var valueAt func(int) interface{} + var valueAt func(int) any if isMap(actual) { keys := value.MapKeys() - valueAt = func(i int) interface{} { + valueAt = func(i int) any { return value.MapIndex(keys[i]).Interface() } } else { - valueAt = func(i int) interface{} { + valueAt = func(i int) any { return value.Index(i).Interface() } } @@ -89,11 +89,11 @@ func (matcher *HaveEachMatcher) Match(actual interface{}) (success bool, err err } // FailureMessage returns a suitable failure message. -func (matcher *HaveEachMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveEachMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to contain element matching", matcher.Element) } // NegatedFailureMessage returns a suitable negated failure message. -func (matcher *HaveEachMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveEachMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to contain element matching", matcher.Element) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_exact_elements.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_exact_elements.go index 23799f1c6ff..8b2d297c574 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_exact_elements.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_exact_elements.go @@ -14,13 +14,13 @@ type mismatchFailure struct { } type HaveExactElementsMatcher struct { - Elements []interface{} + Elements []any mismatchFailures []mismatchFailure missingIndex int extraIndex int } -func (matcher *HaveExactElementsMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveExactElementsMatcher) Match(actual any) (success bool, err error) { matcher.resetState() if isMap(actual) || miter.IsSeq2(actual) { @@ -108,7 +108,7 @@ func (matcher *HaveExactElementsMatcher) Match(actual interface{}) (success bool return success, nil } -func (matcher *HaveExactElementsMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveExactElementsMatcher) FailureMessage(actual any) (message string) { message = format.Message(actual, "to have exact elements with", presentable(matcher.Elements)) if matcher.missingIndex > 0 { message = fmt.Sprintf("%s\nthe missing elements start from index %d", message, matcher.missingIndex) @@ -125,7 +125,7 @@ func (matcher *HaveExactElementsMatcher) FailureMessage(actual interface{}) (mes return } -func (matcher *HaveExactElementsMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveExactElementsMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to contain elements", presentable(matcher.Elements)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_existing_field_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_existing_field_matcher.go index b57018745fa..a5a028e9a6a 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_existing_field_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_existing_field_matcher.go @@ -11,7 +11,7 @@ type HaveExistingFieldMatcher struct { Field string } -func (matcher *HaveExistingFieldMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveExistingFieldMatcher) Match(actual any) (success bool, err error) { // we don't care about the field's actual value, just about any error in // trying to find the field (or method). _, err = extractField(actual, matcher.Field, "HaveExistingField") @@ -27,10 +27,10 @@ func (matcher *HaveExistingFieldMatcher) Match(actual interface{}) (success bool return false, err } -func (matcher *HaveExistingFieldMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveExistingFieldMatcher) FailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\nto have field '%s'", format.Object(actual, 1), matcher.Field) } -func (matcher *HaveExistingFieldMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveExistingFieldMatcher) NegatedFailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\nnot to have field '%s'", format.Object(actual, 1), matcher.Field) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_field.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_field.go index 293457e85e3..d9fbeaf7522 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_field.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_field.go @@ -17,7 +17,7 @@ func (e missingFieldError) Error() string { return string(e) } -func extractField(actual interface{}, field string, matchername string) (any, error) { +func extractField(actual any, field string, matchername string) (any, error) { fields := strings.SplitN(field, ".", 2) actualValue := reflect.ValueOf(actual) @@ -68,7 +68,7 @@ func extractField(actual interface{}, field string, matchername string) (any, er type HaveFieldMatcher struct { Field string - Expected interface{} + Expected any } func (matcher *HaveFieldMatcher) expectedMatcher() omegaMatcher { @@ -80,7 +80,7 @@ func (matcher *HaveFieldMatcher) expectedMatcher() omegaMatcher { return expectedMatcher } -func (matcher *HaveFieldMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveFieldMatcher) Match(actual any) (success bool, err error) { extractedField, err := extractField(actual, matcher.Field, "HaveField") if err != nil { return false, err @@ -89,7 +89,7 @@ func (matcher *HaveFieldMatcher) Match(actual interface{}) (success bool, err er return matcher.expectedMatcher().Match(extractedField) } -func (matcher *HaveFieldMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveFieldMatcher) FailureMessage(actual any) (message string) { extractedField, err := extractField(actual, matcher.Field, "HaveField") if err != nil { // this really shouldn't happen @@ -101,7 +101,7 @@ func (matcher *HaveFieldMatcher) FailureMessage(actual interface{}) (message str return message } -func (matcher *HaveFieldMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveFieldMatcher) NegatedFailureMessage(actual any) (message string) { extractedField, err := extractField(actual, matcher.Field, "HaveField") if err != nil { // this really shouldn't happen diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_body_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_body_matcher.go index d14d9e5fc60..2d561b9a220 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_body_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_body_matcher.go @@ -11,12 +11,12 @@ import ( ) type HaveHTTPBodyMatcher struct { - Expected interface{} - cachedResponse interface{} + Expected any + cachedResponse any cachedBody []byte } -func (matcher *HaveHTTPBodyMatcher) Match(actual interface{}) (bool, error) { +func (matcher *HaveHTTPBodyMatcher) Match(actual any) (bool, error) { body, err := matcher.body(actual) if err != nil { return false, err @@ -34,7 +34,7 @@ func (matcher *HaveHTTPBodyMatcher) Match(actual interface{}) (bool, error) { } } -func (matcher *HaveHTTPBodyMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveHTTPBodyMatcher) FailureMessage(actual any) (message string) { body, err := matcher.body(actual) if err != nil { return fmt.Sprintf("failed to read body: %s", err) @@ -52,7 +52,7 @@ func (matcher *HaveHTTPBodyMatcher) FailureMessage(actual interface{}) (message } } -func (matcher *HaveHTTPBodyMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveHTTPBodyMatcher) NegatedFailureMessage(actual any) (message string) { body, err := matcher.body(actual) if err != nil { return fmt.Sprintf("failed to read body: %s", err) @@ -73,7 +73,7 @@ func (matcher *HaveHTTPBodyMatcher) NegatedFailureMessage(actual interface{}) (m // body returns the body. It is cached because once we read it in Match() // the Reader is closed and it is not readable again in FailureMessage() // or NegatedFailureMessage() -func (matcher *HaveHTTPBodyMatcher) body(actual interface{}) ([]byte, error) { +func (matcher *HaveHTTPBodyMatcher) body(actual any) ([]byte, error) { if matcher.cachedResponse == actual && matcher.cachedBody != nil { return matcher.cachedBody, nil } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_header_with_value_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_header_with_value_matcher.go index c256f452e84..756722659b1 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_header_with_value_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_header_with_value_matcher.go @@ -11,10 +11,10 @@ import ( type HaveHTTPHeaderWithValueMatcher struct { Header string - Value interface{} + Value any } -func (matcher *HaveHTTPHeaderWithValueMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveHTTPHeaderWithValueMatcher) Match(actual any) (success bool, err error) { headerValue, err := matcher.extractHeader(actual) if err != nil { return false, err @@ -28,7 +28,7 @@ func (matcher *HaveHTTPHeaderWithValueMatcher) Match(actual interface{}) (succes return headerMatcher.Match(headerValue) } -func (matcher *HaveHTTPHeaderWithValueMatcher) FailureMessage(actual interface{}) string { +func (matcher *HaveHTTPHeaderWithValueMatcher) FailureMessage(actual any) string { headerValue, err := matcher.extractHeader(actual) if err != nil { panic(err) // protected by Match() @@ -43,7 +43,7 @@ func (matcher *HaveHTTPHeaderWithValueMatcher) FailureMessage(actual interface{} return fmt.Sprintf("HTTP header %q:\n%s", matcher.Header, diff) } -func (matcher *HaveHTTPHeaderWithValueMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveHTTPHeaderWithValueMatcher) NegatedFailureMessage(actual any) (message string) { headerValue, err := matcher.extractHeader(actual) if err != nil { panic(err) // protected by Match() @@ -69,7 +69,7 @@ func (matcher *HaveHTTPHeaderWithValueMatcher) getSubMatcher() (types.GomegaMatc } } -func (matcher *HaveHTTPHeaderWithValueMatcher) extractHeader(actual interface{}) (string, error) { +func (matcher *HaveHTTPHeaderWithValueMatcher) extractHeader(actual any) (string, error) { switch r := actual.(type) { case *http.Response: return r.Header.Get(matcher.Header), nil diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_status_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_status_matcher.go index 0f66e46ece4..8b25b3a9f9d 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_status_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_http_status_matcher.go @@ -12,10 +12,10 @@ import ( ) type HaveHTTPStatusMatcher struct { - Expected []interface{} + Expected []any } -func (matcher *HaveHTTPStatusMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveHTTPStatusMatcher) Match(actual any) (success bool, err error) { var resp *http.Response switch a := actual.(type) { case *http.Response: @@ -48,11 +48,11 @@ func (matcher *HaveHTTPStatusMatcher) Match(actual interface{}) (success bool, e return false, nil } -func (matcher *HaveHTTPStatusMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveHTTPStatusMatcher) FailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\n%s\n%s", formatHttpResponse(actual), "to have HTTP status", matcher.expectedString()) } -func (matcher *HaveHTTPStatusMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveHTTPStatusMatcher) NegatedFailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\n%s\n%s", formatHttpResponse(actual), "not to have HTTP status", matcher.expectedString()) } @@ -64,7 +64,7 @@ func (matcher *HaveHTTPStatusMatcher) expectedString() string { return strings.Join(lines, "\n") } -func formatHttpResponse(input interface{}) string { +func formatHttpResponse(input any) string { var resp *http.Response switch r := input.(type) { case *http.Response: diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_matcher.go index b62ee93cb0f..9e16dcf5d6c 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_matcher.go @@ -11,10 +11,10 @@ import ( ) type HaveKeyMatcher struct { - Key interface{} + Key any } -func (matcher *HaveKeyMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveKeyMatcher) Match(actual any) (success bool, err error) { if !isMap(actual) && !miter.IsSeq2(actual) { return false, fmt.Errorf("HaveKey matcher expects a map/iter.Seq2. Got:%s", format.Object(actual, 1)) } @@ -52,7 +52,7 @@ func (matcher *HaveKeyMatcher) Match(actual interface{}) (success bool, err erro return false, nil } -func (matcher *HaveKeyMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveKeyMatcher) FailureMessage(actual any) (message string) { switch matcher.Key.(type) { case omegaMatcher: return format.Message(actual, "to have key matching", matcher.Key) @@ -61,7 +61,7 @@ func (matcher *HaveKeyMatcher) FailureMessage(actual interface{}) (message strin } } -func (matcher *HaveKeyMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveKeyMatcher) NegatedFailureMessage(actual any) (message string) { switch matcher.Key.(type) { case omegaMatcher: return format.Message(actual, "not to have key matching", matcher.Key) diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_with_value_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_with_value_matcher.go index 3d608f63ebb..1c53f1e56af 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_with_value_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_key_with_value_matcher.go @@ -11,11 +11,11 @@ import ( ) type HaveKeyWithValueMatcher struct { - Key interface{} - Value interface{} + Key any + Value any } -func (matcher *HaveKeyWithValueMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveKeyWithValueMatcher) Match(actual any) (success bool, err error) { if !isMap(actual) && !miter.IsSeq2(actual) { return false, fmt.Errorf("HaveKeyWithValue matcher expects a map/iter.Seq2. Got:%s", format.Object(actual, 1)) } @@ -70,7 +70,7 @@ func (matcher *HaveKeyWithValueMatcher) Match(actual interface{}) (success bool, return false, nil } -func (matcher *HaveKeyWithValueMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveKeyWithValueMatcher) FailureMessage(actual any) (message string) { str := "to have {key: value}" if _, ok := matcher.Key.(omegaMatcher); ok { str += " matching" @@ -78,12 +78,12 @@ func (matcher *HaveKeyWithValueMatcher) FailureMessage(actual interface{}) (mess str += " matching" } - expect := make(map[interface{}]interface{}, 1) + expect := make(map[any]any, 1) expect[matcher.Key] = matcher.Value return format.Message(actual, str, expect) } -func (matcher *HaveKeyWithValueMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveKeyWithValueMatcher) NegatedFailureMessage(actual any) (message string) { kStr := "not to have key" if _, ok := matcher.Key.(omegaMatcher); ok { kStr = "not to have key matching" diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_len_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_len_matcher.go index ca25713fe22..c334d4c0aa0 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_len_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_len_matcher.go @@ -10,7 +10,7 @@ type HaveLenMatcher struct { Count int } -func (matcher *HaveLenMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveLenMatcher) Match(actual any) (success bool, err error) { length, ok := lengthOf(actual) if !ok { return false, fmt.Errorf("HaveLen matcher expects a string/array/map/channel/slice/iterator. Got:\n%s", format.Object(actual, 1)) @@ -19,10 +19,10 @@ func (matcher *HaveLenMatcher) Match(actual interface{}) (success bool, err erro return length == matcher.Count, nil } -func (matcher *HaveLenMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveLenMatcher) FailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\nto have length %d", format.Object(actual, 1), matcher.Count) } -func (matcher *HaveLenMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveLenMatcher) NegatedFailureMessage(actual any) (message string) { return fmt.Sprintf("Expected\n%s\nnot to have length %d", format.Object(actual, 1), matcher.Count) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_occurred_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_occurred_matcher.go index 22a1b67306f..a240f1a1c74 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_occurred_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_occurred_matcher.go @@ -11,7 +11,7 @@ import ( type HaveOccurredMatcher struct { } -func (matcher *HaveOccurredMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveOccurredMatcher) Match(actual any) (success bool, err error) { // is purely nil? if actual == nil { return false, nil @@ -26,10 +26,10 @@ func (matcher *HaveOccurredMatcher) Match(actual interface{}) (success bool, err return !isNil(actual), nil } -func (matcher *HaveOccurredMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveOccurredMatcher) FailureMessage(actual any) (message string) { return fmt.Sprintf("Expected an error to have occurred. Got:\n%s", format.Object(actual, 1)) } -func (matcher *HaveOccurredMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveOccurredMatcher) NegatedFailureMessage(actual any) (message string) { return fmt.Sprintf("Unexpected error:\n%s\n%s", format.Object(actual, 1), "occurred") } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_prefix_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_prefix_matcher.go index 1d8e80270b3..7987d41f7b1 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_prefix_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_prefix_matcher.go @@ -8,10 +8,10 @@ import ( type HavePrefixMatcher struct { Prefix string - Args []interface{} + Args []any } -func (matcher *HavePrefixMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HavePrefixMatcher) Match(actual any) (success bool, err error) { actualString, ok := toString(actual) if !ok { return false, fmt.Errorf("HavePrefix matcher requires a string or stringer. Got:\n%s", format.Object(actual, 1)) @@ -27,10 +27,10 @@ func (matcher *HavePrefixMatcher) prefix() string { return matcher.Prefix } -func (matcher *HavePrefixMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HavePrefixMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to have prefix", matcher.prefix()) } -func (matcher *HavePrefixMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HavePrefixMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to have prefix", matcher.prefix()) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_suffix_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_suffix_matcher.go index 40a3526eb2d..2aa4ceacbc5 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_suffix_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_suffix_matcher.go @@ -8,10 +8,10 @@ import ( type HaveSuffixMatcher struct { Suffix string - Args []interface{} + Args []any } -func (matcher *HaveSuffixMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *HaveSuffixMatcher) Match(actual any) (success bool, err error) { actualString, ok := toString(actual) if !ok { return false, fmt.Errorf("HaveSuffix matcher requires a string or stringer. Got:\n%s", format.Object(actual, 1)) @@ -27,10 +27,10 @@ func (matcher *HaveSuffixMatcher) suffix() string { return matcher.Suffix } -func (matcher *HaveSuffixMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *HaveSuffixMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to have suffix", matcher.suffix()) } -func (matcher *HaveSuffixMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *HaveSuffixMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to have suffix", matcher.suffix()) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_value.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_value.go index f6725283570..4c39e0db00f 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_value.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/have_value.go @@ -12,10 +12,10 @@ const maxIndirections = 31 type HaveValueMatcher struct { Matcher types.GomegaMatcher // the matcher to apply to the "resolved" actual value. - resolvedActual interface{} // the ("resolved") value. + resolvedActual any // the ("resolved") value. } -func (m *HaveValueMatcher) Match(actual interface{}) (bool, error) { +func (m *HaveValueMatcher) Match(actual any) (bool, error) { val := reflect.ValueOf(actual) for allowedIndirs := maxIndirections; allowedIndirs > 0; allowedIndirs-- { // return an error if value isn't valid. Please note that we cannot @@ -45,10 +45,10 @@ func (m *HaveValueMatcher) Match(actual interface{}) (bool, error) { return false, errors.New(format.Message(actual, "too many indirections")) } -func (m *HaveValueMatcher) FailureMessage(_ interface{}) (message string) { +func (m *HaveValueMatcher) FailureMessage(_ any) (message string) { return m.Matcher.FailureMessage(m.resolvedActual) } -func (m *HaveValueMatcher) NegatedFailureMessage(_ interface{}) (message string) { +func (m *HaveValueMatcher) NegatedFailureMessage(_ any) (message string) { return m.Matcher.NegatedFailureMessage(m.resolvedActual) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_error_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_error_matcher.go index c539dd389c8..f9d313772fc 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_error_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_error_matcher.go @@ -71,14 +71,14 @@ func (matcher *MatchErrorMatcher) Match(actual any) (success bool, err error) { format.Object(expected, 1)) } -func (matcher *MatchErrorMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *MatchErrorMatcher) FailureMessage(actual any) (message string) { if matcher.isFunc { return format.Message(actual, fmt.Sprintf("to match error function %s", matcher.FuncErrDescription[0])) } return format.Message(actual, "to match error", matcher.Expected) } -func (matcher *MatchErrorMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *MatchErrorMatcher) NegatedFailureMessage(actual any) (message string) { if matcher.isFunc { return format.Message(actual, fmt.Sprintf("not to match error function %s", matcher.FuncErrDescription[0])) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_json_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_json_matcher.go index f962f139ff8..331f289abca 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_json_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_json_matcher.go @@ -9,18 +9,18 @@ import ( ) type MatchJSONMatcher struct { - JSONToMatch interface{} - firstFailurePath []interface{} + JSONToMatch any + firstFailurePath []any } -func (matcher *MatchJSONMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *MatchJSONMatcher) Match(actual any) (success bool, err error) { actualString, expectedString, err := matcher.prettyPrint(actual) if err != nil { return false, err } - var aval interface{} - var eval interface{} + var aval any + var eval any // this is guarded by prettyPrint json.Unmarshal([]byte(actualString), &aval) @@ -30,17 +30,17 @@ func (matcher *MatchJSONMatcher) Match(actual interface{}) (success bool, err er return equal, nil } -func (matcher *MatchJSONMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *MatchJSONMatcher) FailureMessage(actual any) (message string) { actualString, expectedString, _ := matcher.prettyPrint(actual) return formattedMessage(format.Message(actualString, "to match JSON of", expectedString), matcher.firstFailurePath) } -func (matcher *MatchJSONMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *MatchJSONMatcher) NegatedFailureMessage(actual any) (message string) { actualString, expectedString, _ := matcher.prettyPrint(actual) return formattedMessage(format.Message(actualString, "not to match JSON of", expectedString), matcher.firstFailurePath) } -func (matcher *MatchJSONMatcher) prettyPrint(actual interface{}) (actualFormatted, expectedFormatted string, err error) { +func (matcher *MatchJSONMatcher) prettyPrint(actual any) (actualFormatted, expectedFormatted string, err error) { actualString, ok := toString(actual) if !ok { return "", "", fmt.Errorf("MatchJSONMatcher matcher requires a string, stringer, or []byte. Got actual:\n%s", format.Object(actual, 1)) diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_regexp_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_regexp_matcher.go index adac5db6b8e..779be683e09 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_regexp_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_regexp_matcher.go @@ -9,10 +9,10 @@ import ( type MatchRegexpMatcher struct { Regexp string - Args []interface{} + Args []any } -func (matcher *MatchRegexpMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *MatchRegexpMatcher) Match(actual any) (success bool, err error) { actualString, ok := toString(actual) if !ok { return false, fmt.Errorf("RegExp matcher requires a string or stringer.\nGot:%s", format.Object(actual, 1)) @@ -26,11 +26,11 @@ func (matcher *MatchRegexpMatcher) Match(actual interface{}) (success bool, err return match, nil } -func (matcher *MatchRegexpMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *MatchRegexpMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to match regular expression", matcher.regexp()) } -func (matcher *MatchRegexpMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *MatchRegexpMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "not to match regular expression", matcher.regexp()) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_xml_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_xml_matcher.go index 5c815f5af74..f7dcaf6fdcd 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_xml_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_xml_matcher.go @@ -15,10 +15,10 @@ import ( ) type MatchXMLMatcher struct { - XMLToMatch interface{} + XMLToMatch any } -func (matcher *MatchXMLMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *MatchXMLMatcher) Match(actual any) (success bool, err error) { actualString, expectedString, err := matcher.formattedPrint(actual) if err != nil { return false, err @@ -37,17 +37,17 @@ func (matcher *MatchXMLMatcher) Match(actual interface{}) (success bool, err err return reflect.DeepEqual(aval, eval), nil } -func (matcher *MatchXMLMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *MatchXMLMatcher) FailureMessage(actual any) (message string) { actualString, expectedString, _ := matcher.formattedPrint(actual) return fmt.Sprintf("Expected\n%s\nto match XML of\n%s", actualString, expectedString) } -func (matcher *MatchXMLMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *MatchXMLMatcher) NegatedFailureMessage(actual any) (message string) { actualString, expectedString, _ := matcher.formattedPrint(actual) return fmt.Sprintf("Expected\n%s\nnot to match XML of\n%s", actualString, expectedString) } -func (matcher *MatchXMLMatcher) formattedPrint(actual interface{}) (actualString, expectedString string, err error) { +func (matcher *MatchXMLMatcher) formattedPrint(actual any) (actualString, expectedString string, err error) { var ok bool actualString, ok = toString(actual) if !ok { diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_yaml_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_yaml_matcher.go index 2cb6b47db95..95057c26cc7 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_yaml_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/match_yaml_matcher.go @@ -9,18 +9,18 @@ import ( ) type MatchYAMLMatcher struct { - YAMLToMatch interface{} - firstFailurePath []interface{} + YAMLToMatch any + firstFailurePath []any } -func (matcher *MatchYAMLMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *MatchYAMLMatcher) Match(actual any) (success bool, err error) { actualString, expectedString, err := matcher.toStrings(actual) if err != nil { return false, err } - var aval interface{} - var eval interface{} + var aval any + var eval any if err := yaml.Unmarshal([]byte(actualString), &aval); err != nil { return false, fmt.Errorf("Actual '%s' should be valid YAML, but it is not.\nUnderlying error:%s", actualString, err) @@ -34,23 +34,23 @@ func (matcher *MatchYAMLMatcher) Match(actual interface{}) (success bool, err er return equal, nil } -func (matcher *MatchYAMLMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *MatchYAMLMatcher) FailureMessage(actual any) (message string) { actualString, expectedString, _ := matcher.toNormalisedStrings(actual) return formattedMessage(format.Message(actualString, "to match YAML of", expectedString), matcher.firstFailurePath) } -func (matcher *MatchYAMLMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *MatchYAMLMatcher) NegatedFailureMessage(actual any) (message string) { actualString, expectedString, _ := matcher.toNormalisedStrings(actual) return formattedMessage(format.Message(actualString, "not to match YAML of", expectedString), matcher.firstFailurePath) } -func (matcher *MatchYAMLMatcher) toNormalisedStrings(actual interface{}) (actualFormatted, expectedFormatted string, err error) { +func (matcher *MatchYAMLMatcher) toNormalisedStrings(actual any) (actualFormatted, expectedFormatted string, err error) { actualString, expectedString, err := matcher.toStrings(actual) return normalise(actualString), normalise(expectedString), err } func normalise(input string) string { - var val interface{} + var val any err := yaml.Unmarshal([]byte(input), &val) if err != nil { panic(err) // unreachable since Match already calls Unmarshal @@ -62,7 +62,7 @@ func normalise(input string) string { return strings.TrimSpace(string(output)) } -func (matcher *MatchYAMLMatcher) toStrings(actual interface{}) (actualFormatted, expectedFormatted string, err error) { +func (matcher *MatchYAMLMatcher) toStrings(actual any) (actualFormatted, expectedFormatted string, err error) { actualString, ok := toString(actual) if !ok { return "", "", fmt.Errorf("MatchYAMLMatcher matcher requires a string, stringer, or []byte. Got actual:\n%s", format.Object(actual, 1)) diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/not.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/not.go index 78b71910d12..c598b7899a9 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/not.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/not.go @@ -8,7 +8,7 @@ type NotMatcher struct { Matcher types.GomegaMatcher } -func (m *NotMatcher) Match(actual interface{}) (bool, error) { +func (m *NotMatcher) Match(actual any) (bool, error) { success, err := m.Matcher.Match(actual) if err != nil { return false, err @@ -16,14 +16,14 @@ func (m *NotMatcher) Match(actual interface{}) (bool, error) { return !success, nil } -func (m *NotMatcher) FailureMessage(actual interface{}) (message string) { +func (m *NotMatcher) FailureMessage(actual any) (message string) { return m.Matcher.NegatedFailureMessage(actual) // works beautifully } -func (m *NotMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (m *NotMatcher) NegatedFailureMessage(actual any) (message string) { return m.Matcher.FailureMessage(actual) // works beautifully } -func (m *NotMatcher) MatchMayChangeInTheFuture(actual interface{}) bool { +func (m *NotMatcher) MatchMayChangeInTheFuture(actual any) bool { return types.MatchMayChangeInTheFuture(m.Matcher, actual) // just return m.Matcher's value } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/or.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/or.go index 841ae26ab07..6578404b0ee 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/or.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/or.go @@ -14,7 +14,7 @@ type OrMatcher struct { firstSuccessfulMatcher types.GomegaMatcher } -func (m *OrMatcher) Match(actual interface{}) (success bool, err error) { +func (m *OrMatcher) Match(actual any) (success bool, err error) { m.firstSuccessfulMatcher = nil for _, matcher := range m.Matchers { success, err := matcher.Match(actual) @@ -29,16 +29,16 @@ func (m *OrMatcher) Match(actual interface{}) (success bool, err error) { return false, nil } -func (m *OrMatcher) FailureMessage(actual interface{}) (message string) { +func (m *OrMatcher) FailureMessage(actual any) (message string) { // not the most beautiful list of matchers, but not bad either... return format.Message(actual, fmt.Sprintf("To satisfy at least one of these matchers: %s", m.Matchers)) } -func (m *OrMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (m *OrMatcher) NegatedFailureMessage(actual any) (message string) { return m.firstSuccessfulMatcher.NegatedFailureMessage(actual) } -func (m *OrMatcher) MatchMayChangeInTheFuture(actual interface{}) bool { +func (m *OrMatcher) MatchMayChangeInTheFuture(actual any) bool { /* Example with 3 matchers: A, B, C diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/panic_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/panic_matcher.go index adc8cee6306..8be5a7ccf3e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/panic_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/panic_matcher.go @@ -8,11 +8,11 @@ import ( ) type PanicMatcher struct { - Expected interface{} - object interface{} + Expected any + object any } -func (matcher *PanicMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *PanicMatcher) Match(actual any) (success bool, err error) { if actual == nil { return false, fmt.Errorf("PanicMatcher expects a non-nil actual.") } @@ -52,7 +52,7 @@ func (matcher *PanicMatcher) Match(actual interface{}) (success bool, err error) return } -func (matcher *PanicMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *PanicMatcher) FailureMessage(actual any) (message string) { if matcher.Expected == nil { // We wanted any panic to occur, but none did. return format.Message(actual, "to panic") @@ -91,7 +91,7 @@ func (matcher *PanicMatcher) FailureMessage(actual interface{}) (message string) } } -func (matcher *PanicMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *PanicMatcher) NegatedFailureMessage(actual any) (message string) { if matcher.Expected == nil { // We didn't want any panic to occur, but one did. return format.Message(actual, fmt.Sprintf("not to panic, but panicked with\n%s", format.Object(matcher.object, 1))) diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/receive_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/receive_matcher.go index 948164eaf88..1d9f61d6360 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/receive_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/receive_matcher.go @@ -11,12 +11,12 @@ import ( ) type ReceiveMatcher struct { - Args []interface{} + Args []any receivedValue reflect.Value channelClosed bool } -func (matcher *ReceiveMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *ReceiveMatcher) Match(actual any) (success bool, err error) { if !isChan(actual) { return false, fmt.Errorf("ReceiveMatcher expects a channel. Got:\n%s", format.Object(actual, 1)) } @@ -30,7 +30,7 @@ func (matcher *ReceiveMatcher) Match(actual interface{}) (success bool, err erro var subMatcher omegaMatcher var hasSubMatcher bool - var resultReference interface{} + var resultReference any // Valid arg formats are as follows, always with optional POINTER before // optional MATCHER: @@ -115,8 +115,8 @@ func (matcher *ReceiveMatcher) Match(actual interface{}) (success bool, err erro return false, nil } -func (matcher *ReceiveMatcher) FailureMessage(actual interface{}) (message string) { - var matcherArg interface{} +func (matcher *ReceiveMatcher) FailureMessage(actual any) (message string) { + var matcherArg any if len(matcher.Args) > 0 { matcherArg = matcher.Args[len(matcher.Args)-1] } @@ -136,8 +136,8 @@ func (matcher *ReceiveMatcher) FailureMessage(actual interface{}) (message strin return format.Message(actual, "to receive something."+closedAddendum) } -func (matcher *ReceiveMatcher) NegatedFailureMessage(actual interface{}) (message string) { - var matcherArg interface{} +func (matcher *ReceiveMatcher) NegatedFailureMessage(actual any) (message string) { + var matcherArg any if len(matcher.Args) > 0 { matcherArg = matcher.Args[len(matcher.Args)-1] } @@ -157,7 +157,7 @@ func (matcher *ReceiveMatcher) NegatedFailureMessage(actual interface{}) (messag return format.Message(actual, "not to receive anything."+closedAddendum) } -func (matcher *ReceiveMatcher) MatchMayChangeInTheFuture(actual interface{}) bool { +func (matcher *ReceiveMatcher) MatchMayChangeInTheFuture(actual any) bool { if !isChan(actual) { return false } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/satisfy_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/satisfy_matcher.go index ec68fe8b62c..2adc4825aac 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/satisfy_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/satisfy_matcher.go @@ -8,13 +8,13 @@ import ( ) type SatisfyMatcher struct { - Predicate interface{} + Predicate any // cached type predicateArgType reflect.Type } -func NewSatisfyMatcher(predicate interface{}) *SatisfyMatcher { +func NewSatisfyMatcher(predicate any) *SatisfyMatcher { if predicate == nil { panic("predicate cannot be nil") } @@ -35,7 +35,7 @@ func NewSatisfyMatcher(predicate interface{}) *SatisfyMatcher { } } -func (m *SatisfyMatcher) Match(actual interface{}) (success bool, err error) { +func (m *SatisfyMatcher) Match(actual any) (success bool, err error) { // prepare a parameter to pass to the predicate var param reflect.Value if actual != nil && reflect.TypeOf(actual).AssignableTo(m.predicateArgType) { @@ -57,10 +57,10 @@ func (m *SatisfyMatcher) Match(actual interface{}) (success bool, err error) { return result[0].Bool(), nil } -func (m *SatisfyMatcher) FailureMessage(actual interface{}) (message string) { +func (m *SatisfyMatcher) FailureMessage(actual any) (message string) { return format.Message(actual, "to satisfy predicate", m.Predicate) } -func (m *SatisfyMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (m *SatisfyMatcher) NegatedFailureMessage(actual any) (message string) { return format.Message(actual, "to not satisfy predicate", m.Predicate) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/semi_structured_data_support.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/semi_structured_data_support.go index 1369c1e87f7..30dd58f4a58 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/semi_structured_data_support.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/semi_structured_data_support.go @@ -8,7 +8,7 @@ import ( "strings" ) -func formattedMessage(comparisonMessage string, failurePath []interface{}) string { +func formattedMessage(comparisonMessage string, failurePath []any) string { var diffMessage string if len(failurePath) == 0 { diffMessage = "" @@ -18,7 +18,7 @@ func formattedMessage(comparisonMessage string, failurePath []interface{}) strin return fmt.Sprintf("%s%s", comparisonMessage, diffMessage) } -func formattedFailurePath(failurePath []interface{}) string { +func formattedFailurePath(failurePath []any) string { formattedPaths := []string{} for i := len(failurePath) - 1; i >= 0; i-- { switch p := failurePath[i].(type) { @@ -34,33 +34,33 @@ func formattedFailurePath(failurePath []interface{}) string { return strings.Join(formattedPaths, "") } -func deepEqual(a interface{}, b interface{}) (bool, []interface{}) { - var errorPath []interface{} +func deepEqual(a any, b any) (bool, []any) { + var errorPath []any if reflect.TypeOf(a) != reflect.TypeOf(b) { return false, errorPath } switch a.(type) { - case []interface{}: - if len(a.([]interface{})) != len(b.([]interface{})) { + case []any: + if len(a.([]any)) != len(b.([]any)) { return false, errorPath } - for i, v := range a.([]interface{}) { - elementEqual, keyPath := deepEqual(v, b.([]interface{})[i]) + for i, v := range a.([]any) { + elementEqual, keyPath := deepEqual(v, b.([]any)[i]) if !elementEqual { return false, append(keyPath, i) } } return true, errorPath - case map[interface{}]interface{}: - if len(a.(map[interface{}]interface{})) != len(b.(map[interface{}]interface{})) { + case map[any]any: + if len(a.(map[any]any)) != len(b.(map[any]any)) { return false, errorPath } - for k, v1 := range a.(map[interface{}]interface{}) { - v2, ok := b.(map[interface{}]interface{})[k] + for k, v1 := range a.(map[any]any) { + v2, ok := b.(map[any]any)[k] if !ok { return false, errorPath } @@ -71,13 +71,13 @@ func deepEqual(a interface{}, b interface{}) (bool, []interface{}) { } return true, errorPath - case map[string]interface{}: - if len(a.(map[string]interface{})) != len(b.(map[string]interface{})) { + case map[string]any: + if len(a.(map[string]any)) != len(b.(map[string]any)) { return false, errorPath } - for k, v1 := range a.(map[string]interface{}) { - v2, ok := b.(map[string]interface{})[k] + for k, v1 := range a.(map[string]any) { + v2, ok := b.(map[string]any)[k] if !ok { return false, errorPath } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/succeed_matcher.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/succeed_matcher.go index 327350f7b71..f0b2c4aa665 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/succeed_matcher.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/succeed_matcher.go @@ -14,7 +14,7 @@ type formattedGomegaError interface { type SucceedMatcher struct { } -func (matcher *SucceedMatcher) Match(actual interface{}) (success bool, err error) { +func (matcher *SucceedMatcher) Match(actual any) (success bool, err error) { // is purely nil? if actual == nil { return true, nil @@ -29,7 +29,7 @@ func (matcher *SucceedMatcher) Match(actual interface{}) (success bool, err erro return isNil(actual), nil } -func (matcher *SucceedMatcher) FailureMessage(actual interface{}) (message string) { +func (matcher *SucceedMatcher) FailureMessage(actual any) (message string) { var fgErr formattedGomegaError if errors.As(actual.(error), &fgErr) { return fgErr.FormattedGomegaError() @@ -37,6 +37,6 @@ func (matcher *SucceedMatcher) FailureMessage(actual interface{}) (message strin return fmt.Sprintf("Expected success, but got an error:\n%s", format.Object(actual, 1)) } -func (matcher *SucceedMatcher) NegatedFailureMessage(actual interface{}) (message string) { +func (matcher *SucceedMatcher) NegatedFailureMessage(actual any) (message string) { return "Expected failure, but got no error." } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/bipartitegraph/bipartitegraph.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/bipartitegraph/bipartitegraph.go index 830e308274e..0d78779d474 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/bipartitegraph/bipartitegraph.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/bipartitegraph/bipartitegraph.go @@ -11,7 +11,7 @@ type BipartiteGraph struct { Edges EdgeSet } -func NewBipartiteGraph(leftValues, rightValues []interface{}, neighbours func(interface{}, interface{}) (bool, error)) (*BipartiteGraph, error) { +func NewBipartiteGraph(leftValues, rightValues []any, neighbours func(any, any) (bool, error)) (*BipartiteGraph, error) { left := NodeOrderedSet{} for i, v := range leftValues { left = append(left, Node{ID: i, Value: v}) @@ -41,7 +41,7 @@ func NewBipartiteGraph(leftValues, rightValues []interface{}, neighbours func(in // FreeLeftRight returns left node values and right node values // of the BipartiteGraph's nodes which are not part of the given edges. -func (bg *BipartiteGraph) FreeLeftRight(edges EdgeSet) (leftValues, rightValues []interface{}) { +func (bg *BipartiteGraph) FreeLeftRight(edges EdgeSet) (leftValues, rightValues []any) { for _, node := range bg.Left { if edges.Free(node) { leftValues = append(leftValues, node.Value) diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/node/node.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/node/node.go index cd597a2f220..66d3578d518 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/node/node.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/support/goraph/node/node.go @@ -2,7 +2,7 @@ package node type Node struct { ID int - Value interface{} + Value any } type NodeOrderedSet []Node diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/type_support.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/type_support.go index b9440ac7adc..d020dedc30f 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/type_support.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/type_support.go @@ -20,16 +20,16 @@ import ( ) type omegaMatcher interface { - Match(actual interface{}) (success bool, err error) - FailureMessage(actual interface{}) (message string) - NegatedFailureMessage(actual interface{}) (message string) + Match(actual any) (success bool, err error) + FailureMessage(actual any) (message string) + NegatedFailureMessage(actual any) (message string) } -func isBool(a interface{}) bool { +func isBool(a any) bool { return reflect.TypeOf(a).Kind() == reflect.Bool } -func isNumber(a interface{}) bool { +func isNumber(a any) bool { if a == nil { return false } @@ -37,22 +37,22 @@ func isNumber(a interface{}) bool { return reflect.Int <= kind && kind <= reflect.Float64 } -func isInteger(a interface{}) bool { +func isInteger(a any) bool { kind := reflect.TypeOf(a).Kind() return reflect.Int <= kind && kind <= reflect.Int64 } -func isUnsignedInteger(a interface{}) bool { +func isUnsignedInteger(a any) bool { kind := reflect.TypeOf(a).Kind() return reflect.Uint <= kind && kind <= reflect.Uint64 } -func isFloat(a interface{}) bool { +func isFloat(a any) bool { kind := reflect.TypeOf(a).Kind() return reflect.Float32 <= kind && kind <= reflect.Float64 } -func toInteger(a interface{}) int64 { +func toInteger(a any) int64 { if isInteger(a) { return reflect.ValueOf(a).Int() } else if isUnsignedInteger(a) { @@ -63,7 +63,7 @@ func toInteger(a interface{}) int64 { panic(fmt.Sprintf("Expected a number! Got <%T> %#v", a, a)) } -func toUnsignedInteger(a interface{}) uint64 { +func toUnsignedInteger(a any) uint64 { if isInteger(a) { return uint64(reflect.ValueOf(a).Int()) } else if isUnsignedInteger(a) { @@ -74,7 +74,7 @@ func toUnsignedInteger(a interface{}) uint64 { panic(fmt.Sprintf("Expected a number! Got <%T> %#v", a, a)) } -func toFloat(a interface{}) float64 { +func toFloat(a any) float64 { if isInteger(a) { return float64(reflect.ValueOf(a).Int()) } else if isUnsignedInteger(a) { @@ -85,26 +85,26 @@ func toFloat(a interface{}) float64 { panic(fmt.Sprintf("Expected a number! Got <%T> %#v", a, a)) } -func isError(a interface{}) bool { +func isError(a any) bool { _, ok := a.(error) return ok } -func isChan(a interface{}) bool { +func isChan(a any) bool { if isNil(a) { return false } return reflect.TypeOf(a).Kind() == reflect.Chan } -func isMap(a interface{}) bool { +func isMap(a any) bool { if a == nil { return false } return reflect.TypeOf(a).Kind() == reflect.Map } -func isArrayOrSlice(a interface{}) bool { +func isArrayOrSlice(a any) bool { if a == nil { return false } @@ -116,14 +116,14 @@ func isArrayOrSlice(a interface{}) bool { } } -func isString(a interface{}) bool { +func isString(a any) bool { if a == nil { return false } return reflect.TypeOf(a).Kind() == reflect.String } -func toString(a interface{}) (string, bool) { +func toString(a any) (string, bool) { aString, isString := a.(string) if isString { return aString, true @@ -147,7 +147,7 @@ func toString(a interface{}) (string, bool) { return "", false } -func lengthOf(a interface{}) (int, bool) { +func lengthOf(a any) (int, bool) { if a == nil { return 0, false } @@ -169,7 +169,7 @@ func lengthOf(a interface{}) (int, bool) { return 0, false } } -func capOf(a interface{}) (int, bool) { +func capOf(a any) (int, bool) { if a == nil { return 0, false } @@ -181,7 +181,7 @@ func capOf(a interface{}) (int, bool) { } } -func isNil(a interface{}) bool { +func isNil(a any) bool { if a == nil { return true } diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/with_transform.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/with_transform.go index 6f743b1b32d..6231c3b476a 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/with_transform.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/matchers/with_transform.go @@ -9,20 +9,20 @@ import ( type WithTransformMatcher struct { // input - Transform interface{} // must be a function of one parameter that returns one value and an optional error + Transform any // must be a function of one parameter that returns one value and an optional error Matcher types.GomegaMatcher // cached value transformArgType reflect.Type // state - transformedValue interface{} + transformedValue any } // reflect.Type for error var errorT = reflect.TypeOf((*error)(nil)).Elem() -func NewWithTransformMatcher(transform interface{}, matcher types.GomegaMatcher) *WithTransformMatcher { +func NewWithTransformMatcher(transform any, matcher types.GomegaMatcher) *WithTransformMatcher { if transform == nil { panic("transform function cannot be nil") } @@ -43,7 +43,7 @@ func NewWithTransformMatcher(transform interface{}, matcher types.GomegaMatcher) } } -func (m *WithTransformMatcher) Match(actual interface{}) (bool, error) { +func (m *WithTransformMatcher) Match(actual any) (bool, error) { // prepare a parameter to pass to the Transform function var param reflect.Value if actual != nil && reflect.TypeOf(actual).AssignableTo(m.transformArgType) { @@ -72,15 +72,15 @@ func (m *WithTransformMatcher) Match(actual interface{}) (bool, error) { return m.Matcher.Match(m.transformedValue) } -func (m *WithTransformMatcher) FailureMessage(_ interface{}) (message string) { +func (m *WithTransformMatcher) FailureMessage(_ any) (message string) { return m.Matcher.FailureMessage(m.transformedValue) } -func (m *WithTransformMatcher) NegatedFailureMessage(_ interface{}) (message string) { +func (m *WithTransformMatcher) NegatedFailureMessage(_ any) (message string) { return m.Matcher.NegatedFailureMessage(m.transformedValue) } -func (m *WithTransformMatcher) MatchMayChangeInTheFuture(_ interface{}) bool { +func (m *WithTransformMatcher) MatchMayChangeInTheFuture(_ any) bool { // TODO: Maybe this should always just return true? (Only an issue for non-deterministic transformers.) // // Querying the next matcher is fine if the transformer always will return the same value. diff --git a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/types/types.go b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/types/types.go index 30f2beed30f..685a46f373e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/types/types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/onsi/gomega/types/types.go @@ -10,20 +10,20 @@ type GomegaFailHandler func(message string, callerSkip ...int) // A simple *testing.T interface wrapper type GomegaTestingT interface { Helper() - Fatalf(format string, args ...interface{}) + Fatalf(format string, args ...any) } -// Gomega represents an object that can perform synchronous and assynchronous assertions with Gomega matchers +// Gomega represents an object that can perform synchronous and asynchronous assertions with Gomega matchers type Gomega interface { - Ω(actual interface{}, extra ...interface{}) Assertion - Expect(actual interface{}, extra ...interface{}) Assertion - ExpectWithOffset(offset int, actual interface{}, extra ...interface{}) Assertion + Ω(actual any, extra ...any) Assertion + Expect(actual any, extra ...any) Assertion + ExpectWithOffset(offset int, actual any, extra ...any) Assertion - Eventually(actualOrCtx interface{}, args ...interface{}) AsyncAssertion - EventuallyWithOffset(offset int, actualOrCtx interface{}, args ...interface{}) AsyncAssertion + Eventually(actualOrCtx any, args ...any) AsyncAssertion + EventuallyWithOffset(offset int, actualOrCtx any, args ...any) AsyncAssertion - Consistently(actualOrCtx interface{}, args ...interface{}) AsyncAssertion - ConsistentlyWithOffset(offset int, actualOrCtx interface{}, args ...interface{}) AsyncAssertion + Consistently(actualOrCtx any, args ...any) AsyncAssertion + ConsistentlyWithOffset(offset int, actualOrCtx any, args ...any) AsyncAssertion SetDefaultEventuallyTimeout(time.Duration) SetDefaultEventuallyPollingInterval(time.Duration) @@ -37,9 +37,9 @@ type Gomega interface { // // For details on writing custom matchers, check out: http://onsi.github.io/gomega/#adding-your-own-matchers type GomegaMatcher interface { - Match(actual interface{}) (success bool, err error) - FailureMessage(actual interface{}) (message string) - NegatedFailureMessage(actual interface{}) (message string) + Match(actual any) (success bool, err error) + FailureMessage(actual any) (message string) + NegatedFailureMessage(actual any) (message string) } /* @@ -52,10 +52,10 @@ For example, a process' exit code can never change. So, gexec's Exit matcher re for `MatchMayChangeInTheFuture` until the process exits, at which point it returns `false` forevermore. */ type OracleMatcher interface { - MatchMayChangeInTheFuture(actual interface{}) bool + MatchMayChangeInTheFuture(actual any) bool } -func MatchMayChangeInTheFuture(matcher GomegaMatcher, value interface{}) bool { +func MatchMayChangeInTheFuture(matcher GomegaMatcher, value any) bool { oracleMatcher, ok := matcher.(OracleMatcher) if !ok { return true @@ -67,8 +67,13 @@ func MatchMayChangeInTheFuture(matcher GomegaMatcher, value interface{}) bool { // AsyncAssertions are returned by Eventually and Consistently and enable matchers to be polled repeatedly to ensure // they are eventually satisfied type AsyncAssertion interface { - Should(matcher GomegaMatcher, optionalDescription ...interface{}) bool - ShouldNot(matcher GomegaMatcher, optionalDescription ...interface{}) bool + Should(matcher GomegaMatcher, optionalDescription ...any) bool + ShouldNot(matcher GomegaMatcher, optionalDescription ...any) bool + + // equivalent to above + To(matcher GomegaMatcher, optionalDescription ...any) bool + ToNot(matcher GomegaMatcher, optionalDescription ...any) bool + NotTo(matcher GomegaMatcher, optionalDescription ...any) bool WithOffset(offset int) AsyncAssertion WithTimeout(interval time.Duration) AsyncAssertion @@ -76,18 +81,18 @@ type AsyncAssertion interface { Within(timeout time.Duration) AsyncAssertion ProbeEvery(interval time.Duration) AsyncAssertion WithContext(ctx context.Context) AsyncAssertion - WithArguments(argsToForward ...interface{}) AsyncAssertion + WithArguments(argsToForward ...any) AsyncAssertion MustPassRepeatedly(count int) AsyncAssertion } // Assertions are returned by Ω and Expect and enable assertions against Gomega matchers type Assertion interface { - Should(matcher GomegaMatcher, optionalDescription ...interface{}) bool - ShouldNot(matcher GomegaMatcher, optionalDescription ...interface{}) bool + Should(matcher GomegaMatcher, optionalDescription ...any) bool + ShouldNot(matcher GomegaMatcher, optionalDescription ...any) bool - To(matcher GomegaMatcher, optionalDescription ...interface{}) bool - ToNot(matcher GomegaMatcher, optionalDescription ...interface{}) bool - NotTo(matcher GomegaMatcher, optionalDescription ...interface{}) bool + To(matcher GomegaMatcher, optionalDescription ...any) bool + ToNot(matcher GomegaMatcher, optionalDescription ...any) bool + NotTo(matcher GomegaMatcher, optionalDescription ...any) bool WithOffset(offset int) Assertion diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/README.md b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/README.md index 6444f4b7f6f..71757151c33 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/README.md +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/README.md @@ -1,4 +1,5 @@ -![cobra logo](assets/CobraMain.png) + +![cobra logo](https://github.com/user-attachments/assets/cbc3adf8-0dff-46e9-a88d-5e2d971c169e) Cobra is a library for creating powerful modern CLI applications. @@ -105,7 +106,7 @@ go install github.com/spf13/cobra-cli@latest For complete details on using the Cobra-CLI generator, please read [The Cobra Generator README](https://github.com/spf13/cobra-cli/blob/main/README.md) -For complete details on using the Cobra library, please read the [The Cobra User Guide](site/content/user_guide.md). +For complete details on using the Cobra library, please read [The Cobra User Guide](site/content/user_guide.md). # License diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/active_help.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/active_help.go index 25c30e3ccc3..b3e2dadfed6 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/active_help.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/active_help.go @@ -35,7 +35,7 @@ const ( // This function can be called multiple times before and/or after completions are added to // the array. Each time this function is called with the same array, the new // ActiveHelp line will be shown below the previous ones when completion is triggered. -func AppendActiveHelp(compArray []string, activeHelpStr string) []string { +func AppendActiveHelp(compArray []Completion, activeHelpStr string) []Completion { return append(compArray, fmt.Sprintf("%s%s", activeHelpMarker, activeHelpStr)) } diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/bash_completionsV2.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/bash_completionsV2.go index 1cce5c329c2..d2397aa3668 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/bash_completionsV2.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/bash_completionsV2.go @@ -146,7 +146,7 @@ __%[1]s_process_completion_results() { if (((directive & shellCompDirectiveFilterFileExt) != 0)); then # File extension filtering - local fullFilter filter filteringCmd + local fullFilter="" filter filteringCmd # Do not use quotes around the $completions variable or else newline # characters will be kept. @@ -177,20 +177,71 @@ __%[1]s_process_completion_results() { __%[1]s_handle_special_char "$cur" = # Print the activeHelp statements before we finish + __%[1]s_handle_activeHelp +} + +__%[1]s_handle_activeHelp() { + # Print the activeHelp statements if ((${#activeHelp[*]} != 0)); then - printf "\n"; - printf "%%s\n" "${activeHelp[@]}" - printf "\n" - - # The prompt format is only available from bash 4.4. - # We test if it is available before using it. - if (x=${PS1@P}) 2> /dev/null; then - printf "%%s" "${PS1@P}${COMP_LINE[@]}" - else - # Can't print the prompt. Just print the - # text the user had typed, it is workable enough. - printf "%%s" "${COMP_LINE[@]}" + if [ -z $COMP_TYPE ]; then + # Bash v3 does not set the COMP_TYPE variable. + printf "\n"; + printf "%%s\n" "${activeHelp[@]}" + printf "\n" + __%[1]s_reprint_commandLine + return fi + + # Only print ActiveHelp on the second TAB press + if [ $COMP_TYPE -eq 63 ]; then + printf "\n" + printf "%%s\n" "${activeHelp[@]}" + + if ((${#COMPREPLY[*]} == 0)); then + # When there are no completion choices from the program, file completion + # may kick in if the program has not disabled it; in such a case, we want + # to know if any files will match what the user typed, so that we know if + # there will be completions presented, so that we know how to handle ActiveHelp. + # To find out, we actually trigger the file completion ourselves; + # the call to _filedir will fill COMPREPLY if files match. + if (((directive & shellCompDirectiveNoFileComp) == 0)); then + __%[1]s_debug "Listing files" + _filedir + fi + fi + + if ((${#COMPREPLY[*]} != 0)); then + # If there are completion choices to be shown, print a delimiter. + # Re-printing the command-line will automatically be done + # by the shell when it prints the completion choices. + printf -- "--" + else + # When there are no completion choices at all, we need + # to re-print the command-line since the shell will + # not be doing it itself. + __%[1]s_reprint_commandLine + fi + elif [ $COMP_TYPE -eq 37 ] || [ $COMP_TYPE -eq 42 ]; then + # For completion type: menu-complete/menu-complete-backward and insert-completions + # the completions are immediately inserted into the command-line, so we first + # print the activeHelp message and reprint the command-line since the shell won't. + printf "\n" + printf "%%s\n" "${activeHelp[@]}" + + __%[1]s_reprint_commandLine + fi + fi +} + +__%[1]s_reprint_commandLine() { + # The prompt format is only available from bash 4.4. + # We test if it is available before using it. + if (x=${PS1@P}) 2> /dev/null; then + printf "%%s" "${PS1@P}${COMP_LINE[@]}" + else + # Can't print the prompt. Just print the + # text the user had typed, it is workable enough. + printf "%%s" "${COMP_LINE[@]}" fi } @@ -201,6 +252,8 @@ __%[1]s_extract_activeHelp() { local endIndex=${#activeHelpMarker} while IFS='' read -r comp; do + [[ -z $comp ]] && continue + if [[ ${comp:0:endIndex} == $activeHelpMarker ]]; then comp=${comp:endIndex} __%[1]s_debug "ActiveHelp found: $comp" @@ -223,16 +276,21 @@ __%[1]s_handle_completion_types() { # If the user requested inserting one completion at a time, or all # completions at once on the command-line we must remove the descriptions. # https://github.com/spf13/cobra/issues/1508 - local tab=$'\t' comp - while IFS='' read -r comp; do - [[ -z $comp ]] && continue - # Strip any description - comp=${comp%%%%$tab*} - # Only consider the completions that match - if [[ $comp == "$cur"* ]]; then - COMPREPLY+=("$comp") - fi - done < <(printf "%%s\n" "${completions[@]}") + + # If there are no completions, we don't need to do anything + (( ${#completions[@]} == 0 )) && return 0 + + local tab=$'\t' + + # Strip any description and escape the completion to handled special characters + IFS=$'\n' read -ra completions -d '' < <(printf "%%q\n" "${completions[@]%%%%$tab*}") + + # Only consider the completions that match + IFS=$'\n' read -ra COMPREPLY -d '' < <(IFS=$'\n'; compgen -W "${completions[*]}" -- "${cur}") + + # compgen looses the escaping so we need to escape all completions again since they will + # all be inserted on the command-line. + IFS=$'\n' read -ra COMPREPLY -d '' < <(printf "%%q\n" "${COMPREPLY[@]}") ;; *) @@ -243,11 +301,25 @@ __%[1]s_handle_completion_types() { } __%[1]s_handle_standard_completion_case() { - local tab=$'\t' comp + local tab=$'\t' + + # If there are no completions, we don't need to do anything + (( ${#completions[@]} == 0 )) && return 0 # Short circuit to optimize if we don't have descriptions if [[ "${completions[*]}" != *$tab* ]]; then - IFS=$'\n' read -ra COMPREPLY -d '' < <(compgen -W "${completions[*]}" -- "$cur") + # First, escape the completions to handle special characters + IFS=$'\n' read -ra completions -d '' < <(printf "%%q\n" "${completions[@]}") + # Only consider the completions that match what the user typed + IFS=$'\n' read -ra COMPREPLY -d '' < <(IFS=$'\n'; compgen -W "${completions[*]}" -- "${cur}") + + # compgen looses the escaping so, if there is only a single completion, we need to + # escape it again because it will be inserted on the command-line. If there are multiple + # completions, we don't want to escape them because they will be printed in a list + # and we don't want to show escape characters in that list. + if (( ${#COMPREPLY[@]} == 1 )); then + COMPREPLY[0]=$(printf "%%q" "${COMPREPLY[0]}") + fi return 0 fi @@ -256,23 +328,39 @@ __%[1]s_handle_standard_completion_case() { # Look for the longest completion so that we can format things nicely while IFS='' read -r compline; do [[ -z $compline ]] && continue - # Strip any description before checking the length - comp=${compline%%%%$tab*} + + # Before checking if the completion matches what the user typed, + # we need to strip any description and escape the completion to handle special + # characters because those escape characters are part of what the user typed. + # Don't call "printf" in a sub-shell because it will be much slower + # since we are in a loop. + printf -v comp "%%q" "${compline%%%%$tab*}" &>/dev/null || comp=$(printf "%%q" "${compline%%%%$tab*}") + # Only consider the completions that match [[ $comp == "$cur"* ]] || continue + + # The completions matches. Add it to the list of full completions including + # its description. We don't escape the completion because it may get printed + # in a list if there are more than one and we don't want show escape characters + # in that list. COMPREPLY+=("$compline") + + # Strip any description before checking the length, and again, don't escape + # the completion because this length is only used when printing the completions + # in a list and we don't want show escape characters in that list. + comp=${compline%%%%$tab*} if ((${#comp}>longest)); then longest=${#comp} fi done < <(printf "%%s\n" "${completions[@]}") - # If there is a single completion left, remove the description text + # If there is a single completion left, remove the description text and escape any special characters if ((${#COMPREPLY[*]} == 1)); then __%[1]s_debug "COMPREPLY[0]: ${COMPREPLY[0]}" - comp="${COMPREPLY[0]%%%%$tab*}" - __%[1]s_debug "Removed description from single completion, which is now: ${comp}" - COMPREPLY[0]=$comp - else # Format the descriptions + COMPREPLY[0]=$(printf "%%q" "${COMPREPLY[0]%%%%$tab*}") + __%[1]s_debug "Removed description from single completion, which is now: ${COMPREPLY[0]}" + else + # Format the descriptions __%[1]s_format_comp_descriptions $longest fi } diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/cobra.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/cobra.go index e0b0947b04c..d9cd2414e23 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/cobra.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/cobra.go @@ -176,12 +176,16 @@ func rpad(s string, padding int) string { return fmt.Sprintf(formattedString, s) } -// tmpl executes the given template text on data, writing the result to w. -func tmpl(w io.Writer, text string, data interface{}) error { - t := template.New("top") - t.Funcs(templateFuncs) - template.Must(t.Parse(text)) - return t.Execute(w, data) +func tmpl(text string) *tmplFunc { + return &tmplFunc{ + tmpl: text, + fn: func(w io.Writer, data interface{}) error { + t := template.New("top") + t.Funcs(templateFuncs) + template.Must(t.Parse(text)) + return t.Execute(w, data) + }, + } } // ld compares two strings and returns the levenshtein distance between them. diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/command.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/command.go index 54748fc67eb..dbb2c298ba0 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/command.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/command.go @@ -33,6 +33,9 @@ import ( const ( FlagSetByCobraAnnotation = "cobra_annotation_flag_set_by_cobra" CommandDisplayNameAnnotation = "cobra_annotation_command_display_name" + + helpFlagName = "help" + helpCommandName = "help" ) // FParseErrWhitelist configures Flag parse errors to be ignored @@ -80,11 +83,11 @@ type Command struct { Example string // ValidArgs is list of all valid non-flag arguments that are accepted in shell completions - ValidArgs []string + ValidArgs []Completion // ValidArgsFunction is an optional function that provides valid non-flag arguments for shell completion. // It is a dynamic version of using ValidArgs. // Only one of ValidArgs and ValidArgsFunction can be used for a command. - ValidArgsFunction func(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective) + ValidArgsFunction CompletionFunc // Expected arguments Args PositionalArgs @@ -168,12 +171,12 @@ type Command struct { // usageFunc is usage func defined by user. usageFunc func(*Command) error // usageTemplate is usage template defined by user. - usageTemplate string + usageTemplate *tmplFunc // flagErrorFunc is func defined by user and it's called when the parsing of // flags returns an error. flagErrorFunc func(*Command, error) error // helpTemplate is help template defined by user. - helpTemplate string + helpTemplate *tmplFunc // helpFunc is help func defined by user. helpFunc func(*Command, []string) // helpCommand is command with usage 'help'. If it's not defined by user, @@ -186,7 +189,7 @@ type Command struct { completionCommandGroupID string // versionTemplate is the version template defined by user. - versionTemplate string + versionTemplate *tmplFunc // errPrefix is the error message prefix defined by user. errPrefix string @@ -281,6 +284,7 @@ func (c *Command) SetArgs(a []string) { // SetOutput sets the destination for usage and error messages. // If output is nil, os.Stderr is used. +// // Deprecated: Use SetOut and/or SetErr instead func (c *Command) SetOutput(output io.Writer) { c.outWriter = output @@ -312,7 +316,11 @@ func (c *Command) SetUsageFunc(f func(*Command) error) { // SetUsageTemplate sets usage template. Can be defined by Application. func (c *Command) SetUsageTemplate(s string) { - c.usageTemplate = s + if s == "" { + c.usageTemplate = nil + return + } + c.usageTemplate = tmpl(s) } // SetFlagErrorFunc sets a function to generate an error when flag parsing @@ -348,12 +356,20 @@ func (c *Command) SetCompletionCommandGroupID(groupID string) { // SetHelpTemplate sets help template to be used. Application can use it to set custom template. func (c *Command) SetHelpTemplate(s string) { - c.helpTemplate = s + if s == "" { + c.helpTemplate = nil + return + } + c.helpTemplate = tmpl(s) } // SetVersionTemplate sets version template to be used. Application can use it to set custom template. func (c *Command) SetVersionTemplate(s string) { - c.versionTemplate = s + if s == "" { + c.versionTemplate = nil + return + } + c.versionTemplate = tmpl(s) } // SetErrPrefix sets error message prefix to be used. Application can use it to set custom prefix. @@ -434,7 +450,8 @@ func (c *Command) UsageFunc() (f func(*Command) error) { } return func(c *Command) error { c.mergePersistentFlags() - err := tmpl(c.OutOrStderr(), c.UsageTemplate(), c) + fn := c.getUsageTemplateFunc() + err := fn(c.OutOrStderr(), c) if err != nil { c.PrintErrln(err) } @@ -442,6 +459,19 @@ func (c *Command) UsageFunc() (f func(*Command) error) { } } +// getUsageTemplateFunc returns the usage template function for the command +// going up the command tree if necessary. +func (c *Command) getUsageTemplateFunc() func(w io.Writer, data interface{}) error { + if c.usageTemplate != nil { + return c.usageTemplate.fn + } + + if c.HasParent() { + return c.parent.getUsageTemplateFunc() + } + return defaultUsageFunc +} + // Usage puts out the usage for the command. // Used when a user provides invalid input. // Can be defined by user by overriding UsageFunc. @@ -460,15 +490,30 @@ func (c *Command) HelpFunc() func(*Command, []string) { } return func(c *Command, a []string) { c.mergePersistentFlags() + fn := c.getHelpTemplateFunc() // The help should be sent to stdout // See https://github.com/spf13/cobra/issues/1002 - err := tmpl(c.OutOrStdout(), c.HelpTemplate(), c) + err := fn(c.OutOrStdout(), c) if err != nil { c.PrintErrln(err) } } } +// getHelpTemplateFunc returns the help template function for the command +// going up the command tree if necessary. +func (c *Command) getHelpTemplateFunc() func(w io.Writer, data interface{}) error { + if c.helpTemplate != nil { + return c.helpTemplate.fn + } + + if c.HasParent() { + return c.parent.getHelpTemplateFunc() + } + + return defaultHelpFunc +} + // Help puts out the help for the command. // Used when a user calls help [command]. // Can be defined by user by overriding HelpFunc. @@ -543,71 +588,55 @@ func (c *Command) NamePadding() int { } // UsageTemplate returns usage template for the command. +// This function is kept for backwards-compatibility reasons. func (c *Command) UsageTemplate() string { - if c.usageTemplate != "" { - return c.usageTemplate + if c.usageTemplate != nil { + return c.usageTemplate.tmpl } if c.HasParent() { return c.parent.UsageTemplate() } - return `Usage:{{if .Runnable}} - {{.UseLine}}{{end}}{{if .HasAvailableSubCommands}} - {{.CommandPath}} [command]{{end}}{{if gt (len .Aliases) 0}} - -Aliases: - {{.NameAndAliases}}{{end}}{{if .HasExample}} - -Examples: -{{.Example}}{{end}}{{if .HasAvailableSubCommands}}{{$cmds := .Commands}}{{if eq (len .Groups) 0}} - -Available Commands:{{range $cmds}}{{if (or .IsAvailableCommand (eq .Name "help"))}} - {{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{else}}{{range $group := .Groups}} - -{{.Title}}{{range $cmds}}{{if (and (eq .GroupID $group.ID) (or .IsAvailableCommand (eq .Name "help")))}} - {{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{if not .AllChildCommandsHaveGroup}} - -Additional Commands:{{range $cmds}}{{if (and (eq .GroupID "") (or .IsAvailableCommand (eq .Name "help")))}} - {{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{end}}{{end}}{{if .HasAvailableLocalFlags}} - -Flags: -{{.LocalFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasAvailableInheritedFlags}} - -Global Flags: -{{.InheritedFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasHelpSubCommands}} - -Additional help topics:{{range .Commands}}{{if .IsAdditionalHelpTopicCommand}} - {{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableSubCommands}} - -Use "{{.CommandPath}} [command] --help" for more information about a command.{{end}} -` + return defaultUsageTemplate } // HelpTemplate return help template for the command. +// This function is kept for backwards-compatibility reasons. func (c *Command) HelpTemplate() string { - if c.helpTemplate != "" { - return c.helpTemplate + if c.helpTemplate != nil { + return c.helpTemplate.tmpl } if c.HasParent() { return c.parent.HelpTemplate() } - return `{{with (or .Long .Short)}}{{. | trimTrailingWhitespaces}} - -{{end}}{{if or .Runnable .HasSubCommands}}{{.UsageString}}{{end}}` + return defaultHelpTemplate } // VersionTemplate return version template for the command. +// This function is kept for backwards-compatibility reasons. func (c *Command) VersionTemplate() string { - if c.versionTemplate != "" { - return c.versionTemplate + if c.versionTemplate != nil { + return c.versionTemplate.tmpl } if c.HasParent() { return c.parent.VersionTemplate() } - return `{{with .Name}}{{printf "%s " .}}{{end}}{{printf "version %s" .Version}} -` + return defaultVersionTemplate +} + +// getVersionTemplateFunc returns the version template function for the command +// going up the command tree if necessary. +func (c *Command) getVersionTemplateFunc() func(w io.Writer, data interface{}) error { + if c.versionTemplate != nil { + return c.versionTemplate.fn + } + + if c.HasParent() { + return c.parent.getVersionTemplateFunc() + } + return defaultVersionFunc } // ErrPrefix return error message prefix for the command @@ -894,7 +923,7 @@ func (c *Command) execute(a []string) (err error) { // If help is called, regardless of other flags, return we want help. // Also say we need help if the command isn't runnable. - helpVal, err := c.Flags().GetBool("help") + helpVal, err := c.Flags().GetBool(helpFlagName) if err != nil { // should be impossible to get here as we always declare a help // flag in InitDefaultHelpFlag() @@ -914,7 +943,8 @@ func (c *Command) execute(a []string) (err error) { return err } if versionVal { - err := tmpl(c.OutOrStdout(), c.VersionTemplate(), c) + fn := c.getVersionTemplateFunc() + err := fn(c.OutOrStdout(), c) if err != nil { c.Println(err) } @@ -1068,12 +1098,6 @@ func (c *Command) ExecuteC() (cmd *Command, err error) { // initialize help at the last point to allow for user overriding c.InitDefaultHelpCmd() - // initialize completion at the last point to allow for user overriding - c.InitDefaultCompletionCmd() - - // Now that all commands have been created, let's make sure all groups - // are properly created also - c.checkCommandGroups() args := c.args @@ -1082,9 +1106,16 @@ func (c *Command) ExecuteC() (cmd *Command, err error) { args = os.Args[1:] } - // initialize the hidden command to be used for shell completion + // initialize the __complete command to be used for shell completion c.initCompleteCmd(args) + // initialize the default completion command + c.InitDefaultCompletionCmd(args...) + + // Now that all commands have been created, let's make sure all groups + // are properly created also + c.checkCommandGroups() + var flags []string if c.TraverseChildren { cmd, flags, err = c.Traverse(args) @@ -1187,16 +1218,16 @@ func (c *Command) checkCommandGroups() { // If c already has help flag, it will do nothing. func (c *Command) InitDefaultHelpFlag() { c.mergePersistentFlags() - if c.Flags().Lookup("help") == nil { + if c.Flags().Lookup(helpFlagName) == nil { usage := "help for " - name := c.displayName() + name := c.DisplayName() if name == "" { usage += "this command" } else { usage += name } - c.Flags().BoolP("help", "h", false, usage) - _ = c.Flags().SetAnnotation("help", FlagSetByCobraAnnotation, []string{"true"}) + c.Flags().BoolP(helpFlagName, "h", false, usage) + _ = c.Flags().SetAnnotation(helpFlagName, FlagSetByCobraAnnotation, []string{"true"}) } } @@ -1215,7 +1246,7 @@ func (c *Command) InitDefaultVersionFlag() { if c.Name() == "" { usage += "this command" } else { - usage += c.Name() + usage += c.DisplayName() } if c.Flags().ShorthandLookup("v") == nil { c.Flags().BoolP("version", "v", false, usage) @@ -1239,9 +1270,9 @@ func (c *Command) InitDefaultHelpCmd() { Use: "help [command]", Short: "Help about any command", Long: `Help provides help for any command in the application. -Simply type ` + c.displayName() + ` help [path to command] for full details.`, - ValidArgsFunction: func(c *Command, args []string, toComplete string) ([]string, ShellCompDirective) { - var completions []string +Simply type ` + c.DisplayName() + ` help [path to command] for full details.`, + ValidArgsFunction: func(c *Command, args []string, toComplete string) ([]Completion, ShellCompDirective) { + var completions []Completion cmd, _, e := c.Root().Find(args) if e != nil { return nil, ShellCompDirectiveNoFileComp @@ -1253,7 +1284,7 @@ Simply type ` + c.displayName() + ` help [path to command] for full details.`, for _, subCmd := range cmd.Commands() { if subCmd.IsAvailableCommand() || subCmd == cmd.helpCommand { if strings.HasPrefix(subCmd.Name(), toComplete) { - completions = append(completions, fmt.Sprintf("%s\t%s", subCmd.Name(), subCmd.Short)) + completions = append(completions, CompletionWithDesc(subCmd.Name(), subCmd.Short)) } } } @@ -1430,10 +1461,12 @@ func (c *Command) CommandPath() string { if c.HasParent() { return c.Parent().CommandPath() + " " + c.Name() } - return c.displayName() + return c.DisplayName() } -func (c *Command) displayName() string { +// DisplayName returns the name to display in help text. Returns command Name() +// If CommandDisplayNameAnnoation is not set +func (c *Command) DisplayName() string { if displayName, ok := c.Annotations[CommandDisplayNameAnnotation]; ok { return displayName } @@ -1443,7 +1476,7 @@ func (c *Command) displayName() string { // UseLine puts out the full usage for a given command (including parents). func (c *Command) UseLine() string { var useline string - use := strings.Replace(c.Use, c.Name(), c.displayName(), 1) + use := strings.Replace(c.Use, c.Name(), c.DisplayName(), 1) if c.HasParent() { useline = c.parent.CommandPath() + " " + use } else { @@ -1649,7 +1682,7 @@ func (c *Command) GlobalNormalizationFunc() func(f *flag.FlagSet, name string) f // to this command (local and persistent declared here and by all parents). func (c *Command) Flags() *flag.FlagSet { if c.flags == nil { - c.flags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.flags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) if c.flagErrorBuf == nil { c.flagErrorBuf = new(bytes.Buffer) } @@ -1664,7 +1697,7 @@ func (c *Command) Flags() *flag.FlagSet { func (c *Command) LocalNonPersistentFlags() *flag.FlagSet { persistentFlags := c.PersistentFlags() - out := flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + out := flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) c.LocalFlags().VisitAll(func(f *flag.Flag) { if persistentFlags.Lookup(f.Name) == nil { out.AddFlag(f) @@ -1679,7 +1712,7 @@ func (c *Command) LocalFlags() *flag.FlagSet { c.mergePersistentFlags() if c.lflags == nil { - c.lflags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.lflags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) if c.flagErrorBuf == nil { c.flagErrorBuf = new(bytes.Buffer) } @@ -1707,7 +1740,7 @@ func (c *Command) InheritedFlags() *flag.FlagSet { c.mergePersistentFlags() if c.iflags == nil { - c.iflags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.iflags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) if c.flagErrorBuf == nil { c.flagErrorBuf = new(bytes.Buffer) } @@ -1736,7 +1769,7 @@ func (c *Command) NonInheritedFlags() *flag.FlagSet { // PersistentFlags returns the persistent FlagSet specifically set in the current command. func (c *Command) PersistentFlags() *flag.FlagSet { if c.pflags == nil { - c.pflags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.pflags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) if c.flagErrorBuf == nil { c.flagErrorBuf = new(bytes.Buffer) } @@ -1749,9 +1782,9 @@ func (c *Command) PersistentFlags() *flag.FlagSet { func (c *Command) ResetFlags() { c.flagErrorBuf = new(bytes.Buffer) c.flagErrorBuf.Reset() - c.flags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.flags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) c.flags.SetOutput(c.flagErrorBuf) - c.pflags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.pflags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) c.pflags.SetOutput(c.flagErrorBuf) c.lflags = nil @@ -1868,7 +1901,7 @@ func (c *Command) mergePersistentFlags() { // If c.parentsPflags == nil, it makes new. func (c *Command) updateParentsPflags() { if c.parentsPflags == nil { - c.parentsPflags = flag.NewFlagSet(c.displayName(), flag.ContinueOnError) + c.parentsPflags = flag.NewFlagSet(c.DisplayName(), flag.ContinueOnError) c.parentsPflags.SetOutput(c.flagErrorBuf) c.parentsPflags.SortFlags = false } @@ -1894,3 +1927,141 @@ func commandNameMatches(s string, t string) bool { return s == t } + +// tmplFunc holds a template and a function that will execute said template. +type tmplFunc struct { + tmpl string + fn func(io.Writer, interface{}) error +} + +var defaultUsageTemplate = `Usage:{{if .Runnable}} + {{.UseLine}}{{end}}{{if .HasAvailableSubCommands}} + {{.CommandPath}} [command]{{end}}{{if gt (len .Aliases) 0}} + +Aliases: + {{.NameAndAliases}}{{end}}{{if .HasExample}} + +Examples: +{{.Example}}{{end}}{{if .HasAvailableSubCommands}}{{$cmds := .Commands}}{{if eq (len .Groups) 0}} + +Available Commands:{{range $cmds}}{{if (or .IsAvailableCommand (eq .Name "help"))}} + {{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{else}}{{range $group := .Groups}} + +{{.Title}}{{range $cmds}}{{if (and (eq .GroupID $group.ID) (or .IsAvailableCommand (eq .Name "help")))}} + {{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{if not .AllChildCommandsHaveGroup}} + +Additional Commands:{{range $cmds}}{{if (and (eq .GroupID "") (or .IsAvailableCommand (eq .Name "help")))}} + {{rpad .Name .NamePadding }} {{.Short}}{{end}}{{end}}{{end}}{{end}}{{end}}{{if .HasAvailableLocalFlags}} + +Flags: +{{.LocalFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasAvailableInheritedFlags}} + +Global Flags: +{{.InheritedFlags.FlagUsages | trimTrailingWhitespaces}}{{end}}{{if .HasHelpSubCommands}} + +Additional help topics:{{range .Commands}}{{if .IsAdditionalHelpTopicCommand}} + {{rpad .CommandPath .CommandPathPadding}} {{.Short}}{{end}}{{end}}{{end}}{{if .HasAvailableSubCommands}} + +Use "{{.CommandPath}} [command] --help" for more information about a command.{{end}} +` + +// defaultUsageFunc is equivalent to executing defaultUsageTemplate. The two should be changed in sync. +func defaultUsageFunc(w io.Writer, in interface{}) error { + c := in.(*Command) + fmt.Fprint(w, "Usage:") + if c.Runnable() { + fmt.Fprintf(w, "\n %s", c.UseLine()) + } + if c.HasAvailableSubCommands() { + fmt.Fprintf(w, "\n %s [command]", c.CommandPath()) + } + if len(c.Aliases) > 0 { + fmt.Fprintf(w, "\n\nAliases:\n") + fmt.Fprintf(w, " %s", c.NameAndAliases()) + } + if c.HasExample() { + fmt.Fprintf(w, "\n\nExamples:\n") + fmt.Fprintf(w, "%s", c.Example) + } + if c.HasAvailableSubCommands() { + cmds := c.Commands() + if len(c.Groups()) == 0 { + fmt.Fprintf(w, "\n\nAvailable Commands:") + for _, subcmd := range cmds { + if subcmd.IsAvailableCommand() || subcmd.Name() == helpCommandName { + fmt.Fprintf(w, "\n %s %s", rpad(subcmd.Name(), subcmd.NamePadding()), subcmd.Short) + } + } + } else { + for _, group := range c.Groups() { + fmt.Fprintf(w, "\n\n%s", group.Title) + for _, subcmd := range cmds { + if subcmd.GroupID == group.ID && (subcmd.IsAvailableCommand() || subcmd.Name() == helpCommandName) { + fmt.Fprintf(w, "\n %s %s", rpad(subcmd.Name(), subcmd.NamePadding()), subcmd.Short) + } + } + } + if !c.AllChildCommandsHaveGroup() { + fmt.Fprintf(w, "\n\nAdditional Commands:") + for _, subcmd := range cmds { + if subcmd.GroupID == "" && (subcmd.IsAvailableCommand() || subcmd.Name() == helpCommandName) { + fmt.Fprintf(w, "\n %s %s", rpad(subcmd.Name(), subcmd.NamePadding()), subcmd.Short) + } + } + } + } + } + if c.HasAvailableLocalFlags() { + fmt.Fprintf(w, "\n\nFlags:\n") + fmt.Fprint(w, trimRightSpace(c.LocalFlags().FlagUsages())) + } + if c.HasAvailableInheritedFlags() { + fmt.Fprintf(w, "\n\nGlobal Flags:\n") + fmt.Fprint(w, trimRightSpace(c.InheritedFlags().FlagUsages())) + } + if c.HasHelpSubCommands() { + fmt.Fprintf(w, "\n\nAdditional help topcis:") + for _, subcmd := range c.Commands() { + if subcmd.IsAdditionalHelpTopicCommand() { + fmt.Fprintf(w, "\n %s %s", rpad(subcmd.CommandPath(), subcmd.CommandPathPadding()), subcmd.Short) + } + } + } + if c.HasAvailableSubCommands() { + fmt.Fprintf(w, "\n\nUse \"%s [command] --help\" for more information about a command.", c.CommandPath()) + } + fmt.Fprintln(w) + return nil +} + +var defaultHelpTemplate = `{{with (or .Long .Short)}}{{. | trimTrailingWhitespaces}} + +{{end}}{{if or .Runnable .HasSubCommands}}{{.UsageString}}{{end}}` + +// defaultHelpFunc is equivalent to executing defaultHelpTemplate. The two should be changed in sync. +func defaultHelpFunc(w io.Writer, in interface{}) error { + c := in.(*Command) + usage := c.Long + if usage == "" { + usage = c.Short + } + usage = trimRightSpace(usage) + if usage != "" { + fmt.Fprintln(w, usage) + fmt.Fprintln(w) + } + if c.Runnable() || c.HasSubCommands() { + fmt.Fprint(w, c.UsageString()) + } + return nil +} + +var defaultVersionTemplate = `{{with .DisplayName}}{{printf "%s " .}}{{end}}{{printf "version %s" .Version}} +` + +// defaultVersionFunc is equivalent to executing defaultVersionTemplate. The two should be changed in sync. +func defaultVersionFunc(w io.Writer, in interface{}) error { + c := in.(*Command) + _, err := fmt.Fprintf(w, "%s version %s\n", c.DisplayName(), c.Version) + return err +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/completions.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/completions.go index c0c08b05721..a1752f76317 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/completions.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/completions.go @@ -35,7 +35,7 @@ const ( ) // Global map of flag completion functions. Make sure to use flagCompletionMutex before you try to read and write from it. -var flagCompletionFunctions = map[*pflag.Flag]func(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective){} +var flagCompletionFunctions = map[*pflag.Flag]CompletionFunc{} // lock for reading and writing from flagCompletionFunctions var flagCompletionMutex = &sync.RWMutex{} @@ -117,22 +117,50 @@ type CompletionOptions struct { HiddenDefaultCmd bool } +// Completion is a string that can be used for completions +// +// two formats are supported: +// - the completion choice +// - the completion choice with a textual description (separated by a TAB). +// +// [CompletionWithDesc] can be used to create a completion string with a textual description. +// +// Note: Go type alias is used to provide a more descriptive name in the documentation, but any string can be used. +type Completion = string + +// CompletionFunc is a function that provides completion results. +type CompletionFunc = func(cmd *Command, args []string, toComplete string) ([]Completion, ShellCompDirective) + +// CompletionWithDesc returns a [Completion] with a description by using the TAB delimited format. +func CompletionWithDesc(choice string, description string) Completion { + return choice + "\t" + description +} + // NoFileCompletions can be used to disable file completion for commands that should // not trigger file completions. -func NoFileCompletions(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective) { +// +// This method satisfies [CompletionFunc]. +// It can be used with [Command.RegisterFlagCompletionFunc] and for [Command.ValidArgsFunction]. +func NoFileCompletions(cmd *Command, args []string, toComplete string) ([]Completion, ShellCompDirective) { return nil, ShellCompDirectiveNoFileComp } // FixedCompletions can be used to create a completion function which always // returns the same results. -func FixedCompletions(choices []string, directive ShellCompDirective) func(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective) { - return func(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective) { +// +// This method returns a function that satisfies [CompletionFunc] +// It can be used with [Command.RegisterFlagCompletionFunc] and for [Command.ValidArgsFunction]. +func FixedCompletions(choices []Completion, directive ShellCompDirective) CompletionFunc { + return func(cmd *Command, args []string, toComplete string) ([]Completion, ShellCompDirective) { return choices, directive } } // RegisterFlagCompletionFunc should be called to register a function to provide completion for a flag. -func (c *Command) RegisterFlagCompletionFunc(flagName string, f func(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective)) error { +// +// You can use pre-defined completion functions such as [FixedCompletions] or [NoFileCompletions], +// or you can define your own. +func (c *Command) RegisterFlagCompletionFunc(flagName string, f CompletionFunc) error { flag := c.Flag(flagName) if flag == nil { return fmt.Errorf("RegisterFlagCompletionFunc: flag '%s' does not exist", flagName) @@ -148,7 +176,7 @@ func (c *Command) RegisterFlagCompletionFunc(flagName string, f func(cmd *Comman } // GetFlagCompletionFunc returns the completion function for the given flag of the command, if available. -func (c *Command) GetFlagCompletionFunc(flagName string) (func(*Command, []string, string) ([]string, ShellCompDirective), bool) { +func (c *Command) GetFlagCompletionFunc(flagName string) (CompletionFunc, bool) { flag := c.Flag(flagName) if flag == nil { return nil, false @@ -270,7 +298,15 @@ func (c *Command) initCompleteCmd(args []string) { } } -func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDirective, error) { +// SliceValue is a reduced version of [pflag.SliceValue]. It is used to detect +// flags that accept multiple values and therefore can provide completion +// multiple times. +type SliceValue interface { + // GetSlice returns the flag value list as an array of strings. + GetSlice() []string +} + +func (c *Command) getCompletions(args []string) (*Command, []Completion, ShellCompDirective, error) { // The last argument, which is not completely typed by the user, // should not be part of the list of arguments toComplete := args[len(args)-1] @@ -298,7 +334,7 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi } if err != nil { // Unable to find the real command. E.g., someInvalidCmd - return c, []string{}, ShellCompDirectiveDefault, fmt.Errorf("unable to find a command for arguments: %v", trimmedArgs) + return c, []Completion{}, ShellCompDirectiveDefault, fmt.Errorf("unable to find a command for arguments: %v", trimmedArgs) } finalCmd.ctx = c.ctx @@ -328,7 +364,7 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi // Parse the flags early so we can check if required flags are set if err = finalCmd.ParseFlags(finalArgs); err != nil { - return finalCmd, []string{}, ShellCompDirectiveDefault, fmt.Errorf("Error while parsing flags from args %v: %s", finalArgs, err.Error()) + return finalCmd, []Completion{}, ShellCompDirectiveDefault, fmt.Errorf("Error while parsing flags from args %v: %s", finalArgs, err.Error()) } realArgCount := finalCmd.Flags().NArg() @@ -340,14 +376,14 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi if flagErr != nil { // If error type is flagCompError and we don't want flagCompletion we should ignore the error if _, ok := flagErr.(*flagCompError); !(ok && !flagCompletion) { - return finalCmd, []string{}, ShellCompDirectiveDefault, flagErr + return finalCmd, []Completion{}, ShellCompDirectiveDefault, flagErr } } // Look for the --help or --version flags. If they are present, // there should be no further completions. if helpOrVersionFlagPresent(finalCmd) { - return finalCmd, []string{}, ShellCompDirectiveNoFileComp, nil + return finalCmd, []Completion{}, ShellCompDirectiveNoFileComp, nil } // We only remove the flags from the arguments if DisableFlagParsing is not set. @@ -376,11 +412,11 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi return finalCmd, subDir, ShellCompDirectiveFilterDirs, nil } // Directory completion - return finalCmd, []string{}, ShellCompDirectiveFilterDirs, nil + return finalCmd, []Completion{}, ShellCompDirectiveFilterDirs, nil } } - var completions []string + var completions []Completion var directive ShellCompDirective // Enforce flag groups before doing flag completions @@ -399,10 +435,14 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi // If we have not found any required flags, only then can we show regular flags if len(completions) == 0 { doCompleteFlags := func(flag *pflag.Flag) { - if !flag.Changed || + _, acceptsMultiple := flag.Value.(SliceValue) + acceptsMultiple = acceptsMultiple || strings.Contains(flag.Value.Type(), "Slice") || - strings.Contains(flag.Value.Type(), "Array") { - // If the flag is not already present, or if it can be specified multiple times (Array or Slice) + strings.Contains(flag.Value.Type(), "Array") || + strings.HasPrefix(flag.Value.Type(), "stringTo") + + if !flag.Changed || acceptsMultiple { + // If the flag is not already present, or if it can be specified multiple times (Array, Slice, or stringTo) // we suggest it as a completion completions = append(completions, getFlagNameCompletions(flag, toComplete)...) } @@ -462,7 +502,7 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi for _, subCmd := range finalCmd.Commands() { if subCmd.IsAvailableCommand() || subCmd == finalCmd.helpCommand { if strings.HasPrefix(subCmd.Name(), toComplete) { - completions = append(completions, fmt.Sprintf("%s\t%s", subCmd.Name(), subCmd.Short)) + completions = append(completions, CompletionWithDesc(subCmd.Name(), subCmd.Short)) } directive = ShellCompDirectiveNoFileComp } @@ -507,7 +547,7 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi } // Find the completion function for the flag or command - var completionFn func(cmd *Command, args []string, toComplete string) ([]string, ShellCompDirective) + var completionFn CompletionFunc if flag != nil && flagCompletion { flagCompletionMutex.RLock() completionFn = flagCompletionFunctions[flag] @@ -518,7 +558,7 @@ func (c *Command) getCompletions(args []string) (*Command, []string, ShellCompDi if completionFn != nil { // Go custom completion defined for this flag or command. // Call the registered completion function to get the completions. - var comps []string + var comps []Completion comps, directive = completionFn(finalCmd, finalArgs, toComplete) completions = append(completions, comps...) } @@ -531,23 +571,23 @@ func helpOrVersionFlagPresent(cmd *Command) bool { len(versionFlag.Annotations[FlagSetByCobraAnnotation]) > 0 && versionFlag.Changed { return true } - if helpFlag := cmd.Flags().Lookup("help"); helpFlag != nil && + if helpFlag := cmd.Flags().Lookup(helpFlagName); helpFlag != nil && len(helpFlag.Annotations[FlagSetByCobraAnnotation]) > 0 && helpFlag.Changed { return true } return false } -func getFlagNameCompletions(flag *pflag.Flag, toComplete string) []string { +func getFlagNameCompletions(flag *pflag.Flag, toComplete string) []Completion { if nonCompletableFlag(flag) { - return []string{} + return []Completion{} } - var completions []string + var completions []Completion flagName := "--" + flag.Name if strings.HasPrefix(flagName, toComplete) { // Flag without the = - completions = append(completions, fmt.Sprintf("%s\t%s", flagName, flag.Usage)) + completions = append(completions, CompletionWithDesc(flagName, flag.Usage)) // Why suggest both long forms: --flag and --flag= ? // This forces the user to *always* have to type either an = or a space after the flag name. @@ -559,20 +599,20 @@ func getFlagNameCompletions(flag *pflag.Flag, toComplete string) []string { // if len(flag.NoOptDefVal) == 0 { // // Flag requires a value, so it can be suffixed with = // flagName += "=" - // completions = append(completions, fmt.Sprintf("%s\t%s", flagName, flag.Usage)) + // completions = append(completions, CompletionWithDesc(flagName, flag.Usage)) // } } flagName = "-" + flag.Shorthand if len(flag.Shorthand) > 0 && strings.HasPrefix(flagName, toComplete) { - completions = append(completions, fmt.Sprintf("%s\t%s", flagName, flag.Usage)) + completions = append(completions, CompletionWithDesc(flagName, flag.Usage)) } return completions } -func completeRequireFlags(finalCmd *Command, toComplete string) []string { - var completions []string +func completeRequireFlags(finalCmd *Command, toComplete string) []Completion { + var completions []Completion doCompleteRequiredFlags := func(flag *pflag.Flag) { if _, present := flag.Annotations[BashCompOneRequiredFlag]; present { @@ -687,8 +727,8 @@ func checkIfFlagCompletion(finalCmd *Command, args []string, lastArg string) (*p // 1- the feature has been explicitly disabled by the program, // 2- c has no subcommands (to avoid creating one), // 3- c already has a 'completion' command provided by the program. -func (c *Command) InitDefaultCompletionCmd() { - if c.CompletionOptions.DisableDefaultCmd || !c.HasSubCommands() { +func (c *Command) InitDefaultCompletionCmd(args ...string) { + if c.CompletionOptions.DisableDefaultCmd { return } @@ -701,6 +741,16 @@ func (c *Command) InitDefaultCompletionCmd() { haveNoDescFlag := !c.CompletionOptions.DisableNoDescFlag && !c.CompletionOptions.DisableDescriptions + // Special case to know if there are sub-commands or not. + hasSubCommands := false + for _, cmd := range c.commands { + if cmd.Name() != ShellCompRequestCmd && cmd.Name() != helpCommandName { + // We found a real sub-command (not 'help' or '__complete') + hasSubCommands = true + break + } + } + completionCmd := &Command{ Use: compCmdName, Short: "Generate the autocompletion script for the specified shell", @@ -714,6 +764,22 @@ See each sub-command's help for details on how to use the generated script. } c.AddCommand(completionCmd) + if !hasSubCommands { + // If the 'completion' command will be the only sub-command, + // we only create it if it is actually being called. + // This avoids breaking programs that would suddenly find themselves with + // a subcommand, which would prevent them from accepting arguments. + // We also create the 'completion' command if the user is triggering + // shell completion for it (prog __complete completion '') + subCmd, cmdArgs, err := c.Find(args) + if err != nil || subCmd.Name() != compCmdName && + !(subCmd.Name() == ShellCompRequestCmd && len(cmdArgs) > 1 && cmdArgs[0] == compCmdName) { + // The completion command is not being called or being completed so we remove it. + c.RemoveCommand(completionCmd) + return + } + } + out := c.OutOrStdout() noDesc := c.CompletionOptions.DisableDescriptions shortDesc := "Generate the autocompletion script for %s" diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/powershell_completions.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/powershell_completions.go index a830b7bcad2..746dcb92e3e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/powershell_completions.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/cobra/powershell_completions.go @@ -162,7 +162,10 @@ filter __%[1]s_escapeStringWithSpecialChars { if (-Not $Description) { $Description = " " } - @{Name="$Name";Description="$Description"} + New-Object -TypeName PSCustomObject -Property @{ + Name = "$Name" + Description = "$Description" + } } @@ -240,7 +243,12 @@ filter __%[1]s_escapeStringWithSpecialChars { __%[1]s_debug "Only one completion left" # insert space after value - [System.Management.Automation.CompletionResult]::new($($comp.Name | __%[1]s_escapeStringWithSpecialChars) + $Space, "$($comp.Name)", 'ParameterValue', "$($comp.Description)") + $CompletionText = $($comp.Name | __%[1]s_escapeStringWithSpecialChars) + $Space + if ($ExecutionContext.SessionState.LanguageMode -eq "FullLanguage"){ + [System.Management.Automation.CompletionResult]::new($CompletionText, "$($comp.Name)", 'ParameterValue', "$($comp.Description)") + } else { + $CompletionText + } } else { # Add the proper number of spaces to align the descriptions @@ -255,7 +263,12 @@ filter __%[1]s_escapeStringWithSpecialChars { $Description = " ($($comp.Description))" } - [System.Management.Automation.CompletionResult]::new("$($comp.Name)$Description", "$($comp.Name)$Description", 'ParameterValue', "$($comp.Description)") + $CompletionText = "$($comp.Name)$Description" + if ($ExecutionContext.SessionState.LanguageMode -eq "FullLanguage"){ + [System.Management.Automation.CompletionResult]::new($CompletionText, "$($comp.Name)$Description", 'ParameterValue', "$($comp.Description)") + } else { + $CompletionText + } } } @@ -264,7 +277,13 @@ filter __%[1]s_escapeStringWithSpecialChars { # insert space after value # MenuComplete will automatically show the ToolTip of # the highlighted value at the bottom of the suggestions. - [System.Management.Automation.CompletionResult]::new($($comp.Name | __%[1]s_escapeStringWithSpecialChars) + $Space, "$($comp.Name)", 'ParameterValue', "$($comp.Description)") + + $CompletionText = $($comp.Name | __%[1]s_escapeStringWithSpecialChars) + $Space + if ($ExecutionContext.SessionState.LanguageMode -eq "FullLanguage"){ + [System.Management.Automation.CompletionResult]::new($CompletionText, "$($comp.Name)", 'ParameterValue', "$($comp.Description)") + } else { + $CompletionText + } } # TabCompleteNext and in case we get something unknown @@ -272,7 +291,13 @@ filter __%[1]s_escapeStringWithSpecialChars { # Like MenuComplete but we don't want to add a space here because # the user need to press space anyway to get the completion. # Description will not be shown because that's not possible with TabCompleteNext - [System.Management.Automation.CompletionResult]::new($($comp.Name | __%[1]s_escapeStringWithSpecialChars), "$($comp.Name)", 'ParameterValue', "$($comp.Description)") + + $CompletionText = $($comp.Name | __%[1]s_escapeStringWithSpecialChars) + if ($ExecutionContext.SessionState.LanguageMode -eq "FullLanguage"){ + [System.Management.Automation.CompletionResult]::new($CompletionText, "$($comp.Name)", 'ParameterValue', "$($comp.Description)") + } else { + $CompletionText + } } } diff --git a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.editorconfig b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.editorconfig similarity index 69% rename from cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.editorconfig rename to cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.editorconfig index fad895851e5..4492e9f9fe1 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/fsnotify/fsnotify/.editorconfig +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.editorconfig @@ -1,12 +1,12 @@ root = true -[*.go] -indent_style = tab +[*] +charset = utf-8 +end_of_line = lf indent_size = 4 -insert_final_newline = true - -[*.{yml,yaml}] indent_style = space -indent_size = 2 insert_final_newline = true trim_trailing_whitespace = true + +[*.go] +indent_style = tab diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.golangci.yaml b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.golangci.yaml new file mode 100644 index 00000000000..b274f248451 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/.golangci.yaml @@ -0,0 +1,4 @@ +linters: + disable-all: true + enable: + - nolintlint diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/flag.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/flag.go index 24a5036e95b..7c058de3744 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/flag.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/flag.go @@ -160,7 +160,7 @@ type FlagSet struct { args []string // arguments after flags argsLenAtDash int // len(args) when a '--' was located when parsing, or -1 if no -- errorHandling ErrorHandling - output io.Writer // nil means stderr; use out() accessor + output io.Writer // nil means stderr; use Output() accessor interspersed bool // allow interspersed option/non-option args normalizeNameFunc func(f *FlagSet, name string) NormalizedName @@ -255,13 +255,20 @@ func (f *FlagSet) normalizeFlagName(name string) NormalizedName { return n(f, name) } -func (f *FlagSet) out() io.Writer { +// Output returns the destination for usage and error messages. os.Stderr is returned if +// output was not set or was set to nil. +func (f *FlagSet) Output() io.Writer { if f.output == nil { return os.Stderr } return f.output } +// Name returns the name of the flag set. +func (f *FlagSet) Name() string { + return f.name +} + // SetOutput sets the destination for usage and error messages. // If output is nil, os.Stderr is used. func (f *FlagSet) SetOutput(output io.Writer) { @@ -358,7 +365,7 @@ func (f *FlagSet) ShorthandLookup(name string) *Flag { } if len(name) > 1 { msg := fmt.Sprintf("can not look up shorthand which is more than one ASCII character: %q", name) - fmt.Fprintf(f.out(), msg) + fmt.Fprintf(f.Output(), msg) panic(msg) } c := name[0] @@ -482,7 +489,7 @@ func (f *FlagSet) Set(name, value string) error { } if flag.Deprecated != "" { - fmt.Fprintf(f.out(), "Flag --%s has been deprecated, %s\n", flag.Name, flag.Deprecated) + fmt.Fprintf(f.Output(), "Flag --%s has been deprecated, %s\n", flag.Name, flag.Deprecated) } return nil } @@ -523,7 +530,7 @@ func Set(name, value string) error { // otherwise, the default values of all defined flags in the set. func (f *FlagSet) PrintDefaults() { usages := f.FlagUsages() - fmt.Fprint(f.out(), usages) + fmt.Fprint(f.Output(), usages) } // defaultIsZeroValue returns true if the default value for this flag represents @@ -758,7 +765,7 @@ func PrintDefaults() { // defaultUsage is the default function to print a usage message. func defaultUsage(f *FlagSet) { - fmt.Fprintf(f.out(), "Usage of %s:\n", f.name) + fmt.Fprintf(f.Output(), "Usage of %s:\n", f.name) f.PrintDefaults() } @@ -844,7 +851,7 @@ func (f *FlagSet) AddFlag(flag *Flag) { _, alreadyThere := f.formal[normalizedFlagName] if alreadyThere { msg := fmt.Sprintf("%s flag redefined: %s", f.name, flag.Name) - fmt.Fprintln(f.out(), msg) + fmt.Fprintln(f.Output(), msg) panic(msg) // Happens only if flags are declared with identical names } if f.formal == nil { @@ -860,7 +867,7 @@ func (f *FlagSet) AddFlag(flag *Flag) { } if len(flag.Shorthand) > 1 { msg := fmt.Sprintf("%q shorthand is more than one ASCII character", flag.Shorthand) - fmt.Fprintf(f.out(), msg) + fmt.Fprintf(f.Output(), msg) panic(msg) } if f.shorthands == nil { @@ -870,7 +877,7 @@ func (f *FlagSet) AddFlag(flag *Flag) { used, alreadyThere := f.shorthands[c] if alreadyThere { msg := fmt.Sprintf("unable to redefine %q shorthand in %q flagset: it's already used for %q flag", c, f.name, used.Name) - fmt.Fprintf(f.out(), msg) + fmt.Fprintf(f.Output(), msg) panic(msg) } f.shorthands[c] = flag @@ -909,7 +916,7 @@ func VarP(value Value, name, shorthand, usage string) { func (f *FlagSet) failf(format string, a ...interface{}) error { err := fmt.Errorf(format, a...) if f.errorHandling != ContinueOnError { - fmt.Fprintln(f.out(), err) + fmt.Fprintln(f.Output(), err) f.usage() } return err @@ -1060,7 +1067,7 @@ func (f *FlagSet) parseSingleShortArg(shorthands string, args []string, fn parse } if flag.ShorthandDeprecated != "" { - fmt.Fprintf(f.out(), "Flag shorthand -%s has been deprecated, %s\n", flag.Shorthand, flag.ShorthandDeprecated) + fmt.Fprintf(f.Output(), "Flag shorthand -%s has been deprecated, %s\n", flag.Shorthand, flag.ShorthandDeprecated) } err = fn(flag, value) diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ip.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ip.go index 3d414ba69fe..06b8bcb5721 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ip.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ip.go @@ -16,6 +16,9 @@ func newIPValue(val net.IP, p *net.IP) *ipValue { func (i *ipValue) String() string { return net.IP(*i).String() } func (i *ipValue) Set(s string) error { + if s == "" { + return nil + } ip := net.ParseIP(strings.TrimSpace(s)) if ip == nil { return fmt.Errorf("failed to parse IP: %q", s) diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ipnet_slice.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ipnet_slice.go new file mode 100644 index 00000000000..6b541aa8798 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/ipnet_slice.go @@ -0,0 +1,147 @@ +package pflag + +import ( + "fmt" + "io" + "net" + "strings" +) + +// -- ipNetSlice Value +type ipNetSliceValue struct { + value *[]net.IPNet + changed bool +} + +func newIPNetSliceValue(val []net.IPNet, p *[]net.IPNet) *ipNetSliceValue { + ipnsv := new(ipNetSliceValue) + ipnsv.value = p + *ipnsv.value = val + return ipnsv +} + +// Set converts, and assigns, the comma-separated IPNet argument string representation as the []net.IPNet value of this flag. +// If Set is called on a flag that already has a []net.IPNet assigned, the newly converted values will be appended. +func (s *ipNetSliceValue) Set(val string) error { + + // remove all quote characters + rmQuote := strings.NewReplacer(`"`, "", `'`, "", "`", "") + + // read flag arguments with CSV parser + ipNetStrSlice, err := readAsCSV(rmQuote.Replace(val)) + if err != nil && err != io.EOF { + return err + } + + // parse ip values into slice + out := make([]net.IPNet, 0, len(ipNetStrSlice)) + for _, ipNetStr := range ipNetStrSlice { + _, n, err := net.ParseCIDR(strings.TrimSpace(ipNetStr)) + if err != nil { + return fmt.Errorf("invalid string being converted to CIDR: %s", ipNetStr) + } + out = append(out, *n) + } + + if !s.changed { + *s.value = out + } else { + *s.value = append(*s.value, out...) + } + + s.changed = true + + return nil +} + +// Type returns a string that uniquely represents this flag's type. +func (s *ipNetSliceValue) Type() string { + return "ipNetSlice" +} + +// String defines a "native" format for this net.IPNet slice flag value. +func (s *ipNetSliceValue) String() string { + + ipNetStrSlice := make([]string, len(*s.value)) + for i, n := range *s.value { + ipNetStrSlice[i] = n.String() + } + + out, _ := writeAsCSV(ipNetStrSlice) + return "[" + out + "]" +} + +func ipNetSliceConv(val string) (interface{}, error) { + val = strings.Trim(val, "[]") + // Emtpy string would cause a slice with one (empty) entry + if len(val) == 0 { + return []net.IPNet{}, nil + } + ss := strings.Split(val, ",") + out := make([]net.IPNet, len(ss)) + for i, sval := range ss { + _, n, err := net.ParseCIDR(strings.TrimSpace(sval)) + if err != nil { + return nil, fmt.Errorf("invalid string being converted to CIDR: %s", sval) + } + out[i] = *n + } + return out, nil +} + +// GetIPNetSlice returns the []net.IPNet value of a flag with the given name +func (f *FlagSet) GetIPNetSlice(name string) ([]net.IPNet, error) { + val, err := f.getFlagType(name, "ipNetSlice", ipNetSliceConv) + if err != nil { + return []net.IPNet{}, err + } + return val.([]net.IPNet), nil +} + +// IPNetSliceVar defines a ipNetSlice flag with specified name, default value, and usage string. +// The argument p points to a []net.IPNet variable in which to store the value of the flag. +func (f *FlagSet) IPNetSliceVar(p *[]net.IPNet, name string, value []net.IPNet, usage string) { + f.VarP(newIPNetSliceValue(value, p), name, "", usage) +} + +// IPNetSliceVarP is like IPNetSliceVar, but accepts a shorthand letter that can be used after a single dash. +func (f *FlagSet) IPNetSliceVarP(p *[]net.IPNet, name, shorthand string, value []net.IPNet, usage string) { + f.VarP(newIPNetSliceValue(value, p), name, shorthand, usage) +} + +// IPNetSliceVar defines a []net.IPNet flag with specified name, default value, and usage string. +// The argument p points to a []net.IPNet variable in which to store the value of the flag. +func IPNetSliceVar(p *[]net.IPNet, name string, value []net.IPNet, usage string) { + CommandLine.VarP(newIPNetSliceValue(value, p), name, "", usage) +} + +// IPNetSliceVarP is like IPNetSliceVar, but accepts a shorthand letter that can be used after a single dash. +func IPNetSliceVarP(p *[]net.IPNet, name, shorthand string, value []net.IPNet, usage string) { + CommandLine.VarP(newIPNetSliceValue(value, p), name, shorthand, usage) +} + +// IPNetSlice defines a []net.IPNet flag with specified name, default value, and usage string. +// The return value is the address of a []net.IPNet variable that stores the value of that flag. +func (f *FlagSet) IPNetSlice(name string, value []net.IPNet, usage string) *[]net.IPNet { + p := []net.IPNet{} + f.IPNetSliceVarP(&p, name, "", value, usage) + return &p +} + +// IPNetSliceP is like IPNetSlice, but accepts a shorthand letter that can be used after a single dash. +func (f *FlagSet) IPNetSliceP(name, shorthand string, value []net.IPNet, usage string) *[]net.IPNet { + p := []net.IPNet{} + f.IPNetSliceVarP(&p, name, shorthand, value, usage) + return &p +} + +// IPNetSlice defines a []net.IPNet flag with specified name, default value, and usage string. +// The return value is the address of a []net.IP variable that stores the value of the flag. +func IPNetSlice(name string, value []net.IPNet, usage string) *[]net.IPNet { + return CommandLine.IPNetSliceP(name, "", value, usage) +} + +// IPNetSliceP is like IPNetSlice, but accepts a shorthand letter that can be used after a single dash. +func IPNetSliceP(name, shorthand string, value []net.IPNet, usage string) *[]net.IPNet { + return CommandLine.IPNetSliceP(name, shorthand, value, usage) +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/string_array.go b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/string_array.go index 4894af81802..d1ff0a96ba0 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/string_array.go +++ b/cluster-api/providers/vsphere/vendor/github.com/spf13/pflag/string_array.go @@ -31,11 +31,7 @@ func (s *stringArrayValue) Append(val string) error { func (s *stringArrayValue) Replace(val []string) error { out := make([]string, len(val)) for i, d := range val { - var err error out[i] = d - if err != nil { - return err - } } *s.value = out return nil diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/addressbinding_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/addressbinding_types.go index 8faf6c44e4d..7d723012885 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/addressbinding_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/addressbinding_types.go @@ -24,7 +24,7 @@ type AddressBinding struct { metav1.ObjectMeta `json:"metadata,omitempty"` Spec AddressBindingSpec `json:"spec"` - Status AddressBindingStatus `json:"status"` + Status AddressBindingStatus `json:"status,omitempty"` } //+kubebuilder:object:root=true diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/condition_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/condition_types.go index f527118ca0b..a7d31d45a3d 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/condition_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/condition_types.go @@ -8,9 +8,10 @@ import ( type ConditionType string const ( - Ready ConditionType = "Ready" - GatewayConnectionReady ConditionType = "GatewayConnectionReady" - AutoSnatEnabled ConditionType = "AutoSnatEnabled" + Ready ConditionType = "Ready" + GatewayConnectionReady ConditionType = "GatewayConnectionReady" + AutoSnatEnabled ConditionType = "AutoSnatEnabled" + ExternalIPBlocksConfigured ConditionType = "ExternalIPBlocksConfigured" ) // Condition defines condition of custom resource. diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipaddressallocation_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipaddressallocation_types.go index a63f90e0c3d..5e992f28110 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipaddressallocation_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipaddressallocation_types.go @@ -24,7 +24,7 @@ var ( type IPAddressAllocation struct { metav1.TypeMeta `json:",inline"` metav1.ObjectMeta `json:"metadata"` - + Spec IPAddressAllocationSpec `json:"spec"` Status IPAddressAllocationStatus `json:"status,omitempty"` } diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipblocksinfo_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipblocksinfo_types.go index 4cd8f9c16f8..77871d0baff 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipblocksinfo_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/ipblocksinfo_types.go @@ -22,7 +22,7 @@ type IPBlocksInfo struct { ExternalIPCIDRs []string `json:"externalIPCIDRs,omitempty"` // PrivateTGWIPCIDRs is a list of CIDR strings. Each CIDR is a contiguous IP address // spaces represented by network address and prefix length. The visibility of the - // IPBlocks is PrivateTWG. Only IPBlocks in default project will be included. + // IPBlocks is Private Transit Gateway. Only IPBlocks in default project will be included. PrivateTGWIPCIDRs []string `json:"privateTGWIPCIDRs,omitempty"` } diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnet_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnet_types.go index fcd75d7b40a..3e6dca95743 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnet_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnet_types.go @@ -8,18 +8,27 @@ import ( ) type AccessMode string +type DHCPConfigMode string const ( - AccessModePublic string = "Public" - AccessModePrivate string = "Private" - AccessModeProject string = "PrivateTGW" + AccessModePublic string = "Public" + AccessModePrivate string = "Private" + AccessModeProject string = "PrivateTGW" + DHCPConfigModeDeactivated string = "DHCPDeactivated" + DHCPConfigModeServer string = "DHCPServer" + DHCPConfigModeRelay string = "DHCPRelay" ) // SubnetSpec defines the desired state of Subnet. +// +kubebuilder:validation:XValidation:rule="has(oldSelf.subnetDHCPConfig) || !has(self.subnetDHCPConfig) || !has(self.subnetDHCPConfig.mode) || self.subnetDHCPConfig.mode=='DHCPDeactivated'", message="subnetDHCPConfig cannot switch from DHCPDeactivated to other modes" +// +kubebuilder:validation:XValidation:rule="!has(oldSelf.ipv4SubnetSize) || has(self.ipv4SubnetSize)", message="ipv4SubnetSize is required once set" +// +kubebuilder:validation:XValidation:rule="!has(oldSelf.accessMode) || has(self.accessMode)", message="accessMode is required once set" +// +kubebuilder:validation:XValidation:rule="!has(oldSelf.ipAddresses) || has(self.ipAddresses)", message="ipAddresses is required once set" type SubnetSpec struct { // Size of Subnet based upon estimated workload count. // +kubebuilder:validation:Maximum:=65536 // +kubebuilder:validation:Minimum:=16 + // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="Value is immutable" IPv4SubnetSize int `json:"ipv4SubnetSize,omitempty"` // Access mode of Subnet, accessible only from within VPC or from outside VPC. // +kubebuilder:validation:Enum=Private;Public;PrivateTGW @@ -28,9 +37,19 @@ type SubnetSpec struct { // Subnet CIDRS. // +kubebuilder:validation:MinItems=0 // +kubebuilder:validation:MaxItems=2 + // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="Value is immutable" IPAddresses []string `json:"ipAddresses,omitempty"` - // DHCPConfig DHCP configuration. - DHCPConfig DHCPConfig `json:"DHCPConfig,omitempty"` + + // DHCP mode of a SubnetSet cannot switch from DHCPDeactivated to DHCPServer or DHCPRelay. + // If subnetDHCPConfig is not set, the DHCP mode is DHCPDeactivated by default. + // In order to enforce this rule, two XValidation rules are defined. + // The rule in SubnetSetSpec prevents the condition that subnetDHCPConfig is not set in + // old SubnetSetSpec while the new SubnetSetSpec specifies a field other than DHCPDeactivated. + // The rule in SubnetDHCPConfig prevents the mode changing from empty or + // DHCPDeactivated to DHCPServer or DHCPRelay. + + // DHCP configuration for Subnet. + SubnetDHCPConfig SubnetDHCPConfig `json:"subnetDHCPConfig,omitempty"` } // SubnetStatus defines the observed state of Subnet. @@ -67,10 +86,13 @@ type SubnetList struct { Items []Subnet `json:"items"` } -// DHCPConfig is DHCP configuration. -type DHCPConfig struct { - // +kubebuilder:default:=false - EnableDHCP bool `json:"enableDHCP,omitempty"` +// SubnetDHCPConfig is DHCP configuration for Subnet. +type SubnetDHCPConfig struct { + // DHCP Mode. DHCPDeactivated will be used if it is not defined. + // It cannot switch from DHCPDeactivated to DHCPServer or DHCPRelay. + // +kubebuilder:validation:Enum=DHCPServer;DHCPRelay;DHCPDeactivated + // +kubebuilder:validation:XValidation:rule="oldSelf!='DHCPDeactivated' || oldSelf==self", message="subnetDHCPConfig cannot switch from DHCPDeactivated to other modes" + Mode DHCPConfigMode `json:"mode,omitempty"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnetset_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnetset_types.go index 07d5f4b63fa..2c3910793bc 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnetset_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/subnetset_types.go @@ -8,17 +8,29 @@ import ( ) // SubnetSetSpec defines the desired state of SubnetSet. +// +kubebuilder:validation:XValidation:rule="has(oldSelf.subnetDHCPConfig) || !has(self.subnetDHCPConfig) || !has(self.subnetDHCPConfig.mode) || self.subnetDHCPConfig.mode=='DHCPDeactivated'", message="subnetDHCPConfig cannot switch from DHCPDeactivated to other modes" +// +kubebuilder:validation:XValidation:rule="!has(oldSelf.accessMode) || has(self.accessMode)", message="accessMode is required once set" +// +kubebuilder:validation:XValidation:rule="!has(oldSelf.ipv4SubnetSize) || has(self.ipv4SubnetSize)", message="ipv4SubnetSize is required once set" type SubnetSetSpec struct { // Size of Subnet based upon estimated workload count. // +kubebuilder:validation:Maximum:=65536 // +kubebuilder:validation:Minimum:=16 + // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="Value is immutable" IPv4SubnetSize int `json:"ipv4SubnetSize,omitempty"` // Access mode of Subnet, accessible only from within VPC or from outside VPC. // +kubebuilder:validation:Enum=Private;Public;PrivateTGW // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="Value is immutable" AccessMode AccessMode `json:"accessMode,omitempty"` + // DHCP mode of a SubnetSet cannot switch from DHCPDeactivated to DHCPServer or DHCPRelay. + // If subnetDHCPConfig is not set, the DHCP mode is DHCPDeactivated by default. + // In order to enforce this rule, two XValidation rules are defined. + // The rule in SubnetSetSpec prevents the condition that subnetDHCPConfig is not set in + // old SubnetSetSpec while the new SubnetSetSpec specifies a field other than DHCPDeactivated. + // The rule in SubnetDHCPConfig prevents the mode changing from empty or + // DHCPDeactivated to DHCPServer or DHCPRelay. + // DHCPConfig DHCP configuration. - DHCPConfig DHCPConfig `json:"DHCPConfig,omitempty"` + SubnetDHCPConfig SubnetDHCPConfig `json:"subnetDHCPConfig,omitempty"` } // SubnetInfo defines the observed state of a single Subnet of a SubnetSet. diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/vpcnetworkconfiguration_types.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/vpcnetworkconfiguration_types.go index 84682f354e5..68c565433f8 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/vpcnetworkconfiguration_types.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/vpcnetworkconfiguration_types.go @@ -14,13 +14,13 @@ import ( // in a Namespace's VPCNetworkConfiguration, the Namespace will use the value // in the default VPCNetworkConfiguration. type VPCNetworkConfigurationSpec struct { - // NSX path of the VPC the Namespace associated with. + // NSX path of the VPC the Namespace is associated with. // If VPC is set, only defaultIPv4SubnetSize and defaultSubnetAccessMode // take effect, other fields are ignored. // +optional VPC string `json:"vpc,omitempty"` - // NSX Project the Namespace associated with. + // NSX Project the Namespace is associated with. NSXProject string `json:"nsxProject,omitempty"` // VPCConnectivityProfile ID. This profile has configuration related to creating VPC transit gateway attachment. @@ -32,12 +32,15 @@ type VPCNetworkConfigurationSpec struct { // Default size of Subnets. // Defaults to 32. // +kubebuilder:default=32 + // +kubebuilder:validation:Maximum:=65536 + // +kubebuilder:validation:Minimum:=16 DefaultSubnetSize int `json:"defaultSubnetSize,omitempty"` } // VPCNetworkConfigurationStatus defines the observed state of VPCNetworkConfiguration type VPCNetworkConfigurationStatus struct { - // VPCs describes VPC info, now it includes lb Subnet info which are needed for AKO. + // VPCs describes VPC info, now it includes Load Balancer Subnet info which are needed + // for the Avi Kubernetes Operator (AKO). VPCs []VPCInfo `json:"vpcs,omitempty"` // Conditions describe current state of VPCNetworkConfiguration. Conditions []Condition `json:"conditions,omitempty"` @@ -63,8 +66,7 @@ type VPCInfo struct { // VPCNetworkConfiguration is the Schema for the vpcnetworkconfigurations API. // +kubebuilder:resource:scope="Cluster" -// +kubebuilder:printcolumn:name="NSXProject",type=string,JSONPath=`.spec.nsxProject`,description="NSXProject the Namespace associated with" -// +kubebuilder:printcolumn:name="PrivateIPs",type=string,JSONPath=`.spec.privateIPs`,description="PrivateIPs assigned to the Namespace" +// +kubebuilder:printcolumn:name="VPCPath",type=string,JSONPath=`.status.vpcs[0].vpcPath`,description="NSX VPC path the Namespace is associated with" type VPCNetworkConfiguration struct { metav1.TypeMeta `json:",inline"` metav1.ObjectMeta `json:"metadata,omitempty"` diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/zz_generated.deepcopy.go index f55b4c9c651..4cbd75e0f2e 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1/zz_generated.deepcopy.go @@ -117,21 +117,6 @@ func (in *Condition) DeepCopy() *Condition { return out } -// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. -func (in *DHCPConfig) DeepCopyInto(out *DHCPConfig) { - *out = *in -} - -// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new DHCPConfig. -func (in *DHCPConfig) DeepCopy() *DHCPConfig { - if in == nil { - return nil - } - out := new(DHCPConfig) - in.DeepCopyInto(out) - return out -} - // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *IPAddressAllocation) DeepCopyInto(out *IPAddressAllocation) { *out = *in @@ -820,6 +805,21 @@ func (in *Subnet) DeepCopyObject() runtime.Object { return nil } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *SubnetDHCPConfig) DeepCopyInto(out *SubnetDHCPConfig) { + *out = *in +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new SubnetDHCPConfig. +func (in *SubnetDHCPConfig) DeepCopy() *SubnetDHCPConfig { + if in == nil { + return nil + } + out := new(SubnetDHCPConfig) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *SubnetInfo) DeepCopyInto(out *SubnetInfo) { *out = *in @@ -1042,7 +1042,7 @@ func (in *SubnetSetList) DeepCopyObject() runtime.Object { // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *SubnetSetSpec) DeepCopyInto(out *SubnetSetSpec) { *out = *in - out.DHCPConfig = in.DHCPConfig + out.SubnetDHCPConfig = in.SubnetDHCPConfig } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new SubnetSetSpec. @@ -1092,7 +1092,7 @@ func (in *SubnetSpec) DeepCopyInto(out *SubnetSpec) { *out = make([]string, len(*in)) copy(*out, *in) } - out.DHCPConfig = in.DHCPConfig + out.SubnetDHCPConfig = in.SubnetDHCPConfig } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new SubnetSpec. diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/.goreleaser.yml b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/.goreleaser.yml index e1cb528974b..a359fc97588 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/.goreleaser.yml +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/.goreleaser.yml @@ -92,49 +92,6 @@ changelog: - Merge pull request - Merge branch -# upload disabled since it is maintained in homebrew-core -brews: - - name: govc - ids: - - govcbuild - repository: - owner: govmomi - name: homebrew-tap - # TODO: create token in specified tap repo, add as secret to govmomi repo and reference in release workflow - # token: "{{ .Env.HOMEBREW_TAP_GITHUB_TOKEN }}" - # enable once we do fully automated releases - skip_upload: true - commit_author: - name: Alfred the Narwhal - email: cna-alfred@vmware.com - directory: Formula - homepage: "https://github.com/vmware/govmomi/blob/main/govc/README.md" - description: "govc is a vSphere CLI built on top of govmomi." - test: | - system "#{bin}/govc version" - install: | - bin.install "govc" - - name: vcsim - ids: - - vcsimbuild - repository: - owner: govmomi - name: homebrew-tap - # TODO: create token in specified tap repo, add as secret to govmomi repo and reference in release workflow - # token: "{{ .Env.HOMEBREW_TAP_GITHUB_TOKEN }}" - # enable once we do fully automated releases - skip_upload: true - commit_author: - name: Alfred the Narwhal - email: cna-alfred@vmware.com - directory: Formula - homepage: "https://github.com/vmware/govmomi/blob/main/vcsim/README.md" - description: "vcsim is a vSphere API simulator built on top of govmomi." - test: | - system "#{bin}/vcsim -h" - install: | - bin.install "vcsim" - dockers: - image_templates: - "vmware/govc:{{ .Tag }}" diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/internal/version/version.go b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/internal/version/version.go index 24d1597b4e7..80969fffa61 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/internal/version/version.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/internal/version/version.go @@ -21,5 +21,5 @@ const ( ClientName = "govmomi" // ClientVersion is the version of this SDK - ClientVersion = "0.47.1" + ClientVersion = "0.49.0" ) diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/registry.go b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/registry.go index deacf508bba..ed5b5e35953 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/registry.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/registry.go @@ -1,21 +1,27 @@ -/* -Copyright (c) 2014 VMware, Inc. All Rights Reserved. +// © Broadcom. All Rights Reserved. +// The term “Broadcom” refers to Broadcom Inc. and/or its subsidiaries. +// SPDX-License-Identifier: Apache-2.0 -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 +package mo - http://www.apache.org/licenses/LICENSE-2.0 +import ( + "reflect" -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. -*/ + "github.com/vmware/govmomi/vim25/types" +) -package mo +var t = map[string]reflect.Type{} -import "reflect" +// TODO: 9.0 mo below, not included in the generate mo/mo.go, since the generator still uses older rbvmomi vmodl.db -var t = map[string]reflect.Type{} +type DirectPathProfileManager struct { + Self types.ManagedObjectReference `json:"self"` +} + +func (m DirectPathProfileManager) Reference() types.ManagedObjectReference { + return m.Self +} + +func init() { + t["DirectPathProfileManager"] = reflect.TypeOf((*DirectPathProfileManager)(nil)).Elem() +} diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/retrieve.go b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/retrieve.go index 66a8a978203..51b4c8c3af9 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/retrieve.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/retrieve.go @@ -1,18 +1,6 @@ -/* -Copyright (c) 2014-2024 VMware, Inc. All Rights Reserved. - -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. -*/ +// © Broadcom. All Rights Reserved. +// The term “Broadcom” refers to Broadcom Inc. and/or its subsidiaries. +// SPDX-License-Identifier: Apache-2.0 package mo @@ -36,6 +24,11 @@ func ignoreMissingProperty(ref types.ManagedObjectReference, p types.MissingProp // Seen with vApp child VM return true } + case "ResourcePool": + switch p.Path { + case "resourceConfigSpecDetailed": + return true + } } return false diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/type_info.go b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/type_info.go index cfe5e0afbc4..3068da1c82c 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/type_info.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/mo/type_info.go @@ -1,18 +1,6 @@ -/* -Copyright (c) 2014-2024 VMware, Inc. All Rights Reserved. - -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. -*/ +// © Broadcom. All Rights Reserved. +// The term “Broadcom” refers to Broadcom Inc. and/or its subsidiaries. +// SPDX-License-Identifier: Apache-2.0 package mo @@ -192,8 +180,10 @@ var nilValue reflect.Value func assignValue(val reflect.Value, fi []int, pv reflect.Value, field ...string) { // Indexed property path can only use base types if val.Kind() == reflect.Interface { - base := baseType(val.Type()) - val.Set(reflect.New(base)) + if val.IsNil() { + base := baseType(val.Type()) + val.Set(reflect.New(base)) + } val = val.Elem() } diff --git a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/soap/client.go b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/soap/client.go index 7b4b26ab692..b7ff99f5a64 100644 --- a/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/soap/client.go +++ b/cluster-api/providers/vsphere/vendor/github.com/vmware/govmomi/vim25/soap/client.go @@ -214,9 +214,8 @@ func (c *Client) NewServiceClient(path string, namespace string) *Client { return c.newServiceClientWithTransport(path, namespace, c.t) } -// SessionCookie returns a SessionCookie with value of the vmware_soap_session http.Cookie. -func (c *Client) SessionCookie() *HeaderElement { - for _, cookie := range c.Jar.Cookies(c.URL()) { +func sessionCookie(jar http.CookieJar, u *url.URL) *HeaderElement { + for _, cookie := range jar.Cookies(u) { if cookie.Name == SessionCookieName { return &HeaderElement{Value: cookie.Value} } @@ -224,6 +223,22 @@ func (c *Client) SessionCookie() *HeaderElement { return nil } +// SessionCookie returns a SessionCookie with value of the vmware_soap_session http.Cookie. +func (c *Client) SessionCookie() *HeaderElement { + u := c.URL() + + if cookie := sessionCookie(c.Jar, u); cookie != nil { + return cookie + } + + // Default "/sdk" Path would match above, + // but saw a case of Path == "sdk", where above returns nil. + // The jar entry Path is normally "/", so fallback to that. + u.Path = "/" + + return sessionCookie(c.Jar, u) +} + func (c *Client) newServiceClientWithTransport(path string, namespace string, t *http.Transport) *Client { vc := c.URL() u, err := url.Parse(path) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/common.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/common.go index 214acaf581e..5d6e6156b7b 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/common.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/common.go @@ -18,13 +18,6 @@ const ( WriteErrorKey = attribute.Key("http.write_error") // if an error occurred while writing a reply, the string of the error (io.EOF is not recorded) ) -// Server HTTP metrics. -const ( - serverRequestSize = "http.server.request.size" // Incoming request bytes total - serverResponseSize = "http.server.response.size" // Incoming response bytes total - serverDuration = "http.server.duration" // Incoming end to end duration, milliseconds -) - // Client HTTP metrics. const ( clientRequestSize = "http.client.request.size" // Outgoing request bytes total diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/config.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/config.go index f0a9bb9efeb..a01bfafbe07 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/config.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/config.go @@ -8,6 +8,8 @@ import ( "net/http" "net/http/httptrace" + "go.opentelemetry.io/otel/attribute" + "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/metric" "go.opentelemetry.io/otel/propagation" @@ -33,8 +35,9 @@ type config struct { SpanNameFormatter func(string, *http.Request) string ClientTrace func(context.Context) *httptrace.ClientTrace - TracerProvider trace.TracerProvider - MeterProvider metric.MeterProvider + TracerProvider trace.TracerProvider + MeterProvider metric.MeterProvider + MetricAttributesFn func(*http.Request) []attribute.KeyValue } // Option interface used for setting optional config properties. @@ -194,3 +197,11 @@ func WithServerName(server string) Option { c.ServerName = server }) } + +// WithMetricAttributesFn returns an Option to set a function that maps an HTTP request to a slice of attribute.KeyValue. +// These attributes will be included in metrics for every request. +func WithMetricAttributesFn(metricAttributesFn func(r *http.Request) []attribute.KeyValue) Option { + return optionFunc(func(c *config) { + c.MetricAttributesFn = metricAttributesFn + }) +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/handler.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/handler.go index d01bdccf40d..33580a35b77 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/handler.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/handler.go @@ -9,11 +9,9 @@ import ( "github.com/felixge/httpsnoop" + "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request" "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv" - "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil" "go.opentelemetry.io/otel" - "go.opentelemetry.io/otel/attribute" - "go.opentelemetry.io/otel/metric" "go.opentelemetry.io/otel/propagation" "go.opentelemetry.io/otel/trace" ) @@ -24,7 +22,6 @@ type middleware struct { server string tracer trace.Tracer - meter metric.Meter propagators propagation.TextMapPropagator spanStartOptions []trace.SpanStartOption readEvent bool @@ -34,10 +31,7 @@ type middleware struct { publicEndpoint bool publicEndpointFn func(*http.Request) bool - traceSemconv semconv.HTTPServer - requestBytesCounter metric.Int64Counter - responseBytesCounter metric.Int64Counter - serverLatencyMeasure metric.Float64Histogram + semconv semconv.HTTPServer } func defaultHandlerFormatter(operation string, _ *http.Request) string { @@ -56,8 +50,6 @@ func NewHandler(handler http.Handler, operation string, opts ...Option) http.Han func NewMiddleware(operation string, opts ...Option) func(http.Handler) http.Handler { h := middleware{ operation: operation, - - traceSemconv: semconv.NewHTTPServer(), } defaultOpts := []Option{ @@ -67,7 +59,6 @@ func NewMiddleware(operation string, opts ...Option) func(http.Handler) http.Han c := newConfig(append(defaultOpts, opts...)...) h.configure(c) - h.createMeasures() return func(next http.Handler) http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { @@ -78,7 +69,6 @@ func NewMiddleware(operation string, opts ...Option) func(http.Handler) http.Han func (h *middleware) configure(c *config) { h.tracer = c.Tracer - h.meter = c.Meter h.propagators = c.Propagators h.spanStartOptions = c.SpanStartOptions h.readEvent = c.ReadEvent @@ -88,6 +78,7 @@ func (h *middleware) configure(c *config) { h.publicEndpoint = c.PublicEndpoint h.publicEndpointFn = c.PublicEndpointFn h.server = c.ServerName + h.semconv = semconv.NewHTTPServer(c.Meter) } func handleErr(err error) { @@ -96,30 +87,6 @@ func handleErr(err error) { } } -func (h *middleware) createMeasures() { - var err error - h.requestBytesCounter, err = h.meter.Int64Counter( - serverRequestSize, - metric.WithUnit("By"), - metric.WithDescription("Measures the size of HTTP request messages."), - ) - handleErr(err) - - h.responseBytesCounter, err = h.meter.Int64Counter( - serverResponseSize, - metric.WithUnit("By"), - metric.WithDescription("Measures the size of HTTP response messages."), - ) - handleErr(err) - - h.serverLatencyMeasure, err = h.meter.Float64Histogram( - serverDuration, - metric.WithUnit("ms"), - metric.WithDescription("Measures the duration of inbound HTTP requests."), - ) - handleErr(err) -} - // serveHTTP sets up tracing and calls the given next http.Handler with the span // context injected into the request context. func (h *middleware) serveHTTP(w http.ResponseWriter, r *http.Request, next http.Handler) { @@ -134,7 +101,7 @@ func (h *middleware) serveHTTP(w http.ResponseWriter, r *http.Request, next http ctx := h.propagators.Extract(r.Context(), propagation.HeaderCarrier(r.Header)) opts := []trace.SpanStartOption{ - trace.WithAttributes(h.traceSemconv.RequestTraceAttrs(h.server, r)...), + trace.WithAttributes(h.semconv.RequestTraceAttrs(h.server, r)...), } opts = append(opts, h.spanStartOptions...) @@ -166,14 +133,12 @@ func (h *middleware) serveHTTP(w http.ResponseWriter, r *http.Request, next http } } - var bw bodyWrapper // if request body is nil or NoBody, we don't want to mutate the body as it // will affect the identity of it in an unforeseeable way because we assert // ReadCloser fulfills a certain interface and it is indeed nil or NoBody. + bw := request.NewBodyWrapper(r.Body, readRecordFunc) if r.Body != nil && r.Body != http.NoBody { - bw.ReadCloser = r.Body - bw.record = readRecordFunc - r.Body = &bw + r.Body = bw } writeRecordFunc := func(int64) {} @@ -183,13 +148,7 @@ func (h *middleware) serveHTTP(w http.ResponseWriter, r *http.Request, next http } } - rww := &respWriterWrapper{ - ResponseWriter: w, - record: writeRecordFunc, - ctx: ctx, - props: h.propagators, - statusCode: http.StatusOK, // default status code in case the Handler doesn't write anything - } + rww := request.NewRespWriterWrapper(w, writeRecordFunc) // Wrap w to use our ResponseWriter methods while also exposing // other interfaces that w may implement (http.CloseNotifier, @@ -217,35 +176,35 @@ func (h *middleware) serveHTTP(w http.ResponseWriter, r *http.Request, next http next.ServeHTTP(w, r.WithContext(ctx)) - span.SetStatus(semconv.ServerStatus(rww.statusCode)) - span.SetAttributes(h.traceSemconv.ResponseTraceAttrs(semconv.ResponseTelemetry{ - StatusCode: rww.statusCode, - ReadBytes: bw.read.Load(), - ReadError: bw.err, - WriteBytes: rww.written, - WriteError: rww.err, + statusCode := rww.StatusCode() + bytesWritten := rww.BytesWritten() + span.SetStatus(h.semconv.Status(statusCode)) + span.SetAttributes(h.semconv.ResponseTraceAttrs(semconv.ResponseTelemetry{ + StatusCode: statusCode, + ReadBytes: bw.BytesRead(), + ReadError: bw.Error(), + WriteBytes: bytesWritten, + WriteError: rww.Error(), })...) - // Add metrics - attributes := append(labeler.Get(), semconvutil.HTTPServerRequestMetrics(h.server, r)...) - if rww.statusCode > 0 { - attributes = append(attributes, semconv.HTTPStatusCode(rww.statusCode)) - } - o := metric.WithAttributeSet(attribute.NewSet(attributes...)) - addOpts := []metric.AddOption{o} // Allocate vararg slice once. - h.requestBytesCounter.Add(ctx, bw.read.Load(), addOpts...) - h.responseBytesCounter.Add(ctx, rww.written, addOpts...) - // Use floating point division here for higher precision (instead of Millisecond method). elapsedTime := float64(time.Since(requestStartTime)) / float64(time.Millisecond) - h.serverLatencyMeasure.Record(ctx, elapsedTime, o) + h.semconv.RecordMetrics(ctx, semconv.MetricData{ + ServerName: h.server, + Req: r, + StatusCode: statusCode, + AdditionalAttributes: labeler.Get(), + RequestSize: bw.BytesRead(), + ResponseSize: bytesWritten, + ElapsedTime: elapsedTime, + }) } // WithRouteTag annotates spans and metrics with the provided route name // with HTTP route attribute. func WithRouteTag(route string, h http.Handler) http.Handler { - attr := semconv.NewHTTPServer().Route(route) + attr := semconv.NewHTTPServer(nil).Route(route) return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { span := trace.SpanFromContext(r.Context()) span.SetAttributes(attr) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/body_wrapper.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/body_wrapper.go new file mode 100644 index 00000000000..a945f556616 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/body_wrapper.go @@ -0,0 +1,75 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package request // import "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request" + +import ( + "io" + "sync" +) + +var _ io.ReadCloser = &BodyWrapper{} + +// BodyWrapper wraps a http.Request.Body (an io.ReadCloser) to track the number +// of bytes read and the last error. +type BodyWrapper struct { + io.ReadCloser + OnRead func(n int64) // must not be nil + + mu sync.Mutex + read int64 + err error +} + +// NewBodyWrapper creates a new BodyWrapper. +// +// The onRead attribute is a callback that will be called every time the data +// is read, with the number of bytes being read. +func NewBodyWrapper(body io.ReadCloser, onRead func(int64)) *BodyWrapper { + return &BodyWrapper{ + ReadCloser: body, + OnRead: onRead, + } +} + +// Read reads the data from the io.ReadCloser, and stores the number of bytes +// read and the error. +func (w *BodyWrapper) Read(b []byte) (int, error) { + n, err := w.ReadCloser.Read(b) + n1 := int64(n) + + w.updateReadData(n1, err) + w.OnRead(n1) + return n, err +} + +func (w *BodyWrapper) updateReadData(n int64, err error) { + w.mu.Lock() + defer w.mu.Unlock() + + w.read += n + if err != nil { + w.err = err + } +} + +// Closes closes the io.ReadCloser. +func (w *BodyWrapper) Close() error { + return w.ReadCloser.Close() +} + +// BytesRead returns the number of bytes read up to this point. +func (w *BodyWrapper) BytesRead() int64 { + w.mu.Lock() + defer w.mu.Unlock() + + return w.read +} + +// Error returns the last error. +func (w *BodyWrapper) Error() error { + w.mu.Lock() + defer w.mu.Unlock() + + return w.err +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/resp_writer_wrapper.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/resp_writer_wrapper.go new file mode 100644 index 00000000000..aea171fb260 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request/resp_writer_wrapper.go @@ -0,0 +1,112 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package request // import "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request" + +import ( + "net/http" + "sync" +) + +var _ http.ResponseWriter = &RespWriterWrapper{} + +// RespWriterWrapper wraps a http.ResponseWriter in order to track the number of +// bytes written, the last error, and to catch the first written statusCode. +// TODO: The wrapped http.ResponseWriter doesn't implement any of the optional +// types (http.Hijacker, http.Pusher, http.CloseNotifier, etc) +// that may be useful when using it in real life situations. +type RespWriterWrapper struct { + http.ResponseWriter + OnWrite func(n int64) // must not be nil + + mu sync.RWMutex + written int64 + statusCode int + err error + wroteHeader bool +} + +// NewRespWriterWrapper creates a new RespWriterWrapper. +// +// The onWrite attribute is a callback that will be called every time the data +// is written, with the number of bytes that were written. +func NewRespWriterWrapper(w http.ResponseWriter, onWrite func(int64)) *RespWriterWrapper { + return &RespWriterWrapper{ + ResponseWriter: w, + OnWrite: onWrite, + statusCode: http.StatusOK, // default status code in case the Handler doesn't write anything + } +} + +// Write writes the bytes array into the [ResponseWriter], and tracks the +// number of bytes written and last error. +func (w *RespWriterWrapper) Write(p []byte) (int, error) { + w.mu.Lock() + defer w.mu.Unlock() + + w.writeHeader(http.StatusOK) + + n, err := w.ResponseWriter.Write(p) + n1 := int64(n) + w.OnWrite(n1) + w.written += n1 + w.err = err + return n, err +} + +// WriteHeader persists initial statusCode for span attribution. +// All calls to WriteHeader will be propagated to the underlying ResponseWriter +// and will persist the statusCode from the first call. +// Blocking consecutive calls to WriteHeader alters expected behavior and will +// remove warning logs from net/http where developers will notice incorrect handler implementations. +func (w *RespWriterWrapper) WriteHeader(statusCode int) { + w.mu.Lock() + defer w.mu.Unlock() + + w.writeHeader(statusCode) +} + +// writeHeader persists the status code for span attribution, and propagates +// the call to the underlying ResponseWriter. +// It does not acquire a lock, and therefore assumes that is being handled by a +// parent method. +func (w *RespWriterWrapper) writeHeader(statusCode int) { + if !w.wroteHeader { + w.wroteHeader = true + w.statusCode = statusCode + } + w.ResponseWriter.WriteHeader(statusCode) +} + +// Flush implements [http.Flusher]. +func (w *RespWriterWrapper) Flush() { + w.WriteHeader(http.StatusOK) + + if f, ok := w.ResponseWriter.(http.Flusher); ok { + f.Flush() + } +} + +// BytesWritten returns the number of bytes written. +func (w *RespWriterWrapper) BytesWritten() int64 { + w.mu.RLock() + defer w.mu.RUnlock() + + return w.written +} + +// BytesWritten returns the HTTP status code that was sent. +func (w *RespWriterWrapper) StatusCode() int { + w.mu.RLock() + defer w.mu.RUnlock() + + return w.statusCode +} + +// Error returns the last error. +func (w *RespWriterWrapper) Error() error { + w.mu.RLock() + defer w.mu.RUnlock() + + return w.err +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/env.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/env.go index 3ec0ad00c81..9cae4cab86a 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/env.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/env.go @@ -4,6 +4,7 @@ package semconv // import "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv" import ( + "context" "fmt" "net/http" "os" @@ -11,6 +12,7 @@ import ( "go.opentelemetry.io/otel/attribute" "go.opentelemetry.io/otel/codes" + "go.opentelemetry.io/otel/metric" ) type ResponseTelemetry struct { @@ -23,6 +25,11 @@ type ResponseTelemetry struct { type HTTPServer struct { duplicate bool + + // Old metrics + requestBytesCounter metric.Int64Counter + responseBytesCounter metric.Int64Counter + serverLatencyMeasure metric.Float64Histogram } // RequestTraceAttrs returns trace attributes for an HTTP request received by a @@ -63,15 +70,10 @@ func (s HTTPServer) Route(route string) attribute.KeyValue { return oldHTTPServer{}.Route(route) } -func NewHTTPServer() HTTPServer { - env := strings.ToLower(os.Getenv("OTEL_HTTP_CLIENT_COMPATIBILITY_MODE")) - return HTTPServer{duplicate: env == "http/dup"} -} - -// ServerStatus returns a span status code and message for an HTTP status code +// Status returns a span status code and message for an HTTP status code // value returned by a server. Status codes in the 400-499 range are not // returned as errors. -func ServerStatus(code int) (codes.Code, string) { +func (s HTTPServer) Status(code int) (codes.Code, string) { if code < 100 || code >= 600 { return codes.Error, fmt.Sprintf("Invalid HTTP status code %d", code) } @@ -80,3 +82,84 @@ func ServerStatus(code int) (codes.Code, string) { } return codes.Unset, "" } + +type MetricData struct { + ServerName string + Req *http.Request + StatusCode int + AdditionalAttributes []attribute.KeyValue + + RequestSize int64 + ResponseSize int64 + ElapsedTime float64 +} + +func (s HTTPServer) RecordMetrics(ctx context.Context, md MetricData) { + if s.requestBytesCounter == nil || s.responseBytesCounter == nil || s.serverLatencyMeasure == nil { + // This will happen if an HTTPServer{} is used insted of NewHTTPServer. + return + } + + attributes := oldHTTPServer{}.MetricAttributes(md.ServerName, md.Req, md.StatusCode, md.AdditionalAttributes) + o := metric.WithAttributeSet(attribute.NewSet(attributes...)) + addOpts := []metric.AddOption{o} // Allocate vararg slice once. + s.requestBytesCounter.Add(ctx, md.RequestSize, addOpts...) + s.responseBytesCounter.Add(ctx, md.ResponseSize, addOpts...) + s.serverLatencyMeasure.Record(ctx, md.ElapsedTime, o) + + // TODO: Duplicate Metrics +} + +func NewHTTPServer(meter metric.Meter) HTTPServer { + env := strings.ToLower(os.Getenv("OTEL_SEMCONV_STABILITY_OPT_IN")) + duplicate := env == "http/dup" + server := HTTPServer{ + duplicate: duplicate, + } + server.requestBytesCounter, server.responseBytesCounter, server.serverLatencyMeasure = oldHTTPServer{}.createMeasures(meter) + return server +} + +type HTTPClient struct { + duplicate bool +} + +func NewHTTPClient() HTTPClient { + env := strings.ToLower(os.Getenv("OTEL_SEMCONV_STABILITY_OPT_IN")) + return HTTPClient{duplicate: env == "http/dup"} +} + +// RequestTraceAttrs returns attributes for an HTTP request made by a client. +func (c HTTPClient) RequestTraceAttrs(req *http.Request) []attribute.KeyValue { + if c.duplicate { + return append(oldHTTPClient{}.RequestTraceAttrs(req), newHTTPClient{}.RequestTraceAttrs(req)...) + } + return oldHTTPClient{}.RequestTraceAttrs(req) +} + +// ResponseTraceAttrs returns metric attributes for an HTTP request made by a client. +func (c HTTPClient) ResponseTraceAttrs(resp *http.Response) []attribute.KeyValue { + if c.duplicate { + return append(oldHTTPClient{}.ResponseTraceAttrs(resp), newHTTPClient{}.ResponseTraceAttrs(resp)...) + } + + return oldHTTPClient{}.ResponseTraceAttrs(resp) +} + +func (c HTTPClient) Status(code int) (codes.Code, string) { + if code < 100 || code >= 600 { + return codes.Error, fmt.Sprintf("Invalid HTTP status code %d", code) + } + if code >= 400 { + return codes.Error, "" + } + return codes.Unset, "" +} + +func (c HTTPClient) ErrorType(err error) attribute.KeyValue { + if c.duplicate { + return newHTTPClient{}.ErrorType(err) + } + + return attribute.KeyValue{} +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.24.0.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/httpconv.go similarity index 57% rename from cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.24.0.go rename to cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/httpconv.go index 0c5d4c4608a..745b8c67bc4 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.24.0.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/httpconv.go @@ -4,11 +4,14 @@ package semconv // import "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv" import ( + "fmt" "net/http" + "reflect" + "strconv" "strings" "go.opentelemetry.io/otel/attribute" - semconvNew "go.opentelemetry.io/otel/semconv/v1.24.0" + semconvNew "go.opentelemetry.io/otel/semconv/v1.26.0" ) type newHTTPServer struct{} @@ -195,3 +198,151 @@ func (n newHTTPServer) ResponseTraceAttrs(resp ResponseTelemetry) []attribute.Ke func (n newHTTPServer) Route(route string) attribute.KeyValue { return semconvNew.HTTPRoute(route) } + +type newHTTPClient struct{} + +// RequestTraceAttrs returns trace attributes for an HTTP request made by a client. +func (n newHTTPClient) RequestTraceAttrs(req *http.Request) []attribute.KeyValue { + /* + below attributes are returned: + - http.request.method + - http.request.method.original + - url.full + - server.address + - server.port + - network.protocol.name + - network.protocol.version + */ + numOfAttributes := 3 // URL, server address, proto, and method. + + var urlHost string + if req.URL != nil { + urlHost = req.URL.Host + } + var requestHost string + var requestPort int + for _, hostport := range []string{urlHost, req.Header.Get("Host")} { + requestHost, requestPort = splitHostPort(hostport) + if requestHost != "" || requestPort > 0 { + break + } + } + + eligiblePort := requiredHTTPPort(req.URL != nil && req.URL.Scheme == "https", requestPort) + if eligiblePort > 0 { + numOfAttributes++ + } + useragent := req.UserAgent() + if useragent != "" { + numOfAttributes++ + } + + protoName, protoVersion := netProtocol(req.Proto) + if protoName != "" && protoName != "http" { + numOfAttributes++ + } + if protoVersion != "" { + numOfAttributes++ + } + + method, originalMethod := n.method(req.Method) + if originalMethod != (attribute.KeyValue{}) { + numOfAttributes++ + } + + attrs := make([]attribute.KeyValue, 0, numOfAttributes) + + attrs = append(attrs, method) + if originalMethod != (attribute.KeyValue{}) { + attrs = append(attrs, originalMethod) + } + + var u string + if req.URL != nil { + // Remove any username/password info that may be in the URL. + userinfo := req.URL.User + req.URL.User = nil + u = req.URL.String() + // Restore any username/password info that was removed. + req.URL.User = userinfo + } + attrs = append(attrs, semconvNew.URLFull(u)) + + attrs = append(attrs, semconvNew.ServerAddress(requestHost)) + if eligiblePort > 0 { + attrs = append(attrs, semconvNew.ServerPort(eligiblePort)) + } + + if protoName != "" && protoName != "http" { + attrs = append(attrs, semconvNew.NetworkProtocolName(protoName)) + } + if protoVersion != "" { + attrs = append(attrs, semconvNew.NetworkProtocolVersion(protoVersion)) + } + + return attrs +} + +// ResponseTraceAttrs returns trace attributes for an HTTP response made by a client. +func (n newHTTPClient) ResponseTraceAttrs(resp *http.Response) []attribute.KeyValue { + /* + below attributes are returned: + - http.response.status_code + - error.type + */ + var count int + if resp.StatusCode > 0 { + count++ + } + + if isErrorStatusCode(resp.StatusCode) { + count++ + } + + attrs := make([]attribute.KeyValue, 0, count) + if resp.StatusCode > 0 { + attrs = append(attrs, semconvNew.HTTPResponseStatusCode(resp.StatusCode)) + } + + if isErrorStatusCode(resp.StatusCode) { + errorType := strconv.Itoa(resp.StatusCode) + attrs = append(attrs, semconvNew.ErrorTypeKey.String(errorType)) + } + return attrs +} + +func (n newHTTPClient) ErrorType(err error) attribute.KeyValue { + t := reflect.TypeOf(err) + var value string + if t.PkgPath() == "" && t.Name() == "" { + // Likely a builtin type. + value = t.String() + } else { + value = fmt.Sprintf("%s.%s", t.PkgPath(), t.Name()) + } + + if value == "" { + return semconvNew.ErrorTypeOther + } + + return semconvNew.ErrorTypeKey.String(value) +} + +func (n newHTTPClient) method(method string) (attribute.KeyValue, attribute.KeyValue) { + if method == "" { + return semconvNew.HTTPRequestMethodGet, attribute.KeyValue{} + } + if attr, ok := methodLookup[method]; ok { + return attr, attribute.KeyValue{} + } + + orig := semconvNew.HTTPRequestMethodOriginal(method) + if attr, ok := methodLookup[strings.ToUpper(method)]; ok { + return attr, orig + } + return semconvNew.HTTPRequestMethodGet, orig +} + +func isErrorStatusCode(code int) bool { + return code >= 400 || code < 100 +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/util.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/util.go index e7f293761bd..e6e14924f57 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/util.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/util.go @@ -9,8 +9,9 @@ import ( "strconv" "strings" + "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/attribute" - semconvNew "go.opentelemetry.io/otel/semconv/v1.24.0" + semconvNew "go.opentelemetry.io/otel/semconv/v1.26.0" ) // splitHostPort splits a network address hostport of the form "host", @@ -49,7 +50,7 @@ func splitHostPort(hostport string) (host string, port int) { if err != nil { return } - return host, int(p) + return host, int(p) // nolint: gosec // Byte size checked 16 above. } func requiredHTTPPort(https bool, port int) int { // nolint:revive @@ -89,3 +90,9 @@ var methodLookup = map[string]attribute.KeyValue{ http.MethodPut: semconvNew.HTTPRequestMethodPut, http.MethodTrace: semconvNew.HTTPRequestMethodTrace, } + +func handleErr(err error) { + if err != nil { + otel.Handle(err) + } +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.20.0.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.20.0.go index c3e838aaa54..c999b05e675 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.20.0.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv/v1.20.0.go @@ -7,9 +7,13 @@ import ( "errors" "io" "net/http" + "slices" + "strings" "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil" "go.opentelemetry.io/otel/attribute" + "go.opentelemetry.io/otel/metric" + "go.opentelemetry.io/otel/metric/noop" semconv "go.opentelemetry.io/otel/semconv/v1.20.0" ) @@ -72,3 +76,117 @@ func (o oldHTTPServer) Route(route string) attribute.KeyValue { func HTTPStatusCode(status int) attribute.KeyValue { return semconv.HTTPStatusCode(status) } + +// Server HTTP metrics. +const ( + serverRequestSize = "http.server.request.size" // Incoming request bytes total + serverResponseSize = "http.server.response.size" // Incoming response bytes total + serverDuration = "http.server.duration" // Incoming end to end duration, milliseconds +) + +func (h oldHTTPServer) createMeasures(meter metric.Meter) (metric.Int64Counter, metric.Int64Counter, metric.Float64Histogram) { + if meter == nil { + return noop.Int64Counter{}, noop.Int64Counter{}, noop.Float64Histogram{} + } + var err error + requestBytesCounter, err := meter.Int64Counter( + serverRequestSize, + metric.WithUnit("By"), + metric.WithDescription("Measures the size of HTTP request messages."), + ) + handleErr(err) + + responseBytesCounter, err := meter.Int64Counter( + serverResponseSize, + metric.WithUnit("By"), + metric.WithDescription("Measures the size of HTTP response messages."), + ) + handleErr(err) + + serverLatencyMeasure, err := meter.Float64Histogram( + serverDuration, + metric.WithUnit("ms"), + metric.WithDescription("Measures the duration of inbound HTTP requests."), + ) + handleErr(err) + + return requestBytesCounter, responseBytesCounter, serverLatencyMeasure +} + +func (o oldHTTPServer) MetricAttributes(server string, req *http.Request, statusCode int, additionalAttributes []attribute.KeyValue) []attribute.KeyValue { + n := len(additionalAttributes) + 3 + var host string + var p int + if server == "" { + host, p = splitHostPort(req.Host) + } else { + // Prioritize the primary server name. + host, p = splitHostPort(server) + if p < 0 { + _, p = splitHostPort(req.Host) + } + } + hostPort := requiredHTTPPort(req.TLS != nil, p) + if hostPort > 0 { + n++ + } + protoName, protoVersion := netProtocol(req.Proto) + if protoName != "" { + n++ + } + if protoVersion != "" { + n++ + } + + if statusCode > 0 { + n++ + } + + attributes := slices.Grow(additionalAttributes, n) + attributes = append(attributes, + o.methodMetric(req.Method), + o.scheme(req.TLS != nil), + semconv.NetHostName(host)) + + if hostPort > 0 { + attributes = append(attributes, semconv.NetHostPort(hostPort)) + } + if protoName != "" { + attributes = append(attributes, semconv.NetProtocolName(protoName)) + } + if protoVersion != "" { + attributes = append(attributes, semconv.NetProtocolVersion(protoVersion)) + } + + if statusCode > 0 { + attributes = append(attributes, semconv.HTTPStatusCode(statusCode)) + } + return attributes +} + +func (o oldHTTPServer) methodMetric(method string) attribute.KeyValue { + method = strings.ToUpper(method) + switch method { + case http.MethodConnect, http.MethodDelete, http.MethodGet, http.MethodHead, http.MethodOptions, http.MethodPatch, http.MethodPost, http.MethodPut, http.MethodTrace: + default: + method = "_OTHER" + } + return semconv.HTTPMethod(method) +} + +func (o oldHTTPServer) scheme(https bool) attribute.KeyValue { // nolint:revive + if https { + return semconv.HTTPSchemeHTTPS + } + return semconv.HTTPSchemeHTTP +} + +type oldHTTPClient struct{} + +func (o oldHTTPClient) RequestTraceAttrs(req *http.Request) []attribute.KeyValue { + return semconvutil.HTTPClientRequest(req) +} + +func (o oldHTTPClient) ResponseTraceAttrs(resp *http.Response) []attribute.KeyValue { + return semconvutil.HTTPClientResponse(resp) +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil/netconv.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil/netconv.go index a9a9226b39a..b80a1db61fa 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil/netconv.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil/netconv.go @@ -195,7 +195,7 @@ func splitHostPort(hostport string) (host string, port int) { if err != nil { return } - return host, int(p) + return host, int(p) // nolint: gosec // Bitsize checked to be 16 above. } func netProtocol(proto string) (name string, version string) { diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/transport.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/transport.go index 0d3cb2e4aa4..b4119d3438b 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/transport.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/transport.go @@ -11,13 +11,15 @@ import ( "sync/atomic" "time" + "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request" + "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv" "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil" "go.opentelemetry.io/otel" "go.opentelemetry.io/otel/attribute" "go.opentelemetry.io/otel/codes" "go.opentelemetry.io/otel/metric" "go.opentelemetry.io/otel/propagation" - semconv "go.opentelemetry.io/otel/semconv/v1.20.0" + "go.opentelemetry.io/otel/trace" ) @@ -26,14 +28,16 @@ import ( type Transport struct { rt http.RoundTripper - tracer trace.Tracer - meter metric.Meter - propagators propagation.TextMapPropagator - spanStartOptions []trace.SpanStartOption - filters []Filter - spanNameFormatter func(string, *http.Request) string - clientTrace func(context.Context) *httptrace.ClientTrace + tracer trace.Tracer + meter metric.Meter + propagators propagation.TextMapPropagator + spanStartOptions []trace.SpanStartOption + filters []Filter + spanNameFormatter func(string, *http.Request) string + clientTrace func(context.Context) *httptrace.ClientTrace + metricAttributesFn func(*http.Request) []attribute.KeyValue + semconv semconv.HTTPClient requestBytesCounter metric.Int64Counter responseBytesCounter metric.Int64Counter latencyMeasure metric.Float64Histogram @@ -53,7 +57,8 @@ func NewTransport(base http.RoundTripper, opts ...Option) *Transport { } t := Transport{ - rt: base, + rt: base, + semconv: semconv.NewHTTPClient(), } defaultOpts := []Option{ @@ -76,6 +81,7 @@ func (t *Transport) applyConfig(c *config) { t.filters = c.Filters t.spanNameFormatter = c.SpanNameFormatter t.clientTrace = c.ClientTrace + t.metricAttributesFn = c.MetricAttributesFn } func (t *Transport) createMeasures() { @@ -143,45 +149,49 @@ func (t *Transport) RoundTrip(r *http.Request) (*http.Response, error) { r = r.Clone(ctx) // According to RoundTripper spec, we shouldn't modify the origin request. - // use a body wrapper to determine the request size - var bw bodyWrapper // if request body is nil or NoBody, we don't want to mutate the body as it // will affect the identity of it in an unforeseeable way because we assert // ReadCloser fulfills a certain interface and it is indeed nil or NoBody. + bw := request.NewBodyWrapper(r.Body, func(int64) {}) if r.Body != nil && r.Body != http.NoBody { - bw.ReadCloser = r.Body - // noop to prevent nil panic. not using this record fun yet. - bw.record = func(int64) {} - r.Body = &bw + r.Body = bw } - span.SetAttributes(semconvutil.HTTPClientRequest(r)...) + span.SetAttributes(t.semconv.RequestTraceAttrs(r)...) t.propagators.Inject(ctx, propagation.HeaderCarrier(r.Header)) res, err := t.rt.RoundTrip(r) if err != nil { - span.RecordError(err) + // set error type attribute if the error is part of the predefined + // error types. + // otherwise, record it as an exception + if errType := t.semconv.ErrorType(err); errType.Valid() { + span.SetAttributes(errType) + } else { + span.RecordError(err) + } + span.SetStatus(codes.Error, err.Error()) span.End() return res, err } // metrics - metricAttrs := append(labeler.Get(), semconvutil.HTTPClientRequestMetrics(r)...) + metricAttrs := append(append(labeler.Get(), semconvutil.HTTPClientRequestMetrics(r)...), t.metricAttributesFromRequest(r)...) if res.StatusCode > 0 { metricAttrs = append(metricAttrs, semconv.HTTPStatusCode(res.StatusCode)) } o := metric.WithAttributeSet(attribute.NewSet(metricAttrs...)) - addOpts := []metric.AddOption{o} // Allocate vararg slice once. - t.requestBytesCounter.Add(ctx, bw.read.Load(), addOpts...) + + t.requestBytesCounter.Add(ctx, bw.BytesRead(), o) // For handling response bytes we leverage a callback when the client reads the http response readRecordFunc := func(n int64) { - t.responseBytesCounter.Add(ctx, n, addOpts...) + t.responseBytesCounter.Add(ctx, n, o) } // traces - span.SetAttributes(semconvutil.HTTPClientResponse(res)...) - span.SetStatus(semconvutil.HTTPClientStatus(res.StatusCode)) + span.SetAttributes(t.semconv.ResponseTraceAttrs(res)...) + span.SetStatus(t.semconv.Status(res.StatusCode)) res.Body = newWrappedBody(span, readRecordFunc, res.Body) @@ -193,6 +203,14 @@ func (t *Transport) RoundTrip(r *http.Request) (*http.Response, error) { return res, err } +func (t *Transport) metricAttributesFromRequest(r *http.Request) []attribute.KeyValue { + var attributeForRequest []attribute.KeyValue + if t.metricAttributesFn != nil { + attributeForRequest = t.metricAttributesFn(r) + } + return attributeForRequest +} + // newWrappedBody returns a new and appropriately scoped *wrappedBody as an // io.ReadCloser. If the passed body implements io.Writer, the returned value // will implement io.ReadWriteCloser. diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/version.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/version.go index b0957f28cea..502c1bdafc7 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/version.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/version.go @@ -5,7 +5,7 @@ package otelhttp // import "go.opentelemetry.io/contrib/instrumentation/net/http // Version is the current release version of the otelhttp instrumentation. func Version() string { - return "0.53.0" + return "0.54.0" // This string is updated by the pre_release.sh script during release } diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/wrap.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/wrap.go deleted file mode 100644 index 948f8406c09..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/wrap.go +++ /dev/null @@ -1,99 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -package otelhttp // import "go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp" - -import ( - "context" - "io" - "net/http" - "sync/atomic" - - "go.opentelemetry.io/otel/propagation" -) - -var _ io.ReadCloser = &bodyWrapper{} - -// bodyWrapper wraps a http.Request.Body (an io.ReadCloser) to track the number -// of bytes read and the last error. -type bodyWrapper struct { - io.ReadCloser - record func(n int64) // must not be nil - - read atomic.Int64 - err error -} - -func (w *bodyWrapper) Read(b []byte) (int, error) { - n, err := w.ReadCloser.Read(b) - n1 := int64(n) - w.read.Add(n1) - w.err = err - w.record(n1) - return n, err -} - -func (w *bodyWrapper) Close() error { - return w.ReadCloser.Close() -} - -var _ http.ResponseWriter = &respWriterWrapper{} - -// respWriterWrapper wraps a http.ResponseWriter in order to track the number of -// bytes written, the last error, and to catch the first written statusCode. -// TODO: The wrapped http.ResponseWriter doesn't implement any of the optional -// types (http.Hijacker, http.Pusher, http.CloseNotifier, http.Flusher, etc) -// that may be useful when using it in real life situations. -type respWriterWrapper struct { - http.ResponseWriter - record func(n int64) // must not be nil - - // used to inject the header - ctx context.Context - - props propagation.TextMapPropagator - - written int64 - statusCode int - err error - wroteHeader bool -} - -func (w *respWriterWrapper) Header() http.Header { - return w.ResponseWriter.Header() -} - -func (w *respWriterWrapper) Write(p []byte) (int, error) { - if !w.wroteHeader { - w.WriteHeader(http.StatusOK) - } - n, err := w.ResponseWriter.Write(p) - n1 := int64(n) - w.record(n1) - w.written += n1 - w.err = err - return n, err -} - -// WriteHeader persists initial statusCode for span attribution. -// All calls to WriteHeader will be propagated to the underlying ResponseWriter -// and will persist the statusCode from the first call. -// Blocking consecutive calls to WriteHeader alters expected behavior and will -// remove warning logs from net/http where developers will notice incorrect handler implementations. -func (w *respWriterWrapper) WriteHeader(statusCode int) { - if !w.wroteHeader { - w.wroteHeader = true - w.statusCode = statusCode - } - w.ResponseWriter.WriteHeader(statusCode) -} - -func (w *respWriterWrapper) Flush() { - if !w.wroteHeader { - w.WriteHeader(http.StatusOK) - } - - if f, ok := w.ResponseWriter.(http.Flusher); ok { - f.Flush() - } -} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/.golangci.yml b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/.golangci.yml index 6d9c8b64958..d9abe194d94 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/.golangci.yml +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/.golangci.yml @@ -9,6 +9,8 @@ linters: disable-all: true # Specifically enable linters we want to use. enable: + - asasalint + - bodyclose - depguard - errcheck - errorlint diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CHANGELOG.md b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CHANGELOG.md index c01e6998e0b..6107c17b89f 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CHANGELOG.md +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CHANGELOG.md @@ -8,6 +8,64 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm ## [Unreleased] + + + +## [1.29.0/0.51.0/0.5.0] 2024-08-23 + +This release is the last to support [Go 1.21]. +The next release will require at least [Go 1.22]. + +### Added + +- Add MacOS ARM64 platform to the compatibility testing suite. (#5577) +- Add `InstrumentationScope` field to `SpanStub` in `go.opentelemetry.io/otel/sdk/trace/tracetest`, as a replacement for the deprecated `InstrumentationLibrary`. (#5627) +- Make the initial release of `go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc`. + This new module contains an OTLP exporter that transmits log telemetry using gRPC. + This module is unstable and breaking changes may be introduced. + See our [versioning policy](VERSIONING.md) for more information about these stability guarantees. (#5629) +- Add `Walk` function to `TraceState` in `go.opentelemetry.io/otel/trace` to iterate all the key-value pairs. (#5651) +- Bridge the trace state in `go.opentelemetry.io/otel/bridge/opencensus`. (#5651) +- Zero value of `SimpleProcessor` in `go.opentelemetry.io/otel/sdk/log` no longer panics. (#5665) +- The `FilterProcessor` interface type is added in `go.opentelemetry.io/otel/sdk/log/internal/x`. + This is an optional and experimental interface that log `Processor`s can implement to instruct the `Logger` if a `Record` will be processed or not. + It replaces the existing `Enabled` method that is removed from the `Processor` interface itself. + It does not fall within the scope of the OpenTelemetry Go versioning and stability [policy](./VERSIONING.md) and it may be changed in backwards incompatible ways or removed in feature releases. (#5692) +- Support [Go 1.23]. (#5720) + +### Changed + +- `NewMemberRaw`, `NewKeyProperty` and `NewKeyValuePropertyRaw` in `go.opentelemetry.io/otel/baggage` allow UTF-8 string in key. (#5132) +- `Processor.OnEmit` in `go.opentelemetry.io/otel/sdk/log` now accepts a pointer to `Record` instead of a value so that the record modifications done in a processor are propagated to subsequent registered processors. (#5636) +- `SimpleProcessor.Enabled` in `go.opentelemetry.io/otel/sdk/log` now returns `false` if the exporter is `nil`. (#5665) +- Update the concurrency requirements of `Exporter` in `go.opentelemetry.io/otel/sdk/log`. (#5666) +- `SimpleProcessor` in `go.opentelemetry.io/otel/sdk/log` synchronizes `OnEmit` calls. (#5666) +- The `Processor` interface in `go.opentelemetry.io/otel/sdk/log` no longer includes the `Enabled` method. + See the `FilterProcessor` interface type added in `go.opentelemetry.io/otel/sdk/log/internal/x` to continue providing this functionality. (#5692) +- The `SimpleProcessor` type in `go.opentelemetry.io/otel/sdk/log` is no longer comparable. (#5693) +- The `BatchProcessor` type in `go.opentelemetry.io/otel/sdk/log` is no longer comparable. (#5693) + +### Fixed + +- Correct comments for the priority of the `WithEndpoint` and `WithEndpointURL` options and their corresponding environment variables in `go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp`. (#5584) +- Pass the underlying error rather than a generic retry-able failure in `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp`, `go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp` and `go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp`. (#5541) +- Correct the `Tracer`, `Meter`, and `Logger` names used in `go.opentelemetry.io/otel/example/dice`. (#5612) +- Correct the `Tracer` names used in `go.opentelemetry.io/otel/example/namedtracer`. (#5612) +- Correct the `Tracer` name used in `go.opentelemetry.io/otel/example/opencensus`. (#5612) +- Correct the `Tracer` and `Meter` names used in `go.opentelemetry.io/otel/example/otel-collector`. (#5612) +- Correct the `Tracer` names used in `go.opentelemetry.io/otel/example/passthrough`. (#5612) +- Correct the `Meter` name used in `go.opentelemetry.io/otel/example/prometheus`. (#5612) +- Correct the `Tracer` names used in `go.opentelemetry.io/otel/example/zipkin`. (#5612) +- Correct comments for the priority of the `WithEndpoint` and `WithEndpointURL` options and their corresponding environment variables in `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc` and `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp`. (#5641) +- Correct comments for the priority of the `WithEndpoint` and `WithEndpointURL` options and their corresponding environment variables in `go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp`. (#5650) +- Stop percent encoding header environment variables in `go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc`, `go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp`, `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc` and `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp` (#5705) +- Remove invalid environment variable header keys in `go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc`, `go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp`, `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetricgrpc` and `go.opentelemetry.io/otel/exporters/otlp/otlpmetric/otlpmetrichttp` (#5705) + +### Removed + +- The `Enabled` method of the `SimpleProcessor` in `go.opentelemetry.io/otel/sdk/log` is removed. (#5692) +- The `Enabled` method of the `BatchProcessor` in `go.opentelemetry.io/otel/sdk/log` is removed. (#5692) + ## [1.28.0/0.50.0/0.4.0] 2024-07-02 ### Added @@ -49,6 +107,7 @@ This project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.htm - Fix stale timestamps reported by the last-value aggregation. (#5517) - Indicate the `Exporter` in `go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp` must be created by the `New` method. (#5521) - Improved performance in all `{Bool,Int64,Float64,String}SliceValue` functions of `go.opentelemetry.io/attributes` by reducing the number of allocations. (#5549) +- Replace invalid percent-encoded octet sequences with replacement char in `go.opentelemetry.io/otel/baggage`. (#5528) ## [1.27.0/0.49.0/0.3.0] 2024-05-21 @@ -175,7 +234,7 @@ The next release will require at least [Go 1.21]. This module includes OpenTelemetry Go's implementation of the Logs Bridge API. This module is in an alpha state, it is subject to breaking changes. See our [versioning policy](./VERSIONING.md) for more info. (#4961) -- ARM64 platform to the compatibility testing suite. (#4994) +- Add ARM64 platform to the compatibility testing suite. (#4994) ### Fixed @@ -3003,7 +3062,8 @@ It contains api and sdk for trace and meter. - CircleCI build CI manifest files. - CODEOWNERS file to track owners of this project. -[Unreleased]: https://github.com/open-telemetry/opentelemetry-go/compare/v1.28.0...HEAD +[Unreleased]: https://github.com/open-telemetry/opentelemetry-go/compare/v1.29.0...HEAD +[1.29.0/0.51.0/0.5.0]: https://github.com/open-telemetry/opentelemetry-go/releases/tag/v1.29.0 [1.28.0/0.50.0/0.4.0]: https://github.com/open-telemetry/opentelemetry-go/releases/tag/v1.28.0 [1.27.0/0.49.0/0.3.0]: https://github.com/open-telemetry/opentelemetry-go/releases/tag/v1.27.0 [1.26.0/0.48.0/0.2.0-alpha]: https://github.com/open-telemetry/opentelemetry-go/releases/tag/v1.26.0 @@ -3086,6 +3146,9 @@ It contains api and sdk for trace and meter. [0.1.1]: https://github.com/open-telemetry/opentelemetry-go/releases/tag/v0.1.1 [0.1.0]: https://github.com/open-telemetry/opentelemetry-go/releases/tag/v0.1.0 + + +[Go 1.23]: https://go.dev/doc/go1.23 [Go 1.22]: https://go.dev/doc/go1.22 [Go 1.21]: https://go.dev/doc/go1.21 [Go 1.20]: https://go.dev/doc/go1.20 diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CODEOWNERS b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CODEOWNERS index 20255493323..5904bb7070e 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CODEOWNERS +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CODEOWNERS @@ -5,7 +5,7 @@ ##################################################### # # Learn about membership in OpenTelemetry community: -# https://github.com/open-telemetry/community/blob/main/community-membership.md +# https://github.com/open-telemetry/community/blob/main/guides/contributor/membership.md # # # Learn about CODEOWNERS file format: diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CONTRIBUTING.md b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CONTRIBUTING.md index b86572f58ea..b7402576f98 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CONTRIBUTING.md +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/CONTRIBUTING.md @@ -650,7 +650,7 @@ should be canceled. ### Become an Approver or a Maintainer See the [community membership document in OpenTelemetry community -repo](https://github.com/open-telemetry/community/blob/main/community-membership.md). +repo](https://github.com/open-telemetry/community/blob/main/guides/contributor/membership.md). [Approver]: #approvers [Maintainer]: #maintainers diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/Makefile b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/Makefile index f33619f76a2..070b1e57df1 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/Makefile +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/Makefile @@ -178,17 +178,14 @@ test-coverage: $(GOCOVMERGE) done; \ $(GOCOVMERGE) $$(find . -name coverage.out) > coverage.txt -# Adding a directory will include all benchmarks in that directory if a filter is not specified. -BENCHMARK_TARGETS := sdk/trace .PHONY: benchmark -benchmark: $(BENCHMARK_TARGETS:%=benchmark/%) -BENCHMARK_FILTER = . -# You can override the filter for a particular directory by adding a rule here. -benchmark/sdk/trace: BENCHMARK_FILTER = SpanWithAttributes_8/AlwaysSample +benchmark: $(OTEL_GO_MOD_DIRS:%=benchmark/%) benchmark/%: - @echo "$(GO) test -timeout $(TIMEOUT)s -run=xxxxxMatchNothingxxxxx -bench=$(BENCHMARK_FILTER) $*..." \ + @echo "$(GO) test -run=xxxxxMatchNothingxxxxx -bench=. $*..." \ && cd $* \ - $(foreach filter, $(BENCHMARK_FILTER), && $(GO) test -timeout $(TIMEOUT)s -run=xxxxxMatchNothingxxxxx -bench=$(filter)) + && $(GO) list ./... \ + | grep -v third_party \ + | xargs $(GO) test -run=xxxxxMatchNothingxxxxx -bench=. .PHONY: golangci-lint golangci-lint-fix golangci-lint-fix: ARGS=--fix diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/README.md b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/README.md index 5a890931731..657df347103 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/README.md +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/README.md @@ -47,20 +47,29 @@ stop ensuring compatibility with these versions in the following manner: Currently, this project supports the following environments. -| OS | Go Version | Architecture | -|---------|------------|--------------| -| Ubuntu | 1.22 | amd64 | -| Ubuntu | 1.21 | amd64 | -| Ubuntu | 1.22 | 386 | -| Ubuntu | 1.21 | 386 | -| Linux | 1.22 | arm64 | -| Linux | 1.21 | arm64 | -| MacOS | 1.22 | amd64 | -| MacOS | 1.21 | amd64 | -| Windows | 1.22 | amd64 | -| Windows | 1.21 | amd64 | -| Windows | 1.22 | 386 | -| Windows | 1.21 | 386 | +| OS | Go Version | Architecture | +|----------|------------|--------------| +| Ubuntu | 1.23 | amd64 | +| Ubuntu | 1.22 | amd64 | +| Ubuntu | 1.21 | amd64 | +| Ubuntu | 1.23 | 386 | +| Ubuntu | 1.22 | 386 | +| Ubuntu | 1.21 | 386 | +| Linux | 1.23 | arm64 | +| Linux | 1.22 | arm64 | +| Linux | 1.21 | arm64 | +| macOS 13 | 1.23 | amd64 | +| macOS 13 | 1.22 | amd64 | +| macOS 13 | 1.21 | amd64 | +| macOS | 1.23 | arm64 | +| macOS | 1.22 | arm64 | +| macOS | 1.21 | arm64 | +| Windows | 1.23 | amd64 | +| Windows | 1.22 | amd64 | +| Windows | 1.21 | amd64 | +| Windows | 1.23 | 386 | +| Windows | 1.22 | 386 | +| Windows | 1.21 | 386 | While this project should work for other systems, no compatibility guarantees are made for those systems currently. diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/RELEASING.md b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/RELEASING.md index 940f57f3d87..59992984d42 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/RELEASING.md +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/RELEASING.md @@ -69,6 +69,7 @@ Update go.mod for submodules to depend on the new release which will happen in t ``` - Move all the `Unreleased` changes into a new section following the title scheme (`[] - `). + - Make sure the new section is under the comment for released section, like ``, so it is protected from being overwritten in the future. - Update all the appropriate links at the bottom. 4. Push the changes to upstream and create a Pull Request on GitHub. diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/baggage/baggage.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/baggage/baggage.go index c40c896cc66..b3569e95e5c 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/baggage/baggage.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/baggage/baggage.go @@ -44,9 +44,15 @@ type Property struct { // NewKeyProperty returns a new Property for key. // +// The passed key must be valid, non-empty UTF-8 string. // If key is invalid, an error will be returned. +// However, the specific Propagators that are used to transmit baggage entries across +// component boundaries may impose their own restrictions on Property key. +// For example, the W3C Baggage specification restricts the Property keys to strings that +// satisfy the token definition from RFC7230, Section 3.2.6. +// For maximum compatibility, alpha-numeric value are strongly recommended to be used as Property key. func NewKeyProperty(key string) (Property, error) { - if !validateKey(key) { + if !validateBaggageName(key) { return newInvalidProperty(), fmt.Errorf("%w: %q", errInvalidKey, key) } @@ -62,6 +68,10 @@ func NewKeyProperty(key string) (Property, error) { // Notice: Consider using [NewKeyValuePropertyRaw] instead // that does not require percent-encoding of the value. func NewKeyValueProperty(key, value string) (Property, error) { + if !validateKey(key) { + return newInvalidProperty(), fmt.Errorf("%w: %q", errInvalidKey, key) + } + if !validateValue(value) { return newInvalidProperty(), fmt.Errorf("%w: %q", errInvalidValue, value) } @@ -74,11 +84,20 @@ func NewKeyValueProperty(key, value string) (Property, error) { // NewKeyValuePropertyRaw returns a new Property for key with value. // -// The passed key must be compliant with W3C Baggage specification. +// The passed key must be valid, non-empty UTF-8 string. +// The passed value must be valid UTF-8 string. +// However, the specific Propagators that are used to transmit baggage entries across +// component boundaries may impose their own restrictions on Property key. +// For example, the W3C Baggage specification restricts the Property keys to strings that +// satisfy the token definition from RFC7230, Section 3.2.6. +// For maximum compatibility, alpha-numeric value are strongly recommended to be used as Property key. func NewKeyValuePropertyRaw(key, value string) (Property, error) { - if !validateKey(key) { + if !validateBaggageName(key) { return newInvalidProperty(), fmt.Errorf("%w: %q", errInvalidKey, key) } + if !validateBaggageValue(value) { + return newInvalidProperty(), fmt.Errorf("%w: %q", errInvalidValue, value) + } p := Property{ key: key, @@ -115,12 +134,15 @@ func (p Property) validate() error { return fmt.Errorf("invalid property: %w", err) } - if !validateKey(p.key) { + if !validateBaggageName(p.key) { return errFunc(fmt.Errorf("%w: %q", errInvalidKey, p.key)) } if !p.hasValue && p.value != "" { return errFunc(errors.New("inconsistent value")) } + if p.hasValue && !validateBaggageValue(p.value) { + return errFunc(fmt.Errorf("%w: %q", errInvalidValue, p.value)) + } return nil } @@ -138,7 +160,15 @@ func (p Property) Value() (string, bool) { // String encodes Property into a header string compliant with the W3C Baggage // specification. +// It would return empty string if the key is invalid with the W3C Baggage +// specification. This could happen for a UTF-8 key, as it may contain +// invalid characters. func (p Property) String() string { + // W3C Baggage specification does not allow percent-encoded keys. + if !validateKey(p.key) { + return "" + } + if p.hasValue { return fmt.Sprintf("%s%s%v", p.key, keyValueDelimiter, valueEscape(p.value)) } @@ -203,9 +233,14 @@ func (p properties) validate() error { // String encodes properties into a header string compliant with the W3C Baggage // specification. func (p properties) String() string { - props := make([]string, len(p)) - for i, prop := range p { - props[i] = prop.String() + props := make([]string, 0, len(p)) + for _, prop := range p { + s := prop.String() + + // Ignored empty properties. + if s != "" { + props = append(props, s) + } } return strings.Join(props, propertyDelimiter) } @@ -230,6 +265,10 @@ type Member struct { // Notice: Consider using [NewMemberRaw] instead // that does not require percent-encoding of the value. func NewMember(key, value string, props ...Property) (Member, error) { + if !validateKey(key) { + return newInvalidMember(), fmt.Errorf("%w: %q", errInvalidKey, key) + } + if !validateValue(value) { return newInvalidMember(), fmt.Errorf("%w: %q", errInvalidValue, value) } @@ -242,7 +281,13 @@ func NewMember(key, value string, props ...Property) (Member, error) { // NewMemberRaw returns a new Member from the passed arguments. // -// The passed key must be compliant with W3C Baggage specification. +// The passed key must be valid, non-empty UTF-8 string. +// The passed value must be valid UTF-8 string. +// However, the specific Propagators that are used to transmit baggage entries across +// component boundaries may impose their own restrictions on baggage key. +// For example, the W3C Baggage specification restricts the baggage keys to strings that +// satisfy the token definition from RFC7230, Section 3.2.6. +// For maximum compatibility, alpha-numeric value are strongly recommended to be used as baggage key. func NewMemberRaw(key, value string, props ...Property) (Member, error) { m := Member{ key: key, @@ -294,19 +339,45 @@ func parseMember(member string) (Member, error) { return newInvalidMember(), fmt.Errorf("%w: %q", errInvalidKey, key) } - val := strings.TrimSpace(v) - if !validateValue(val) { + rawVal := strings.TrimSpace(v) + if !validateValue(rawVal) { return newInvalidMember(), fmt.Errorf("%w: %q", errInvalidValue, v) } // Decode a percent-encoded value. - value, err := url.PathUnescape(val) + unescapeVal, err := url.PathUnescape(rawVal) if err != nil { return newInvalidMember(), fmt.Errorf("%w: %w", errInvalidValue, err) } + + value := replaceInvalidUTF8Sequences(len(rawVal), unescapeVal) return Member{key: key, value: value, properties: props, hasData: true}, nil } +// replaceInvalidUTF8Sequences replaces invalid UTF-8 sequences with '�'. +func replaceInvalidUTF8Sequences(cap int, unescapeVal string) string { + if utf8.ValidString(unescapeVal) { + return unescapeVal + } + // W3C baggage spec: + // https://github.com/w3c/baggage/blob/8c215efbeebd3fa4b1aceb937a747e56444f22f3/baggage/HTTP_HEADER_FORMAT.md?plain=1#L69 + + var b strings.Builder + b.Grow(cap) + for i := 0; i < len(unescapeVal); { + r, size := utf8.DecodeRuneInString(unescapeVal[i:]) + if r == utf8.RuneError && size == 1 { + // Invalid UTF-8 sequence found, replace it with '�' + _, _ = b.WriteString("�") + } else { + _, _ = b.WriteRune(r) + } + i += size + } + + return b.String() +} + // validate ensures m conforms to the W3C Baggage specification. // A key must be an ASCII string, returning an error otherwise. func (m Member) validate() error { @@ -314,9 +385,12 @@ func (m Member) validate() error { return fmt.Errorf("%w: %q", errInvalidMember, m) } - if !validateKey(m.key) { + if !validateBaggageName(m.key) { return fmt.Errorf("%w: %q", errInvalidKey, m.key) } + if !validateBaggageValue(m.value) { + return fmt.Errorf("%w: %q", errInvalidValue, m.value) + } return m.properties.validate() } @@ -331,10 +405,15 @@ func (m Member) Properties() []Property { return m.properties.Copy() } // String encodes Member into a header string compliant with the W3C Baggage // specification. +// It would return empty string if the key is invalid with the W3C Baggage +// specification. This could happen for a UTF-8 key, as it may contain +// invalid characters. func (m Member) String() string { - // A key is just an ASCII string. A value is restricted to be - // US-ASCII characters excluding CTLs, whitespace, - // DQUOTE, comma, semicolon, and backslash. + // W3C Baggage specification does not allow percent-encoded keys. + if !validateKey(m.key) { + return "" + } + s := m.key + keyValueDelimiter + valueEscape(m.value) if len(m.properties) > 0 { s += propertyDelimiter + m.properties.String() @@ -448,7 +527,7 @@ func (b Baggage) Member(key string) Member { } // Members returns all the baggage list-members. -// The order of the returned list-members does not have significance. +// The order of the returned list-members is not significant. // // The returned members are not validated, as we assume the validation happened // when they were added to the Baggage. @@ -469,8 +548,8 @@ func (b Baggage) Members() []Member { return members } -// SetMember returns a copy the Baggage with the member included. If the -// baggage contains a Member with the same key the existing Member is +// SetMember returns a copy of the Baggage with the member included. If the +// baggage contains a Member with the same key, the existing Member is // replaced. // // If member is invalid according to the W3C Baggage specification, an error @@ -528,14 +607,22 @@ func (b Baggage) Len() int { // String encodes Baggage into a header string compliant with the W3C Baggage // specification. +// It would ignore members where the member key is invalid with the W3C Baggage +// specification. This could happen for a UTF-8 key, as it may contain +// invalid characters. func (b Baggage) String() string { members := make([]string, 0, len(b.list)) for k, v := range b.list { - members = append(members, Member{ + s := Member{ key: k, value: v.Value, properties: fromInternalProperties(v.Properties), - }.String()) + }.String() + + // Ignored empty members. + if s != "" { + members = append(members, s) + } } return strings.Join(members, listDelimiter) } @@ -607,10 +694,12 @@ func parsePropertyInternal(s string) (p Property, ok bool) { } // Decode a percent-encoded value. - value, err := url.PathUnescape(s[valueStart:valueEnd]) + rawVal := s[valueStart:valueEnd] + unescapeVal, err := url.PathUnescape(rawVal) if err != nil { return } + value := replaceInvalidUTF8Sequences(len(rawVal), unescapeVal) ok = true p.key = s[keyStart:keyEnd] @@ -720,6 +809,24 @@ var safeKeyCharset = [utf8.RuneSelf]bool{ '~': true, } +// validateBaggageName checks if the string is a valid OpenTelemetry Baggage name. +// Baggage name is a valid, non-empty UTF-8 string. +func validateBaggageName(s string) bool { + if len(s) == 0 { + return false + } + + return utf8.ValidString(s) +} + +// validateBaggageValue checks if the string is a valid OpenTelemetry Baggage value. +// Baggage value is a valid UTF-8 strings. +// Empty string is also a valid UTF-8 string. +func validateBaggageValue(s string) bool { + return utf8.ValidString(s) +} + +// validateKey checks if the string is a valid W3C Baggage key. func validateKey(s string) bool { if len(s) == 0 { return false @@ -738,6 +845,7 @@ func validateKeyChar(c int32) bool { return c >= 0 && c < int32(utf8.RuneSelf) && safeKeyCharset[c] } +// validateValue checks if the string is a valid W3C Baggage value. func validateValue(s string) bool { for _, c := range s { if !validateValueChar(c) { diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/codes/codes.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/codes/codes.go index df29d96a6da..2acbac35466 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/codes/codes.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/codes/codes.go @@ -83,7 +83,7 @@ func (c *Code) UnmarshalJSON(b []byte) error { return fmt.Errorf("invalid code: %q", ci) } - *c = Code(ci) + *c = Code(ci) // nolint: gosec // Bit size of 32 check above. return nil } return fmt.Errorf("invalid code: %q", string(b)) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/doc.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/doc.go index 441c595014d..921f85961ad 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/doc.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/doc.go @@ -17,6 +17,8 @@ To read more about tracing, see go.opentelemetry.io/otel/trace. To read more about metrics, see go.opentelemetry.io/otel/metric. +To read more about logs, see go.opentelemetry.io/otel/log. + To read more about propagation, see go.opentelemetry.io/otel/propagation and go.opentelemetry.io/otel/baggage. */ diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/internal/rawhelpers.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/internal/rawhelpers.go index 3e7bb3b3566..9b1da2c02b9 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/internal/rawhelpers.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/internal/rawhelpers.go @@ -24,7 +24,8 @@ func Int64ToRaw(i int64) uint64 { } func RawToInt64(r uint64) int64 { - return int64(r) + // Assumes original was a valid int64 (overflow not checked). + return int64(r) // nolint: gosec } func Float64ToRaw(f float64) uint64 { @@ -36,9 +37,11 @@ func RawToFloat64(r uint64) float64 { } func RawPtrToFloat64Ptr(r *uint64) *float64 { - return (*float64)(unsafe.Pointer(r)) + // Assumes original was a valid *float64 (overflow not checked). + return (*float64)(unsafe.Pointer(r)) // nolint: gosec } func RawPtrToInt64Ptr(r *uint64) *int64 { - return (*int64)(unsafe.Pointer(r)) + // Assumes original was a valid *int64 (overflow not checked). + return (*int64)(unsafe.Pointer(r)) // nolint: gosec } diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/meter.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/meter.go index 6a7991e0151..14e08c24a4b 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/meter.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/meter.go @@ -52,6 +52,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Int64Counter(name string, options ...Int64CounterOption) (Int64Counter, error) + // Int64UpDownCounter returns a new Int64UpDownCounter instrument // identified by name and configured with options. The instrument is used // to synchronously record int64 measurements during a computational @@ -61,6 +62,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Int64UpDownCounter(name string, options ...Int64UpDownCounterOption) (Int64UpDownCounter, error) + // Int64Histogram returns a new Int64Histogram instrument identified by // name and configured with options. The instrument is used to // synchronously record the distribution of int64 measurements during a @@ -70,6 +72,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Int64Histogram(name string, options ...Int64HistogramOption) (Int64Histogram, error) + // Int64Gauge returns a new Int64Gauge instrument identified by name and // configured with options. The instrument is used to synchronously record // instantaneous int64 measurements during a computational operation. @@ -78,6 +81,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Int64Gauge(name string, options ...Int64GaugeOption) (Int64Gauge, error) + // Int64ObservableCounter returns a new Int64ObservableCounter identified // by name and configured with options. The instrument is used to // asynchronously record increasing int64 measurements once per a @@ -92,6 +96,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Int64ObservableCounter(name string, options ...Int64ObservableCounterOption) (Int64ObservableCounter, error) + // Int64ObservableUpDownCounter returns a new Int64ObservableUpDownCounter // instrument identified by name and configured with options. The // instrument is used to asynchronously record int64 measurements once per @@ -106,6 +111,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Int64ObservableUpDownCounter(name string, options ...Int64ObservableUpDownCounterOption) (Int64ObservableUpDownCounter, error) + // Int64ObservableGauge returns a new Int64ObservableGauge instrument // identified by name and configured with options. The instrument is used // to asynchronously record instantaneous int64 measurements once per a @@ -130,6 +136,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Float64Counter(name string, options ...Float64CounterOption) (Float64Counter, error) + // Float64UpDownCounter returns a new Float64UpDownCounter instrument // identified by name and configured with options. The instrument is used // to synchronously record float64 measurements during a computational @@ -139,6 +146,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Float64UpDownCounter(name string, options ...Float64UpDownCounterOption) (Float64UpDownCounter, error) + // Float64Histogram returns a new Float64Histogram instrument identified by // name and configured with options. The instrument is used to // synchronously record the distribution of float64 measurements during a @@ -148,6 +156,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Float64Histogram(name string, options ...Float64HistogramOption) (Float64Histogram, error) + // Float64Gauge returns a new Float64Gauge instrument identified by name and // configured with options. The instrument is used to synchronously record // instantaneous float64 measurements during a computational operation. @@ -156,6 +165,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Float64Gauge(name string, options ...Float64GaugeOption) (Float64Gauge, error) + // Float64ObservableCounter returns a new Float64ObservableCounter // instrument identified by name and configured with options. The // instrument is used to asynchronously record increasing float64 @@ -170,6 +180,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Float64ObservableCounter(name string, options ...Float64ObservableCounterOption) (Float64ObservableCounter, error) + // Float64ObservableUpDownCounter returns a new // Float64ObservableUpDownCounter instrument identified by name and // configured with options. The instrument is used to asynchronously record @@ -184,6 +195,7 @@ type Meter interface { // See the Instrument Name section of the package documentation for more // information. Float64ObservableUpDownCounter(name string, options ...Float64ObservableUpDownCounterOption) (Float64ObservableUpDownCounter, error) + // Float64ObservableGauge returns a new Float64ObservableGauge instrument // identified by name and configured with options. The instrument is used // to asynchronously record instantaneous float64 measurements once per a @@ -242,6 +254,7 @@ type Observer interface { // ObserveFloat64 records the float64 value for obsrv. ObserveFloat64(obsrv Float64Observable, value float64, opts ...ObserveOption) + // ObserveInt64 records the int64 value for obsrv. ObserveInt64(obsrv Int64Observable, value int64, opts ...ObserveOption) } diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/README.md b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/README.md new file mode 100644 index 00000000000..bb89694356b --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/README.md @@ -0,0 +1,3 @@ +# Metric Noop + +[![PkgGoDev](https://pkg.go.dev/badge/go.opentelemetry.io/otel/metric/noop)](https://pkg.go.dev/go.opentelemetry.io/otel/metric/noop) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/noop.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/noop.go new file mode 100644 index 00000000000..ca6fcbdc099 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/metric/noop/noop.go @@ -0,0 +1,281 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +// Package noop provides an implementation of the OpenTelemetry metric API that +// produces no telemetry and minimizes used computation resources. +// +// Using this package to implement the OpenTelemetry metric API will +// effectively disable OpenTelemetry. +// +// This implementation can be embedded in other implementations of the +// OpenTelemetry metric API. Doing so will mean the implementation defaults to +// no operation for methods it does not implement. +package noop // import "go.opentelemetry.io/otel/metric/noop" + +import ( + "context" + + "go.opentelemetry.io/otel/metric" + "go.opentelemetry.io/otel/metric/embedded" +) + +var ( + // Compile-time check this implements the OpenTelemetry API. + + _ metric.MeterProvider = MeterProvider{} + _ metric.Meter = Meter{} + _ metric.Observer = Observer{} + _ metric.Registration = Registration{} + _ metric.Int64Counter = Int64Counter{} + _ metric.Float64Counter = Float64Counter{} + _ metric.Int64UpDownCounter = Int64UpDownCounter{} + _ metric.Float64UpDownCounter = Float64UpDownCounter{} + _ metric.Int64Histogram = Int64Histogram{} + _ metric.Float64Histogram = Float64Histogram{} + _ metric.Int64Gauge = Int64Gauge{} + _ metric.Float64Gauge = Float64Gauge{} + _ metric.Int64ObservableCounter = Int64ObservableCounter{} + _ metric.Float64ObservableCounter = Float64ObservableCounter{} + _ metric.Int64ObservableGauge = Int64ObservableGauge{} + _ metric.Float64ObservableGauge = Float64ObservableGauge{} + _ metric.Int64ObservableUpDownCounter = Int64ObservableUpDownCounter{} + _ metric.Float64ObservableUpDownCounter = Float64ObservableUpDownCounter{} + _ metric.Int64Observer = Int64Observer{} + _ metric.Float64Observer = Float64Observer{} +) + +// MeterProvider is an OpenTelemetry No-Op MeterProvider. +type MeterProvider struct{ embedded.MeterProvider } + +// NewMeterProvider returns a MeterProvider that does not record any telemetry. +func NewMeterProvider() MeterProvider { + return MeterProvider{} +} + +// Meter returns an OpenTelemetry Meter that does not record any telemetry. +func (MeterProvider) Meter(string, ...metric.MeterOption) metric.Meter { + return Meter{} +} + +// Meter is an OpenTelemetry No-Op Meter. +type Meter struct{ embedded.Meter } + +// Int64Counter returns a Counter used to record int64 measurements that +// produces no telemetry. +func (Meter) Int64Counter(string, ...metric.Int64CounterOption) (metric.Int64Counter, error) { + return Int64Counter{}, nil +} + +// Int64UpDownCounter returns an UpDownCounter used to record int64 +// measurements that produces no telemetry. +func (Meter) Int64UpDownCounter(string, ...metric.Int64UpDownCounterOption) (metric.Int64UpDownCounter, error) { + return Int64UpDownCounter{}, nil +} + +// Int64Histogram returns a Histogram used to record int64 measurements that +// produces no telemetry. +func (Meter) Int64Histogram(string, ...metric.Int64HistogramOption) (metric.Int64Histogram, error) { + return Int64Histogram{}, nil +} + +// Int64Gauge returns a Gauge used to record int64 measurements that +// produces no telemetry. +func (Meter) Int64Gauge(string, ...metric.Int64GaugeOption) (metric.Int64Gauge, error) { + return Int64Gauge{}, nil +} + +// Int64ObservableCounter returns an ObservableCounter used to record int64 +// measurements that produces no telemetry. +func (Meter) Int64ObservableCounter(string, ...metric.Int64ObservableCounterOption) (metric.Int64ObservableCounter, error) { + return Int64ObservableCounter{}, nil +} + +// Int64ObservableUpDownCounter returns an ObservableUpDownCounter used to +// record int64 measurements that produces no telemetry. +func (Meter) Int64ObservableUpDownCounter(string, ...metric.Int64ObservableUpDownCounterOption) (metric.Int64ObservableUpDownCounter, error) { + return Int64ObservableUpDownCounter{}, nil +} + +// Int64ObservableGauge returns an ObservableGauge used to record int64 +// measurements that produces no telemetry. +func (Meter) Int64ObservableGauge(string, ...metric.Int64ObservableGaugeOption) (metric.Int64ObservableGauge, error) { + return Int64ObservableGauge{}, nil +} + +// Float64Counter returns a Counter used to record int64 measurements that +// produces no telemetry. +func (Meter) Float64Counter(string, ...metric.Float64CounterOption) (metric.Float64Counter, error) { + return Float64Counter{}, nil +} + +// Float64UpDownCounter returns an UpDownCounter used to record int64 +// measurements that produces no telemetry. +func (Meter) Float64UpDownCounter(string, ...metric.Float64UpDownCounterOption) (metric.Float64UpDownCounter, error) { + return Float64UpDownCounter{}, nil +} + +// Float64Histogram returns a Histogram used to record int64 measurements that +// produces no telemetry. +func (Meter) Float64Histogram(string, ...metric.Float64HistogramOption) (metric.Float64Histogram, error) { + return Float64Histogram{}, nil +} + +// Float64Gauge returns a Gauge used to record float64 measurements that +// produces no telemetry. +func (Meter) Float64Gauge(string, ...metric.Float64GaugeOption) (metric.Float64Gauge, error) { + return Float64Gauge{}, nil +} + +// Float64ObservableCounter returns an ObservableCounter used to record int64 +// measurements that produces no telemetry. +func (Meter) Float64ObservableCounter(string, ...metric.Float64ObservableCounterOption) (metric.Float64ObservableCounter, error) { + return Float64ObservableCounter{}, nil +} + +// Float64ObservableUpDownCounter returns an ObservableUpDownCounter used to +// record int64 measurements that produces no telemetry. +func (Meter) Float64ObservableUpDownCounter(string, ...metric.Float64ObservableUpDownCounterOption) (metric.Float64ObservableUpDownCounter, error) { + return Float64ObservableUpDownCounter{}, nil +} + +// Float64ObservableGauge returns an ObservableGauge used to record int64 +// measurements that produces no telemetry. +func (Meter) Float64ObservableGauge(string, ...metric.Float64ObservableGaugeOption) (metric.Float64ObservableGauge, error) { + return Float64ObservableGauge{}, nil +} + +// RegisterCallback performs no operation. +func (Meter) RegisterCallback(metric.Callback, ...metric.Observable) (metric.Registration, error) { + return Registration{}, nil +} + +// Observer acts as a recorder of measurements for multiple instruments in a +// Callback, it performing no operation. +type Observer struct{ embedded.Observer } + +// ObserveFloat64 performs no operation. +func (Observer) ObserveFloat64(metric.Float64Observable, float64, ...metric.ObserveOption) { +} + +// ObserveInt64 performs no operation. +func (Observer) ObserveInt64(metric.Int64Observable, int64, ...metric.ObserveOption) { +} + +// Registration is the registration of a Callback with a No-Op Meter. +type Registration struct{ embedded.Registration } + +// Unregister unregisters the Callback the Registration represents with the +// No-Op Meter. This will always return nil because the No-Op Meter performs no +// operation, including hold any record of registrations. +func (Registration) Unregister() error { return nil } + +// Int64Counter is an OpenTelemetry Counter used to record int64 measurements. +// It produces no telemetry. +type Int64Counter struct{ embedded.Int64Counter } + +// Add performs no operation. +func (Int64Counter) Add(context.Context, int64, ...metric.AddOption) {} + +// Float64Counter is an OpenTelemetry Counter used to record float64 +// measurements. It produces no telemetry. +type Float64Counter struct{ embedded.Float64Counter } + +// Add performs no operation. +func (Float64Counter) Add(context.Context, float64, ...metric.AddOption) {} + +// Int64UpDownCounter is an OpenTelemetry UpDownCounter used to record int64 +// measurements. It produces no telemetry. +type Int64UpDownCounter struct{ embedded.Int64UpDownCounter } + +// Add performs no operation. +func (Int64UpDownCounter) Add(context.Context, int64, ...metric.AddOption) {} + +// Float64UpDownCounter is an OpenTelemetry UpDownCounter used to record +// float64 measurements. It produces no telemetry. +type Float64UpDownCounter struct{ embedded.Float64UpDownCounter } + +// Add performs no operation. +func (Float64UpDownCounter) Add(context.Context, float64, ...metric.AddOption) {} + +// Int64Histogram is an OpenTelemetry Histogram used to record int64 +// measurements. It produces no telemetry. +type Int64Histogram struct{ embedded.Int64Histogram } + +// Record performs no operation. +func (Int64Histogram) Record(context.Context, int64, ...metric.RecordOption) {} + +// Float64Histogram is an OpenTelemetry Histogram used to record float64 +// measurements. It produces no telemetry. +type Float64Histogram struct{ embedded.Float64Histogram } + +// Record performs no operation. +func (Float64Histogram) Record(context.Context, float64, ...metric.RecordOption) {} + +// Int64Gauge is an OpenTelemetry Gauge used to record instantaneous int64 +// measurements. It produces no telemetry. +type Int64Gauge struct{ embedded.Int64Gauge } + +// Record performs no operation. +func (Int64Gauge) Record(context.Context, int64, ...metric.RecordOption) {} + +// Float64Gauge is an OpenTelemetry Gauge used to record instantaneous float64 +// measurements. It produces no telemetry. +type Float64Gauge struct{ embedded.Float64Gauge } + +// Record performs no operation. +func (Float64Gauge) Record(context.Context, float64, ...metric.RecordOption) {} + +// Int64ObservableCounter is an OpenTelemetry ObservableCounter used to record +// int64 measurements. It produces no telemetry. +type Int64ObservableCounter struct { + metric.Int64Observable + embedded.Int64ObservableCounter +} + +// Float64ObservableCounter is an OpenTelemetry ObservableCounter used to record +// float64 measurements. It produces no telemetry. +type Float64ObservableCounter struct { + metric.Float64Observable + embedded.Float64ObservableCounter +} + +// Int64ObservableGauge is an OpenTelemetry ObservableGauge used to record +// int64 measurements. It produces no telemetry. +type Int64ObservableGauge struct { + metric.Int64Observable + embedded.Int64ObservableGauge +} + +// Float64ObservableGauge is an OpenTelemetry ObservableGauge used to record +// float64 measurements. It produces no telemetry. +type Float64ObservableGauge struct { + metric.Float64Observable + embedded.Float64ObservableGauge +} + +// Int64ObservableUpDownCounter is an OpenTelemetry ObservableUpDownCounter +// used to record int64 measurements. It produces no telemetry. +type Int64ObservableUpDownCounter struct { + metric.Int64Observable + embedded.Int64ObservableUpDownCounter +} + +// Float64ObservableUpDownCounter is an OpenTelemetry ObservableUpDownCounter +// used to record float64 measurements. It produces no telemetry. +type Float64ObservableUpDownCounter struct { + metric.Float64Observable + embedded.Float64ObservableUpDownCounter +} + +// Int64Observer is a recorder of int64 measurements that performs no operation. +type Int64Observer struct{ embedded.Int64Observer } + +// Observe performs no operation. +func (Int64Observer) Observe(int64, ...metric.ObserveOption) {} + +// Float64Observer is a recorder of float64 measurements that performs no +// operation. +type Float64Observer struct{ embedded.Float64Observer } + +// Observe performs no operation. +func (Float64Observer) Observe(float64, ...metric.ObserveOption) {} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/instrumentation/library.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/instrumentation/library.go index f4d1857c4f4..f2cdf3c6518 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/instrumentation/library.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/instrumentation/library.go @@ -4,5 +4,6 @@ package instrumentation // import "go.opentelemetry.io/otel/sdk/instrumentation" // Library represents the instrumentation library. -// Deprecated: please use Scope instead. +// +// Deprecated: use [Scope] instead. type Library = Scope diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/snapshot.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/snapshot.go index 32f862790c7..d511d0f271f 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/snapshot.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/snapshot.go @@ -99,7 +99,7 @@ func (s snapshot) InstrumentationScope() instrumentation.Scope { // InstrumentationLibrary returns information about the instrumentation // library that created the span. -func (s snapshot) InstrumentationLibrary() instrumentation.Library { +func (s snapshot) InstrumentationLibrary() instrumentation.Library { //nolint:staticcheck // This method needs to be define for backwards compatibility return s.instrumentationScope } diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/span.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/span.go index ac90f1a2600..4945f508303 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/span.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/trace/span.go @@ -62,7 +62,7 @@ type ReadOnlySpan interface { // InstrumentationLibrary returns information about the instrumentation // library that created the span. // Deprecated: please use InstrumentationScope instead. - InstrumentationLibrary() instrumentation.Library + InstrumentationLibrary() instrumentation.Library //nolint:staticcheck // This method needs to be define for backwards compatibility // Resource returns information about the entity that produced the span. Resource() *resource.Resource // DroppedAttributes returns the number of attributes dropped by the span @@ -642,7 +642,7 @@ func (s *recordingSpan) InstrumentationScope() instrumentation.Scope { // InstrumentationLibrary returns the instrumentation.Library associated with // the Tracer that created this span. -func (s *recordingSpan) InstrumentationLibrary() instrumentation.Library { +func (s *recordingSpan) InstrumentationLibrary() instrumentation.Library { //nolint:staticcheck // This method needs to be define for backwards compatibility s.mu.Lock() defer s.mu.Unlock() return s.tracer.instrumentationScope diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/version.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/version.go index 33d065a7cb9..b7cede891c4 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/version.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/sdk/version.go @@ -5,5 +5,5 @@ package sdk // import "go.opentelemetry.io/otel/sdk" // Version is the current release version of the OpenTelemetry SDK in use. func Version() string { - return "1.28.0" + return "1.29.0" } diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/README.md b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/README.md deleted file mode 100644 index 0b6cbe960cb..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/README.md +++ /dev/null @@ -1,3 +0,0 @@ -# Semconv v1.24.0 - -[![PkgGoDev](https://pkg.go.dev/badge/go.opentelemetry.io/otel/semconv/v1.24.0)](https://pkg.go.dev/go.opentelemetry.io/otel/semconv/v1.24.0) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/attribute_group.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/attribute_group.go deleted file mode 100644 index 6e688345cbb..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/attribute_group.go +++ /dev/null @@ -1,4387 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -// Code generated from semantic convention specification. DO NOT EDIT. - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -import "go.opentelemetry.io/otel/attribute" - -// Describes FaaS attributes. -const ( - // FaaSInvokedNameKey is the attribute Key conforming to the - // "faas.invoked_name" semantic conventions. It represents the name of the - // invoked function. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'my-function' - // Note: SHOULD be equal to the `faas.name` resource attribute of the - // invoked function. - FaaSInvokedNameKey = attribute.Key("faas.invoked_name") - - // FaaSInvokedProviderKey is the attribute Key conforming to the - // "faas.invoked_provider" semantic conventions. It represents the cloud - // provider of the invoked function. - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - // Note: SHOULD be equal to the `cloud.provider` resource attribute of the - // invoked function. - FaaSInvokedProviderKey = attribute.Key("faas.invoked_provider") - - // FaaSInvokedRegionKey is the attribute Key conforming to the - // "faas.invoked_region" semantic conventions. It represents the cloud - // region of the invoked function. - // - // Type: string - // RequirementLevel: ConditionallyRequired (For some cloud providers, like - // AWS or GCP, the region in which a function is hosted is essential to - // uniquely identify the function and also part of its endpoint. Since it's - // part of the endpoint being called, the region is always known to - // clients. In these cases, `faas.invoked_region` MUST be set accordingly. - // If the region is unknown to the client or not required for identifying - // the invoked function, setting `faas.invoked_region` is optional.) - // Stability: experimental - // Examples: 'eu-central-1' - // Note: SHOULD be equal to the `cloud.region` resource attribute of the - // invoked function. - FaaSInvokedRegionKey = attribute.Key("faas.invoked_region") - - // FaaSTriggerKey is the attribute Key conforming to the "faas.trigger" - // semantic conventions. It represents the type of the trigger which caused - // this function invocation. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - FaaSTriggerKey = attribute.Key("faas.trigger") -) - -var ( - // Alibaba Cloud - FaaSInvokedProviderAlibabaCloud = FaaSInvokedProviderKey.String("alibaba_cloud") - // Amazon Web Services - FaaSInvokedProviderAWS = FaaSInvokedProviderKey.String("aws") - // Microsoft Azure - FaaSInvokedProviderAzure = FaaSInvokedProviderKey.String("azure") - // Google Cloud Platform - FaaSInvokedProviderGCP = FaaSInvokedProviderKey.String("gcp") - // Tencent Cloud - FaaSInvokedProviderTencentCloud = FaaSInvokedProviderKey.String("tencent_cloud") -) - -var ( - // A response to some data source operation such as a database or filesystem read/write - FaaSTriggerDatasource = FaaSTriggerKey.String("datasource") - // To provide an answer to an inbound HTTP request - FaaSTriggerHTTP = FaaSTriggerKey.String("http") - // A function is set to be executed when messages are sent to a messaging system - FaaSTriggerPubsub = FaaSTriggerKey.String("pubsub") - // A function is scheduled to be executed regularly - FaaSTriggerTimer = FaaSTriggerKey.String("timer") - // If none of the others apply - FaaSTriggerOther = FaaSTriggerKey.String("other") -) - -// FaaSInvokedName returns an attribute KeyValue conforming to the -// "faas.invoked_name" semantic conventions. It represents the name of the -// invoked function. -func FaaSInvokedName(val string) attribute.KeyValue { - return FaaSInvokedNameKey.String(val) -} - -// FaaSInvokedRegion returns an attribute KeyValue conforming to the -// "faas.invoked_region" semantic conventions. It represents the cloud region -// of the invoked function. -func FaaSInvokedRegion(val string) attribute.KeyValue { - return FaaSInvokedRegionKey.String(val) -} - -// Attributes for Events represented using Log Records. -const ( - // EventNameKey is the attribute Key conforming to the "event.name" - // semantic conventions. It represents the identifies the class / type of - // event. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'browser.mouse.click', 'device.app.lifecycle' - // Note: Event names are subject to the same rules as [attribute - // names](https://github.com/open-telemetry/opentelemetry-specification/tree/v1.26.0/specification/common/attribute-naming.md). - // Notably, event names are namespaced to avoid collisions and provide a - // clean separation of semantics for events in separate domains like - // browser, mobile, and kubernetes. - EventNameKey = attribute.Key("event.name") -) - -// EventName returns an attribute KeyValue conforming to the "event.name" -// semantic conventions. It represents the identifies the class / type of -// event. -func EventName(val string) attribute.KeyValue { - return EventNameKey.String(val) -} - -// The attributes described in this section are rather generic. They may be -// used in any Log Record they apply to. -const ( - // LogRecordUIDKey is the attribute Key conforming to the "log.record.uid" - // semantic conventions. It represents a unique identifier for the Log - // Record. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '01ARZ3NDEKTSV4RRFFQ69G5FAV' - // Note: If an id is provided, other log records with the same id will be - // considered duplicates and can be removed safely. This means, that two - // distinguishable log records MUST have different values. - // The id MAY be an [Universally Unique Lexicographically Sortable - // Identifier (ULID)](https://github.com/ulid/spec), but other identifiers - // (e.g. UUID) may be used as needed. - LogRecordUIDKey = attribute.Key("log.record.uid") -) - -// LogRecordUID returns an attribute KeyValue conforming to the -// "log.record.uid" semantic conventions. It represents a unique identifier for -// the Log Record. -func LogRecordUID(val string) attribute.KeyValue { - return LogRecordUIDKey.String(val) -} - -// Describes Log attributes -const ( - // LogIostreamKey is the attribute Key conforming to the "log.iostream" - // semantic conventions. It represents the stream associated with the log. - // See below for a list of well-known values. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - LogIostreamKey = attribute.Key("log.iostream") -) - -var ( - // Logs from stdout stream - LogIostreamStdout = LogIostreamKey.String("stdout") - // Events from stderr stream - LogIostreamStderr = LogIostreamKey.String("stderr") -) - -// A file to which log was emitted. -const ( - // LogFileNameKey is the attribute Key conforming to the "log.file.name" - // semantic conventions. It represents the basename of the file. - // - // Type: string - // RequirementLevel: Recommended - // Stability: experimental - // Examples: 'audit.log' - LogFileNameKey = attribute.Key("log.file.name") - - // LogFileNameResolvedKey is the attribute Key conforming to the - // "log.file.name_resolved" semantic conventions. It represents the - // basename of the file, with symlinks resolved. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'uuid.log' - LogFileNameResolvedKey = attribute.Key("log.file.name_resolved") - - // LogFilePathKey is the attribute Key conforming to the "log.file.path" - // semantic conventions. It represents the full path to the file. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/var/log/mysql/audit.log' - LogFilePathKey = attribute.Key("log.file.path") - - // LogFilePathResolvedKey is the attribute Key conforming to the - // "log.file.path_resolved" semantic conventions. It represents the full - // path to the file, with symlinks resolved. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/var/lib/docker/uuid.log' - LogFilePathResolvedKey = attribute.Key("log.file.path_resolved") -) - -// LogFileName returns an attribute KeyValue conforming to the -// "log.file.name" semantic conventions. It represents the basename of the -// file. -func LogFileName(val string) attribute.KeyValue { - return LogFileNameKey.String(val) -} - -// LogFileNameResolved returns an attribute KeyValue conforming to the -// "log.file.name_resolved" semantic conventions. It represents the basename of -// the file, with symlinks resolved. -func LogFileNameResolved(val string) attribute.KeyValue { - return LogFileNameResolvedKey.String(val) -} - -// LogFilePath returns an attribute KeyValue conforming to the -// "log.file.path" semantic conventions. It represents the full path to the -// file. -func LogFilePath(val string) attribute.KeyValue { - return LogFilePathKey.String(val) -} - -// LogFilePathResolved returns an attribute KeyValue conforming to the -// "log.file.path_resolved" semantic conventions. It represents the full path -// to the file, with symlinks resolved. -func LogFilePathResolved(val string) attribute.KeyValue { - return LogFilePathResolvedKey.String(val) -} - -// Describes Database attributes -const ( - // PoolNameKey is the attribute Key conforming to the "pool.name" semantic - // conventions. It represents the name of the connection pool; unique - // within the instrumented application. In case the connection pool - // implementation doesn't provide a name, then the - // [db.connection_string](/docs/database/database-spans.md#connection-level-attributes) - // should be used - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'myDataSource' - PoolNameKey = attribute.Key("pool.name") - - // StateKey is the attribute Key conforming to the "state" semantic - // conventions. It represents the state of a connection in the pool - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - // Examples: 'idle' - StateKey = attribute.Key("state") -) - -var ( - // idle - StateIdle = StateKey.String("idle") - // used - StateUsed = StateKey.String("used") -) - -// PoolName returns an attribute KeyValue conforming to the "pool.name" -// semantic conventions. It represents the name of the connection pool; unique -// within the instrumented application. In case the connection pool -// implementation doesn't provide a name, then the -// [db.connection_string](/docs/database/database-spans.md#connection-level-attributes) -// should be used -func PoolName(val string) attribute.KeyValue { - return PoolNameKey.String(val) -} - -// ASP.NET Core attributes -const ( - // AspnetcoreDiagnosticsHandlerTypeKey is the attribute Key conforming to - // the "aspnetcore.diagnostics.handler.type" semantic conventions. It - // represents the full type name of the - // [`IExceptionHandler`](https://learn.microsoft.com/dotnet/api/microsoft.aspnetcore.diagnostics.iexceptionhandler) - // implementation that handled the exception. - // - // Type: string - // RequirementLevel: ConditionallyRequired (if and only if the exception - // was handled by this handler.) - // Stability: experimental - // Examples: 'Contoso.MyHandler' - AspnetcoreDiagnosticsHandlerTypeKey = attribute.Key("aspnetcore.diagnostics.handler.type") - - // AspnetcoreRateLimitingPolicyKey is the attribute Key conforming to the - // "aspnetcore.rate_limiting.policy" semantic conventions. It represents - // the rate limiting policy name. - // - // Type: string - // RequirementLevel: ConditionallyRequired (if the matched endpoint for the - // request had a rate-limiting policy.) - // Stability: experimental - // Examples: 'fixed', 'sliding', 'token' - AspnetcoreRateLimitingPolicyKey = attribute.Key("aspnetcore.rate_limiting.policy") - - // AspnetcoreRateLimitingResultKey is the attribute Key conforming to the - // "aspnetcore.rate_limiting.result" semantic conventions. It represents - // the rate-limiting result, shows whether the lease was acquired or - // contains a rejection reason - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - // Examples: 'acquired', 'request_canceled' - AspnetcoreRateLimitingResultKey = attribute.Key("aspnetcore.rate_limiting.result") - - // AspnetcoreRequestIsUnhandledKey is the attribute Key conforming to the - // "aspnetcore.request.is_unhandled" semantic conventions. It represents - // the flag indicating if request was handled by the application pipeline. - // - // Type: boolean - // RequirementLevel: ConditionallyRequired (if and only if the request was - // not handled.) - // Stability: experimental - // Examples: True - AspnetcoreRequestIsUnhandledKey = attribute.Key("aspnetcore.request.is_unhandled") - - // AspnetcoreRoutingIsFallbackKey is the attribute Key conforming to the - // "aspnetcore.routing.is_fallback" semantic conventions. It represents a - // value that indicates whether the matched route is a fallback route. - // - // Type: boolean - // RequirementLevel: ConditionallyRequired (If and only if a route was - // successfully matched.) - // Stability: experimental - // Examples: True - AspnetcoreRoutingIsFallbackKey = attribute.Key("aspnetcore.routing.is_fallback") -) - -var ( - // Lease was acquired - AspnetcoreRateLimitingResultAcquired = AspnetcoreRateLimitingResultKey.String("acquired") - // Lease request was rejected by the endpoint limiter - AspnetcoreRateLimitingResultEndpointLimiter = AspnetcoreRateLimitingResultKey.String("endpoint_limiter") - // Lease request was rejected by the global limiter - AspnetcoreRateLimitingResultGlobalLimiter = AspnetcoreRateLimitingResultKey.String("global_limiter") - // Lease request was canceled - AspnetcoreRateLimitingResultRequestCanceled = AspnetcoreRateLimitingResultKey.String("request_canceled") -) - -// AspnetcoreDiagnosticsHandlerType returns an attribute KeyValue conforming -// to the "aspnetcore.diagnostics.handler.type" semantic conventions. It -// represents the full type name of the -// [`IExceptionHandler`](https://learn.microsoft.com/dotnet/api/microsoft.aspnetcore.diagnostics.iexceptionhandler) -// implementation that handled the exception. -func AspnetcoreDiagnosticsHandlerType(val string) attribute.KeyValue { - return AspnetcoreDiagnosticsHandlerTypeKey.String(val) -} - -// AspnetcoreRateLimitingPolicy returns an attribute KeyValue conforming to -// the "aspnetcore.rate_limiting.policy" semantic conventions. It represents -// the rate limiting policy name. -func AspnetcoreRateLimitingPolicy(val string) attribute.KeyValue { - return AspnetcoreRateLimitingPolicyKey.String(val) -} - -// AspnetcoreRequestIsUnhandled returns an attribute KeyValue conforming to -// the "aspnetcore.request.is_unhandled" semantic conventions. It represents -// the flag indicating if request was handled by the application pipeline. -func AspnetcoreRequestIsUnhandled(val bool) attribute.KeyValue { - return AspnetcoreRequestIsUnhandledKey.Bool(val) -} - -// AspnetcoreRoutingIsFallback returns an attribute KeyValue conforming to -// the "aspnetcore.routing.is_fallback" semantic conventions. It represents a -// value that indicates whether the matched route is a fallback route. -func AspnetcoreRoutingIsFallback(val bool) attribute.KeyValue { - return AspnetcoreRoutingIsFallbackKey.Bool(val) -} - -// SignalR attributes -const ( - // SignalrConnectionStatusKey is the attribute Key conforming to the - // "signalr.connection.status" semantic conventions. It represents the - // signalR HTTP connection closure status. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'app_shutdown', 'timeout' - SignalrConnectionStatusKey = attribute.Key("signalr.connection.status") - - // SignalrTransportKey is the attribute Key conforming to the - // "signalr.transport" semantic conventions. It represents the [SignalR - // transport - // type](https://github.com/dotnet/aspnetcore/blob/main/src/SignalR/docs/specs/TransportProtocols.md) - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'web_sockets', 'long_polling' - SignalrTransportKey = attribute.Key("signalr.transport") -) - -var ( - // The connection was closed normally - SignalrConnectionStatusNormalClosure = SignalrConnectionStatusKey.String("normal_closure") - // The connection was closed due to a timeout - SignalrConnectionStatusTimeout = SignalrConnectionStatusKey.String("timeout") - // The connection was closed because the app is shutting down - SignalrConnectionStatusAppShutdown = SignalrConnectionStatusKey.String("app_shutdown") -) - -var ( - // ServerSentEvents protocol - SignalrTransportServerSentEvents = SignalrTransportKey.String("server_sent_events") - // LongPolling protocol - SignalrTransportLongPolling = SignalrTransportKey.String("long_polling") - // WebSockets protocol - SignalrTransportWebSockets = SignalrTransportKey.String("web_sockets") -) - -// Describes JVM buffer metric attributes. -const ( - // JvmBufferPoolNameKey is the attribute Key conforming to the - // "jvm.buffer.pool.name" semantic conventions. It represents the name of - // the buffer pool. - // - // Type: string - // RequirementLevel: Recommended - // Stability: experimental - // Examples: 'mapped', 'direct' - // Note: Pool names are generally obtained via - // [BufferPoolMXBean#getName()](https://docs.oracle.com/en/java/javase/11/docs/api/java.management/java/lang/management/BufferPoolMXBean.html#getName()). - JvmBufferPoolNameKey = attribute.Key("jvm.buffer.pool.name") -) - -// JvmBufferPoolName returns an attribute KeyValue conforming to the -// "jvm.buffer.pool.name" semantic conventions. It represents the name of the -// buffer pool. -func JvmBufferPoolName(val string) attribute.KeyValue { - return JvmBufferPoolNameKey.String(val) -} - -// Describes JVM memory metric attributes. -const ( - // JvmMemoryPoolNameKey is the attribute Key conforming to the - // "jvm.memory.pool.name" semantic conventions. It represents the name of - // the memory pool. - // - // Type: string - // RequirementLevel: Recommended - // Stability: stable - // Examples: 'G1 Old Gen', 'G1 Eden space', 'G1 Survivor Space' - // Note: Pool names are generally obtained via - // [MemoryPoolMXBean#getName()](https://docs.oracle.com/en/java/javase/11/docs/api/java.management/java/lang/management/MemoryPoolMXBean.html#getName()). - JvmMemoryPoolNameKey = attribute.Key("jvm.memory.pool.name") - - // JvmMemoryTypeKey is the attribute Key conforming to the - // "jvm.memory.type" semantic conventions. It represents the type of - // memory. - // - // Type: Enum - // RequirementLevel: Recommended - // Stability: stable - // Examples: 'heap', 'non_heap' - JvmMemoryTypeKey = attribute.Key("jvm.memory.type") -) - -var ( - // Heap memory - JvmMemoryTypeHeap = JvmMemoryTypeKey.String("heap") - // Non-heap memory - JvmMemoryTypeNonHeap = JvmMemoryTypeKey.String("non_heap") -) - -// JvmMemoryPoolName returns an attribute KeyValue conforming to the -// "jvm.memory.pool.name" semantic conventions. It represents the name of the -// memory pool. -func JvmMemoryPoolName(val string) attribute.KeyValue { - return JvmMemoryPoolNameKey.String(val) -} - -// Describes System metric attributes -const ( - // SystemDeviceKey is the attribute Key conforming to the "system.device" - // semantic conventions. It represents the device identifier - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '(identifier)' - SystemDeviceKey = attribute.Key("system.device") -) - -// SystemDevice returns an attribute KeyValue conforming to the -// "system.device" semantic conventions. It represents the device identifier -func SystemDevice(val string) attribute.KeyValue { - return SystemDeviceKey.String(val) -} - -// Describes System CPU metric attributes -const ( - // SystemCPULogicalNumberKey is the attribute Key conforming to the - // "system.cpu.logical_number" semantic conventions. It represents the - // logical CPU number [0..n-1] - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1 - SystemCPULogicalNumberKey = attribute.Key("system.cpu.logical_number") - - // SystemCPUStateKey is the attribute Key conforming to the - // "system.cpu.state" semantic conventions. It represents the state of the - // CPU - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'idle', 'interrupt' - SystemCPUStateKey = attribute.Key("system.cpu.state") -) - -var ( - // user - SystemCPUStateUser = SystemCPUStateKey.String("user") - // system - SystemCPUStateSystem = SystemCPUStateKey.String("system") - // nice - SystemCPUStateNice = SystemCPUStateKey.String("nice") - // idle - SystemCPUStateIdle = SystemCPUStateKey.String("idle") - // iowait - SystemCPUStateIowait = SystemCPUStateKey.String("iowait") - // interrupt - SystemCPUStateInterrupt = SystemCPUStateKey.String("interrupt") - // steal - SystemCPUStateSteal = SystemCPUStateKey.String("steal") -) - -// SystemCPULogicalNumber returns an attribute KeyValue conforming to the -// "system.cpu.logical_number" semantic conventions. It represents the logical -// CPU number [0..n-1] -func SystemCPULogicalNumber(val int) attribute.KeyValue { - return SystemCPULogicalNumberKey.Int(val) -} - -// Describes System Memory metric attributes -const ( - // SystemMemoryStateKey is the attribute Key conforming to the - // "system.memory.state" semantic conventions. It represents the memory - // state - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'free', 'cached' - SystemMemoryStateKey = attribute.Key("system.memory.state") -) - -var ( - // used - SystemMemoryStateUsed = SystemMemoryStateKey.String("used") - // free - SystemMemoryStateFree = SystemMemoryStateKey.String("free") - // shared - SystemMemoryStateShared = SystemMemoryStateKey.String("shared") - // buffers - SystemMemoryStateBuffers = SystemMemoryStateKey.String("buffers") - // cached - SystemMemoryStateCached = SystemMemoryStateKey.String("cached") -) - -// Describes System Memory Paging metric attributes -const ( - // SystemPagingDirectionKey is the attribute Key conforming to the - // "system.paging.direction" semantic conventions. It represents the paging - // access direction - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'in' - SystemPagingDirectionKey = attribute.Key("system.paging.direction") - - // SystemPagingStateKey is the attribute Key conforming to the - // "system.paging.state" semantic conventions. It represents the memory - // paging state - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'free' - SystemPagingStateKey = attribute.Key("system.paging.state") - - // SystemPagingTypeKey is the attribute Key conforming to the - // "system.paging.type" semantic conventions. It represents the memory - // paging type - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'minor' - SystemPagingTypeKey = attribute.Key("system.paging.type") -) - -var ( - // in - SystemPagingDirectionIn = SystemPagingDirectionKey.String("in") - // out - SystemPagingDirectionOut = SystemPagingDirectionKey.String("out") -) - -var ( - // used - SystemPagingStateUsed = SystemPagingStateKey.String("used") - // free - SystemPagingStateFree = SystemPagingStateKey.String("free") -) - -var ( - // major - SystemPagingTypeMajor = SystemPagingTypeKey.String("major") - // minor - SystemPagingTypeMinor = SystemPagingTypeKey.String("minor") -) - -// Describes Filesystem metric attributes -const ( - // SystemFilesystemModeKey is the attribute Key conforming to the - // "system.filesystem.mode" semantic conventions. It represents the - // filesystem mode - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'rw, ro' - SystemFilesystemModeKey = attribute.Key("system.filesystem.mode") - - // SystemFilesystemMountpointKey is the attribute Key conforming to the - // "system.filesystem.mountpoint" semantic conventions. It represents the - // filesystem mount path - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/mnt/data' - SystemFilesystemMountpointKey = attribute.Key("system.filesystem.mountpoint") - - // SystemFilesystemStateKey is the attribute Key conforming to the - // "system.filesystem.state" semantic conventions. It represents the - // filesystem state - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'used' - SystemFilesystemStateKey = attribute.Key("system.filesystem.state") - - // SystemFilesystemTypeKey is the attribute Key conforming to the - // "system.filesystem.type" semantic conventions. It represents the - // filesystem type - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'ext4' - SystemFilesystemTypeKey = attribute.Key("system.filesystem.type") -) - -var ( - // used - SystemFilesystemStateUsed = SystemFilesystemStateKey.String("used") - // free - SystemFilesystemStateFree = SystemFilesystemStateKey.String("free") - // reserved - SystemFilesystemStateReserved = SystemFilesystemStateKey.String("reserved") -) - -var ( - // fat32 - SystemFilesystemTypeFat32 = SystemFilesystemTypeKey.String("fat32") - // exfat - SystemFilesystemTypeExfat = SystemFilesystemTypeKey.String("exfat") - // ntfs - SystemFilesystemTypeNtfs = SystemFilesystemTypeKey.String("ntfs") - // refs - SystemFilesystemTypeRefs = SystemFilesystemTypeKey.String("refs") - // hfsplus - SystemFilesystemTypeHfsplus = SystemFilesystemTypeKey.String("hfsplus") - // ext4 - SystemFilesystemTypeExt4 = SystemFilesystemTypeKey.String("ext4") -) - -// SystemFilesystemMode returns an attribute KeyValue conforming to the -// "system.filesystem.mode" semantic conventions. It represents the filesystem -// mode -func SystemFilesystemMode(val string) attribute.KeyValue { - return SystemFilesystemModeKey.String(val) -} - -// SystemFilesystemMountpoint returns an attribute KeyValue conforming to -// the "system.filesystem.mountpoint" semantic conventions. It represents the -// filesystem mount path -func SystemFilesystemMountpoint(val string) attribute.KeyValue { - return SystemFilesystemMountpointKey.String(val) -} - -// Describes Network metric attributes -const ( - // SystemNetworkStateKey is the attribute Key conforming to the - // "system.network.state" semantic conventions. It represents a stateless - // protocol MUST NOT set this attribute - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'close_wait' - SystemNetworkStateKey = attribute.Key("system.network.state") -) - -var ( - // close - SystemNetworkStateClose = SystemNetworkStateKey.String("close") - // close_wait - SystemNetworkStateCloseWait = SystemNetworkStateKey.String("close_wait") - // closing - SystemNetworkStateClosing = SystemNetworkStateKey.String("closing") - // delete - SystemNetworkStateDelete = SystemNetworkStateKey.String("delete") - // established - SystemNetworkStateEstablished = SystemNetworkStateKey.String("established") - // fin_wait_1 - SystemNetworkStateFinWait1 = SystemNetworkStateKey.String("fin_wait_1") - // fin_wait_2 - SystemNetworkStateFinWait2 = SystemNetworkStateKey.String("fin_wait_2") - // last_ack - SystemNetworkStateLastAck = SystemNetworkStateKey.String("last_ack") - // listen - SystemNetworkStateListen = SystemNetworkStateKey.String("listen") - // syn_recv - SystemNetworkStateSynRecv = SystemNetworkStateKey.String("syn_recv") - // syn_sent - SystemNetworkStateSynSent = SystemNetworkStateKey.String("syn_sent") - // time_wait - SystemNetworkStateTimeWait = SystemNetworkStateKey.String("time_wait") -) - -// Describes System Process metric attributes -const ( - // SystemProcessesStatusKey is the attribute Key conforming to the - // "system.processes.status" semantic conventions. It represents the - // process state, e.g., [Linux Process State - // Codes](https://man7.org/linux/man-pages/man1/ps.1.html#PROCESS_STATE_CODES) - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'running' - SystemProcessesStatusKey = attribute.Key("system.processes.status") -) - -var ( - // running - SystemProcessesStatusRunning = SystemProcessesStatusKey.String("running") - // sleeping - SystemProcessesStatusSleeping = SystemProcessesStatusKey.String("sleeping") - // stopped - SystemProcessesStatusStopped = SystemProcessesStatusKey.String("stopped") - // defunct - SystemProcessesStatusDefunct = SystemProcessesStatusKey.String("defunct") -) - -// These attributes may be used to describe the client in a connection-based -// network interaction where there is one side that initiates the connection -// (the client is the side that initiates the connection). This covers all TCP -// network interactions since TCP is connection-based and one side initiates -// the connection (an exception is made for peer-to-peer communication over TCP -// where the "user-facing" surface of the protocol / API doesn't expose a clear -// notion of client and server). This also covers UDP network interactions -// where one side initiates the interaction, e.g. QUIC (HTTP/3) and DNS. -const ( - // ClientAddressKey is the attribute Key conforming to the "client.address" - // semantic conventions. It represents the client address - domain name if - // available without reverse DNS lookup; otherwise, IP address or Unix - // domain socket name. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'client.example.com', '10.1.2.80', '/tmp/my.sock' - // Note: When observed from the server side, and when communicating through - // an intermediary, `client.address` SHOULD represent the client address - // behind any intermediaries, for example proxies, if it's available. - ClientAddressKey = attribute.Key("client.address") - - // ClientPortKey is the attribute Key conforming to the "client.port" - // semantic conventions. It represents the client port number. - // - // Type: int - // RequirementLevel: Optional - // Stability: stable - // Examples: 65123 - // Note: When observed from the server side, and when communicating through - // an intermediary, `client.port` SHOULD represent the client port behind - // any intermediaries, for example proxies, if it's available. - ClientPortKey = attribute.Key("client.port") -) - -// ClientAddress returns an attribute KeyValue conforming to the -// "client.address" semantic conventions. It represents the client address - -// domain name if available without reverse DNS lookup; otherwise, IP address -// or Unix domain socket name. -func ClientAddress(val string) attribute.KeyValue { - return ClientAddressKey.String(val) -} - -// ClientPort returns an attribute KeyValue conforming to the "client.port" -// semantic conventions. It represents the client port number. -func ClientPort(val int) attribute.KeyValue { - return ClientPortKey.Int(val) -} - -// The attributes used to describe telemetry in the context of databases. -const ( - // DBCassandraConsistencyLevelKey is the attribute Key conforming to the - // "db.cassandra.consistency_level" semantic conventions. It represents the - // consistency level of the query. Based on consistency values from - // [CQL](https://docs.datastax.com/en/cassandra-oss/3.0/cassandra/dml/dmlConfigConsistency.html). - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - DBCassandraConsistencyLevelKey = attribute.Key("db.cassandra.consistency_level") - - // DBCassandraCoordinatorDCKey is the attribute Key conforming to the - // "db.cassandra.coordinator.dc" semantic conventions. It represents the - // data center of the coordinating node for a query. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'us-west-2' - DBCassandraCoordinatorDCKey = attribute.Key("db.cassandra.coordinator.dc") - - // DBCassandraCoordinatorIDKey is the attribute Key conforming to the - // "db.cassandra.coordinator.id" semantic conventions. It represents the ID - // of the coordinating node for a query. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'be13faa2-8574-4d71-926d-27f16cf8a7af' - DBCassandraCoordinatorIDKey = attribute.Key("db.cassandra.coordinator.id") - - // DBCassandraIdempotenceKey is the attribute Key conforming to the - // "db.cassandra.idempotence" semantic conventions. It represents the - // whether or not the query is idempotent. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - DBCassandraIdempotenceKey = attribute.Key("db.cassandra.idempotence") - - // DBCassandraPageSizeKey is the attribute Key conforming to the - // "db.cassandra.page_size" semantic conventions. It represents the fetch - // size used for paging, i.e. how many rows will be returned at once. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 5000 - DBCassandraPageSizeKey = attribute.Key("db.cassandra.page_size") - - // DBCassandraSpeculativeExecutionCountKey is the attribute Key conforming - // to the "db.cassandra.speculative_execution_count" semantic conventions. - // It represents the number of times a query was speculatively executed. - // Not set or `0` if the query was not executed speculatively. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 0, 2 - DBCassandraSpeculativeExecutionCountKey = attribute.Key("db.cassandra.speculative_execution_count") - - // DBCassandraTableKey is the attribute Key conforming to the - // "db.cassandra.table" semantic conventions. It represents the name of the - // primary Cassandra table that the operation is acting upon, including the - // keyspace name (if applicable). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'mytable' - // Note: This mirrors the db.sql.table attribute but references cassandra - // rather than sql. It is not recommended to attempt any client-side - // parsing of `db.statement` just to get this property, but it should be - // set if it is provided by the library being instrumented. If the - // operation is acting upon an anonymous table, or more than one table, - // this value MUST NOT be set. - DBCassandraTableKey = attribute.Key("db.cassandra.table") - - // DBConnectionStringKey is the attribute Key conforming to the - // "db.connection_string" semantic conventions. It represents the - // connection string used to connect to the database. It is recommended to - // remove embedded credentials. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Server=(localdb)\\v11.0;Integrated Security=true;' - DBConnectionStringKey = attribute.Key("db.connection_string") - - // DBCosmosDBClientIDKey is the attribute Key conforming to the - // "db.cosmosdb.client_id" semantic conventions. It represents the unique - // Cosmos client instance id. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '3ba4827d-4422-483f-b59f-85b74211c11d' - DBCosmosDBClientIDKey = attribute.Key("db.cosmosdb.client_id") - - // DBCosmosDBConnectionModeKey is the attribute Key conforming to the - // "db.cosmosdb.connection_mode" semantic conventions. It represents the - // cosmos client connection mode. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - DBCosmosDBConnectionModeKey = attribute.Key("db.cosmosdb.connection_mode") - - // DBCosmosDBContainerKey is the attribute Key conforming to the - // "db.cosmosdb.container" semantic conventions. It represents the cosmos - // DB container name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'anystring' - DBCosmosDBContainerKey = attribute.Key("db.cosmosdb.container") - - // DBCosmosDBOperationTypeKey is the attribute Key conforming to the - // "db.cosmosdb.operation_type" semantic conventions. It represents the - // cosmosDB Operation Type. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - DBCosmosDBOperationTypeKey = attribute.Key("db.cosmosdb.operation_type") - - // DBCosmosDBRequestChargeKey is the attribute Key conforming to the - // "db.cosmosdb.request_charge" semantic conventions. It represents the rU - // consumed for that operation - // - // Type: double - // RequirementLevel: Optional - // Stability: experimental - // Examples: 46.18, 1.0 - DBCosmosDBRequestChargeKey = attribute.Key("db.cosmosdb.request_charge") - - // DBCosmosDBRequestContentLengthKey is the attribute Key conforming to the - // "db.cosmosdb.request_content_length" semantic conventions. It represents - // the request payload size in bytes - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - DBCosmosDBRequestContentLengthKey = attribute.Key("db.cosmosdb.request_content_length") - - // DBCosmosDBStatusCodeKey is the attribute Key conforming to the - // "db.cosmosdb.status_code" semantic conventions. It represents the cosmos - // DB status code. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 200, 201 - DBCosmosDBStatusCodeKey = attribute.Key("db.cosmosdb.status_code") - - // DBCosmosDBSubStatusCodeKey is the attribute Key conforming to the - // "db.cosmosdb.sub_status_code" semantic conventions. It represents the - // cosmos DB sub status code. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1000, 1002 - DBCosmosDBSubStatusCodeKey = attribute.Key("db.cosmosdb.sub_status_code") - - // DBElasticsearchClusterNameKey is the attribute Key conforming to the - // "db.elasticsearch.cluster.name" semantic conventions. It represents the - // represents the identifier of an Elasticsearch cluster. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'e9106fc68e3044f0b1475b04bf4ffd5f' - DBElasticsearchClusterNameKey = attribute.Key("db.elasticsearch.cluster.name") - - // DBElasticsearchNodeNameKey is the attribute Key conforming to the - // "db.elasticsearch.node.name" semantic conventions. It represents the - // represents the human-readable identifier of the node/instance to which a - // request was routed. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'instance-0000000001' - DBElasticsearchNodeNameKey = attribute.Key("db.elasticsearch.node.name") - - // DBInstanceIDKey is the attribute Key conforming to the "db.instance.id" - // semantic conventions. It represents an identifier (address, unique name, - // or any other identifier) of the database instance that is executing - // queries or mutations on the current connection. This is useful in cases - // where the database is running in a clustered environment and the - // instrumentation is able to record the node executing the query. The - // client may obtain this value in databases like MySQL using queries like - // `select @@hostname`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'mysql-e26b99z.example.com' - DBInstanceIDKey = attribute.Key("db.instance.id") - - // DBJDBCDriverClassnameKey is the attribute Key conforming to the - // "db.jdbc.driver_classname" semantic conventions. It represents the - // fully-qualified class name of the [Java Database Connectivity - // (JDBC)](https://docs.oracle.com/javase/8/docs/technotes/guides/jdbc/) - // driver used to connect. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'org.postgresql.Driver', - // 'com.microsoft.sqlserver.jdbc.SQLServerDriver' - DBJDBCDriverClassnameKey = attribute.Key("db.jdbc.driver_classname") - - // DBMongoDBCollectionKey is the attribute Key conforming to the - // "db.mongodb.collection" semantic conventions. It represents the MongoDB - // collection being accessed within the database stated in `db.name`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'customers', 'products' - DBMongoDBCollectionKey = attribute.Key("db.mongodb.collection") - - // DBMSSQLInstanceNameKey is the attribute Key conforming to the - // "db.mssql.instance_name" semantic conventions. It represents the - // Microsoft SQL Server [instance - // name](https://docs.microsoft.com/sql/connect/jdbc/building-the-connection-url?view=sql-server-ver15) - // connecting to. This name is used to determine the port of a named - // instance. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MSSQLSERVER' - // Note: If setting a `db.mssql.instance_name`, `server.port` is no longer - // required (but still recommended if non-standard). - DBMSSQLInstanceNameKey = attribute.Key("db.mssql.instance_name") - - // DBNameKey is the attribute Key conforming to the "db.name" semantic - // conventions. It represents the this attribute is used to report the name - // of the database being accessed. For commands that switch the database, - // this should be set to the target database (even if the command fails). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'customers', 'main' - // Note: In some SQL databases, the database name to be used is called - // "schema name". In case there are multiple layers that could be - // considered for database name (e.g. Oracle instance name and schema - // name), the database name to be used is the more specific layer (e.g. - // Oracle schema name). - DBNameKey = attribute.Key("db.name") - - // DBOperationKey is the attribute Key conforming to the "db.operation" - // semantic conventions. It represents the name of the operation being - // executed, e.g. the [MongoDB command - // name](https://docs.mongodb.com/manual/reference/command/#database-operations) - // such as `findAndModify`, or the SQL keyword. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'findAndModify', 'HMSET', 'SELECT' - // Note: When setting this to an SQL keyword, it is not recommended to - // attempt any client-side parsing of `db.statement` just to get this - // property, but it should be set if the operation name is provided by the - // library being instrumented. If the SQL statement has an ambiguous - // operation, or performs more than one operation, this value may be - // omitted. - DBOperationKey = attribute.Key("db.operation") - - // DBRedisDBIndexKey is the attribute Key conforming to the - // "db.redis.database_index" semantic conventions. It represents the index - // of the database being accessed as used in the [`SELECT` - // command](https://redis.io/commands/select), provided as an integer. To - // be used instead of the generic `db.name` attribute. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 0, 1, 15 - DBRedisDBIndexKey = attribute.Key("db.redis.database_index") - - // DBSQLTableKey is the attribute Key conforming to the "db.sql.table" - // semantic conventions. It represents the name of the primary table that - // the operation is acting upon, including the database name (if - // applicable). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'public.users', 'customers' - // Note: It is not recommended to attempt any client-side parsing of - // `db.statement` just to get this property, but it should be set if it is - // provided by the library being instrumented. If the operation is acting - // upon an anonymous table, or more than one table, this value MUST NOT be - // set. - DBSQLTableKey = attribute.Key("db.sql.table") - - // DBStatementKey is the attribute Key conforming to the "db.statement" - // semantic conventions. It represents the database statement being - // executed. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'SELECT * FROM wuser_table', 'SET mykey "WuValue"' - DBStatementKey = attribute.Key("db.statement") - - // DBSystemKey is the attribute Key conforming to the "db.system" semantic - // conventions. It represents an identifier for the database management - // system (DBMS) product being used. See below for a list of well-known - // identifiers. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - DBSystemKey = attribute.Key("db.system") - - // DBUserKey is the attribute Key conforming to the "db.user" semantic - // conventions. It represents the username for accessing the database. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'readonly_user', 'reporting_user' - DBUserKey = attribute.Key("db.user") -) - -var ( - // all - DBCassandraConsistencyLevelAll = DBCassandraConsistencyLevelKey.String("all") - // each_quorum - DBCassandraConsistencyLevelEachQuorum = DBCassandraConsistencyLevelKey.String("each_quorum") - // quorum - DBCassandraConsistencyLevelQuorum = DBCassandraConsistencyLevelKey.String("quorum") - // local_quorum - DBCassandraConsistencyLevelLocalQuorum = DBCassandraConsistencyLevelKey.String("local_quorum") - // one - DBCassandraConsistencyLevelOne = DBCassandraConsistencyLevelKey.String("one") - // two - DBCassandraConsistencyLevelTwo = DBCassandraConsistencyLevelKey.String("two") - // three - DBCassandraConsistencyLevelThree = DBCassandraConsistencyLevelKey.String("three") - // local_one - DBCassandraConsistencyLevelLocalOne = DBCassandraConsistencyLevelKey.String("local_one") - // any - DBCassandraConsistencyLevelAny = DBCassandraConsistencyLevelKey.String("any") - // serial - DBCassandraConsistencyLevelSerial = DBCassandraConsistencyLevelKey.String("serial") - // local_serial - DBCassandraConsistencyLevelLocalSerial = DBCassandraConsistencyLevelKey.String("local_serial") -) - -var ( - // Gateway (HTTP) connections mode - DBCosmosDBConnectionModeGateway = DBCosmosDBConnectionModeKey.String("gateway") - // Direct connection - DBCosmosDBConnectionModeDirect = DBCosmosDBConnectionModeKey.String("direct") -) - -var ( - // invalid - DBCosmosDBOperationTypeInvalid = DBCosmosDBOperationTypeKey.String("Invalid") - // create - DBCosmosDBOperationTypeCreate = DBCosmosDBOperationTypeKey.String("Create") - // patch - DBCosmosDBOperationTypePatch = DBCosmosDBOperationTypeKey.String("Patch") - // read - DBCosmosDBOperationTypeRead = DBCosmosDBOperationTypeKey.String("Read") - // read_feed - DBCosmosDBOperationTypeReadFeed = DBCosmosDBOperationTypeKey.String("ReadFeed") - // delete - DBCosmosDBOperationTypeDelete = DBCosmosDBOperationTypeKey.String("Delete") - // replace - DBCosmosDBOperationTypeReplace = DBCosmosDBOperationTypeKey.String("Replace") - // execute - DBCosmosDBOperationTypeExecute = DBCosmosDBOperationTypeKey.String("Execute") - // query - DBCosmosDBOperationTypeQuery = DBCosmosDBOperationTypeKey.String("Query") - // head - DBCosmosDBOperationTypeHead = DBCosmosDBOperationTypeKey.String("Head") - // head_feed - DBCosmosDBOperationTypeHeadFeed = DBCosmosDBOperationTypeKey.String("HeadFeed") - // upsert - DBCosmosDBOperationTypeUpsert = DBCosmosDBOperationTypeKey.String("Upsert") - // batch - DBCosmosDBOperationTypeBatch = DBCosmosDBOperationTypeKey.String("Batch") - // query_plan - DBCosmosDBOperationTypeQueryPlan = DBCosmosDBOperationTypeKey.String("QueryPlan") - // execute_javascript - DBCosmosDBOperationTypeExecuteJavascript = DBCosmosDBOperationTypeKey.String("ExecuteJavaScript") -) - -var ( - // Some other SQL database. Fallback only. See notes - DBSystemOtherSQL = DBSystemKey.String("other_sql") - // Microsoft SQL Server - DBSystemMSSQL = DBSystemKey.String("mssql") - // Microsoft SQL Server Compact - DBSystemMssqlcompact = DBSystemKey.String("mssqlcompact") - // MySQL - DBSystemMySQL = DBSystemKey.String("mysql") - // Oracle Database - DBSystemOracle = DBSystemKey.String("oracle") - // IBM DB2 - DBSystemDB2 = DBSystemKey.String("db2") - // PostgreSQL - DBSystemPostgreSQL = DBSystemKey.String("postgresql") - // Amazon Redshift - DBSystemRedshift = DBSystemKey.String("redshift") - // Apache Hive - DBSystemHive = DBSystemKey.String("hive") - // Cloudscape - DBSystemCloudscape = DBSystemKey.String("cloudscape") - // HyperSQL DataBase - DBSystemHSQLDB = DBSystemKey.String("hsqldb") - // Progress Database - DBSystemProgress = DBSystemKey.String("progress") - // SAP MaxDB - DBSystemMaxDB = DBSystemKey.String("maxdb") - // SAP HANA - DBSystemHanaDB = DBSystemKey.String("hanadb") - // Ingres - DBSystemIngres = DBSystemKey.String("ingres") - // FirstSQL - DBSystemFirstSQL = DBSystemKey.String("firstsql") - // EnterpriseDB - DBSystemEDB = DBSystemKey.String("edb") - // InterSystems Caché - DBSystemCache = DBSystemKey.String("cache") - // Adabas (Adaptable Database System) - DBSystemAdabas = DBSystemKey.String("adabas") - // Firebird - DBSystemFirebird = DBSystemKey.String("firebird") - // Apache Derby - DBSystemDerby = DBSystemKey.String("derby") - // FileMaker - DBSystemFilemaker = DBSystemKey.String("filemaker") - // Informix - DBSystemInformix = DBSystemKey.String("informix") - // InstantDB - DBSystemInstantDB = DBSystemKey.String("instantdb") - // InterBase - DBSystemInterbase = DBSystemKey.String("interbase") - // MariaDB - DBSystemMariaDB = DBSystemKey.String("mariadb") - // Netezza - DBSystemNetezza = DBSystemKey.String("netezza") - // Pervasive PSQL - DBSystemPervasive = DBSystemKey.String("pervasive") - // PointBase - DBSystemPointbase = DBSystemKey.String("pointbase") - // SQLite - DBSystemSqlite = DBSystemKey.String("sqlite") - // Sybase - DBSystemSybase = DBSystemKey.String("sybase") - // Teradata - DBSystemTeradata = DBSystemKey.String("teradata") - // Vertica - DBSystemVertica = DBSystemKey.String("vertica") - // H2 - DBSystemH2 = DBSystemKey.String("h2") - // ColdFusion IMQ - DBSystemColdfusion = DBSystemKey.String("coldfusion") - // Apache Cassandra - DBSystemCassandra = DBSystemKey.String("cassandra") - // Apache HBase - DBSystemHBase = DBSystemKey.String("hbase") - // MongoDB - DBSystemMongoDB = DBSystemKey.String("mongodb") - // Redis - DBSystemRedis = DBSystemKey.String("redis") - // Couchbase - DBSystemCouchbase = DBSystemKey.String("couchbase") - // CouchDB - DBSystemCouchDB = DBSystemKey.String("couchdb") - // Microsoft Azure Cosmos DB - DBSystemCosmosDB = DBSystemKey.String("cosmosdb") - // Amazon DynamoDB - DBSystemDynamoDB = DBSystemKey.String("dynamodb") - // Neo4j - DBSystemNeo4j = DBSystemKey.String("neo4j") - // Apache Geode - DBSystemGeode = DBSystemKey.String("geode") - // Elasticsearch - DBSystemElasticsearch = DBSystemKey.String("elasticsearch") - // Memcached - DBSystemMemcached = DBSystemKey.String("memcached") - // CockroachDB - DBSystemCockroachdb = DBSystemKey.String("cockroachdb") - // OpenSearch - DBSystemOpensearch = DBSystemKey.String("opensearch") - // ClickHouse - DBSystemClickhouse = DBSystemKey.String("clickhouse") - // Cloud Spanner - DBSystemSpanner = DBSystemKey.String("spanner") - // Trino - DBSystemTrino = DBSystemKey.String("trino") -) - -// DBCassandraCoordinatorDC returns an attribute KeyValue conforming to the -// "db.cassandra.coordinator.dc" semantic conventions. It represents the data -// center of the coordinating node for a query. -func DBCassandraCoordinatorDC(val string) attribute.KeyValue { - return DBCassandraCoordinatorDCKey.String(val) -} - -// DBCassandraCoordinatorID returns an attribute KeyValue conforming to the -// "db.cassandra.coordinator.id" semantic conventions. It represents the ID of -// the coordinating node for a query. -func DBCassandraCoordinatorID(val string) attribute.KeyValue { - return DBCassandraCoordinatorIDKey.String(val) -} - -// DBCassandraIdempotence returns an attribute KeyValue conforming to the -// "db.cassandra.idempotence" semantic conventions. It represents the whether -// or not the query is idempotent. -func DBCassandraIdempotence(val bool) attribute.KeyValue { - return DBCassandraIdempotenceKey.Bool(val) -} - -// DBCassandraPageSize returns an attribute KeyValue conforming to the -// "db.cassandra.page_size" semantic conventions. It represents the fetch size -// used for paging, i.e. how many rows will be returned at once. -func DBCassandraPageSize(val int) attribute.KeyValue { - return DBCassandraPageSizeKey.Int(val) -} - -// DBCassandraSpeculativeExecutionCount returns an attribute KeyValue -// conforming to the "db.cassandra.speculative_execution_count" semantic -// conventions. It represents the number of times a query was speculatively -// executed. Not set or `0` if the query was not executed speculatively. -func DBCassandraSpeculativeExecutionCount(val int) attribute.KeyValue { - return DBCassandraSpeculativeExecutionCountKey.Int(val) -} - -// DBCassandraTable returns an attribute KeyValue conforming to the -// "db.cassandra.table" semantic conventions. It represents the name of the -// primary Cassandra table that the operation is acting upon, including the -// keyspace name (if applicable). -func DBCassandraTable(val string) attribute.KeyValue { - return DBCassandraTableKey.String(val) -} - -// DBConnectionString returns an attribute KeyValue conforming to the -// "db.connection_string" semantic conventions. It represents the connection -// string used to connect to the database. It is recommended to remove embedded -// credentials. -func DBConnectionString(val string) attribute.KeyValue { - return DBConnectionStringKey.String(val) -} - -// DBCosmosDBClientID returns an attribute KeyValue conforming to the -// "db.cosmosdb.client_id" semantic conventions. It represents the unique -// Cosmos client instance id. -func DBCosmosDBClientID(val string) attribute.KeyValue { - return DBCosmosDBClientIDKey.String(val) -} - -// DBCosmosDBContainer returns an attribute KeyValue conforming to the -// "db.cosmosdb.container" semantic conventions. It represents the cosmos DB -// container name. -func DBCosmosDBContainer(val string) attribute.KeyValue { - return DBCosmosDBContainerKey.String(val) -} - -// DBCosmosDBRequestCharge returns an attribute KeyValue conforming to the -// "db.cosmosdb.request_charge" semantic conventions. It represents the rU -// consumed for that operation -func DBCosmosDBRequestCharge(val float64) attribute.KeyValue { - return DBCosmosDBRequestChargeKey.Float64(val) -} - -// DBCosmosDBRequestContentLength returns an attribute KeyValue conforming -// to the "db.cosmosdb.request_content_length" semantic conventions. It -// represents the request payload size in bytes -func DBCosmosDBRequestContentLength(val int) attribute.KeyValue { - return DBCosmosDBRequestContentLengthKey.Int(val) -} - -// DBCosmosDBStatusCode returns an attribute KeyValue conforming to the -// "db.cosmosdb.status_code" semantic conventions. It represents the cosmos DB -// status code. -func DBCosmosDBStatusCode(val int) attribute.KeyValue { - return DBCosmosDBStatusCodeKey.Int(val) -} - -// DBCosmosDBSubStatusCode returns an attribute KeyValue conforming to the -// "db.cosmosdb.sub_status_code" semantic conventions. It represents the cosmos -// DB sub status code. -func DBCosmosDBSubStatusCode(val int) attribute.KeyValue { - return DBCosmosDBSubStatusCodeKey.Int(val) -} - -// DBElasticsearchClusterName returns an attribute KeyValue conforming to -// the "db.elasticsearch.cluster.name" semantic conventions. It represents the -// represents the identifier of an Elasticsearch cluster. -func DBElasticsearchClusterName(val string) attribute.KeyValue { - return DBElasticsearchClusterNameKey.String(val) -} - -// DBElasticsearchNodeName returns an attribute KeyValue conforming to the -// "db.elasticsearch.node.name" semantic conventions. It represents the -// represents the human-readable identifier of the node/instance to which a -// request was routed. -func DBElasticsearchNodeName(val string) attribute.KeyValue { - return DBElasticsearchNodeNameKey.String(val) -} - -// DBInstanceID returns an attribute KeyValue conforming to the -// "db.instance.id" semantic conventions. It represents an identifier (address, -// unique name, or any other identifier) of the database instance that is -// executing queries or mutations on the current connection. This is useful in -// cases where the database is running in a clustered environment and the -// instrumentation is able to record the node executing the query. The client -// may obtain this value in databases like MySQL using queries like `select -// @@hostname`. -func DBInstanceID(val string) attribute.KeyValue { - return DBInstanceIDKey.String(val) -} - -// DBJDBCDriverClassname returns an attribute KeyValue conforming to the -// "db.jdbc.driver_classname" semantic conventions. It represents the -// fully-qualified class name of the [Java Database Connectivity -// (JDBC)](https://docs.oracle.com/javase/8/docs/technotes/guides/jdbc/) driver -// used to connect. -func DBJDBCDriverClassname(val string) attribute.KeyValue { - return DBJDBCDriverClassnameKey.String(val) -} - -// DBMongoDBCollection returns an attribute KeyValue conforming to the -// "db.mongodb.collection" semantic conventions. It represents the MongoDB -// collection being accessed within the database stated in `db.name`. -func DBMongoDBCollection(val string) attribute.KeyValue { - return DBMongoDBCollectionKey.String(val) -} - -// DBMSSQLInstanceName returns an attribute KeyValue conforming to the -// "db.mssql.instance_name" semantic conventions. It represents the Microsoft -// SQL Server [instance -// name](https://docs.microsoft.com/sql/connect/jdbc/building-the-connection-url?view=sql-server-ver15) -// connecting to. This name is used to determine the port of a named instance. -func DBMSSQLInstanceName(val string) attribute.KeyValue { - return DBMSSQLInstanceNameKey.String(val) -} - -// DBName returns an attribute KeyValue conforming to the "db.name" semantic -// conventions. It represents the this attribute is used to report the name of -// the database being accessed. For commands that switch the database, this -// should be set to the target database (even if the command fails). -func DBName(val string) attribute.KeyValue { - return DBNameKey.String(val) -} - -// DBOperation returns an attribute KeyValue conforming to the -// "db.operation" semantic conventions. It represents the name of the operation -// being executed, e.g. the [MongoDB command -// name](https://docs.mongodb.com/manual/reference/command/#database-operations) -// such as `findAndModify`, or the SQL keyword. -func DBOperation(val string) attribute.KeyValue { - return DBOperationKey.String(val) -} - -// DBRedisDBIndex returns an attribute KeyValue conforming to the -// "db.redis.database_index" semantic conventions. It represents the index of -// the database being accessed as used in the [`SELECT` -// command](https://redis.io/commands/select), provided as an integer. To be -// used instead of the generic `db.name` attribute. -func DBRedisDBIndex(val int) attribute.KeyValue { - return DBRedisDBIndexKey.Int(val) -} - -// DBSQLTable returns an attribute KeyValue conforming to the "db.sql.table" -// semantic conventions. It represents the name of the primary table that the -// operation is acting upon, including the database name (if applicable). -func DBSQLTable(val string) attribute.KeyValue { - return DBSQLTableKey.String(val) -} - -// DBStatement returns an attribute KeyValue conforming to the -// "db.statement" semantic conventions. It represents the database statement -// being executed. -func DBStatement(val string) attribute.KeyValue { - return DBStatementKey.String(val) -} - -// DBUser returns an attribute KeyValue conforming to the "db.user" semantic -// conventions. It represents the username for accessing the database. -func DBUser(val string) attribute.KeyValue { - return DBUserKey.String(val) -} - -// Describes deprecated HTTP attributes. -const ( - // HTTPFlavorKey is the attribute Key conforming to the "http.flavor" - // semantic conventions. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: deprecated - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorKey = attribute.Key("http.flavor") - - // HTTPMethodKey is the attribute Key conforming to the "http.method" - // semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'GET', 'POST', 'HEAD' - // Deprecated: use `http.request.method` instead. - HTTPMethodKey = attribute.Key("http.method") - - // HTTPRequestContentLengthKey is the attribute Key conforming to the - // "http.request_content_length" semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 3495 - // Deprecated: use `http.request.header.content-length` instead. - HTTPRequestContentLengthKey = attribute.Key("http.request_content_length") - - // HTTPResponseContentLengthKey is the attribute Key conforming to the - // "http.response_content_length" semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 3495 - // Deprecated: use `http.response.header.content-length` instead. - HTTPResponseContentLengthKey = attribute.Key("http.response_content_length") - - // HTTPSchemeKey is the attribute Key conforming to the "http.scheme" - // semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'http', 'https' - // Deprecated: use `url.scheme` instead. - HTTPSchemeKey = attribute.Key("http.scheme") - - // HTTPStatusCodeKey is the attribute Key conforming to the - // "http.status_code" semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 200 - // Deprecated: use `http.response.status_code` instead. - HTTPStatusCodeKey = attribute.Key("http.status_code") - - // HTTPTargetKey is the attribute Key conforming to the "http.target" - // semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: '/search?q=OpenTelemetry#SemConv' - // Deprecated: use `url.path` and `url.query` instead. - HTTPTargetKey = attribute.Key("http.target") - - // HTTPURLKey is the attribute Key conforming to the "http.url" semantic - // conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'https://www.foo.bar/search?q=OpenTelemetry#SemConv' - // Deprecated: use `url.full` instead. - HTTPURLKey = attribute.Key("http.url") - - // HTTPUserAgentKey is the attribute Key conforming to the - // "http.user_agent" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'CERN-LineMode/2.15 libwww/2.17b3', 'Mozilla/5.0 (iPhone; CPU - // iPhone OS 14_7_1 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) - // Version/14.1.2 Mobile/15E148 Safari/604.1' - // Deprecated: use `user_agent.original` instead. - HTTPUserAgentKey = attribute.Key("http.user_agent") -) - -var ( - // HTTP/1.0 - // - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorHTTP10 = HTTPFlavorKey.String("1.0") - // HTTP/1.1 - // - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorHTTP11 = HTTPFlavorKey.String("1.1") - // HTTP/2 - // - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorHTTP20 = HTTPFlavorKey.String("2.0") - // HTTP/3 - // - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorHTTP30 = HTTPFlavorKey.String("3.0") - // SPDY protocol - // - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorSPDY = HTTPFlavorKey.String("SPDY") - // QUIC protocol - // - // Deprecated: use `network.protocol.name` instead. - HTTPFlavorQUIC = HTTPFlavorKey.String("QUIC") -) - -// HTTPMethod returns an attribute KeyValue conforming to the "http.method" -// semantic conventions. -// -// Deprecated: use `http.request.method` instead. -func HTTPMethod(val string) attribute.KeyValue { - return HTTPMethodKey.String(val) -} - -// HTTPRequestContentLength returns an attribute KeyValue conforming to the -// "http.request_content_length" semantic conventions. -// -// Deprecated: use `http.request.header.content-length` instead. -func HTTPRequestContentLength(val int) attribute.KeyValue { - return HTTPRequestContentLengthKey.Int(val) -} - -// HTTPResponseContentLength returns an attribute KeyValue conforming to the -// "http.response_content_length" semantic conventions. -// -// Deprecated: use `http.response.header.content-length` instead. -func HTTPResponseContentLength(val int) attribute.KeyValue { - return HTTPResponseContentLengthKey.Int(val) -} - -// HTTPScheme returns an attribute KeyValue conforming to the "http.scheme" -// semantic conventions. -// -// Deprecated: use `url.scheme` instead. -func HTTPScheme(val string) attribute.KeyValue { - return HTTPSchemeKey.String(val) -} - -// HTTPStatusCode returns an attribute KeyValue conforming to the -// "http.status_code" semantic conventions. -// -// Deprecated: use `http.response.status_code` instead. -func HTTPStatusCode(val int) attribute.KeyValue { - return HTTPStatusCodeKey.Int(val) -} - -// HTTPTarget returns an attribute KeyValue conforming to the "http.target" -// semantic conventions. -// -// Deprecated: use `url.path` and `url.query` instead. -func HTTPTarget(val string) attribute.KeyValue { - return HTTPTargetKey.String(val) -} - -// HTTPURL returns an attribute KeyValue conforming to the "http.url" -// semantic conventions. -// -// Deprecated: use `url.full` instead. -func HTTPURL(val string) attribute.KeyValue { - return HTTPURLKey.String(val) -} - -// HTTPUserAgent returns an attribute KeyValue conforming to the -// "http.user_agent" semantic conventions. -// -// Deprecated: use `user_agent.original` instead. -func HTTPUserAgent(val string) attribute.KeyValue { - return HTTPUserAgentKey.String(val) -} - -// These attributes may be used for any network related operation. -const ( - // NetHostNameKey is the attribute Key conforming to the "net.host.name" - // semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'example.com' - // Deprecated: use `server.address`. - NetHostNameKey = attribute.Key("net.host.name") - - // NetHostPortKey is the attribute Key conforming to the "net.host.port" - // semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 8080 - // Deprecated: use `server.port`. - NetHostPortKey = attribute.Key("net.host.port") - - // NetPeerNameKey is the attribute Key conforming to the "net.peer.name" - // semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'example.com' - // Deprecated: use `server.address` on client spans and `client.address` on - // server spans. - NetPeerNameKey = attribute.Key("net.peer.name") - - // NetPeerPortKey is the attribute Key conforming to the "net.peer.port" - // semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 8080 - // Deprecated: use `server.port` on client spans and `client.port` on - // server spans. - NetPeerPortKey = attribute.Key("net.peer.port") - - // NetProtocolNameKey is the attribute Key conforming to the - // "net.protocol.name" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'amqp', 'http', 'mqtt' - // Deprecated: use `network.protocol.name`. - NetProtocolNameKey = attribute.Key("net.protocol.name") - - // NetProtocolVersionKey is the attribute Key conforming to the - // "net.protocol.version" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: '3.1.1' - // Deprecated: use `network.protocol.version`. - NetProtocolVersionKey = attribute.Key("net.protocol.version") - - // NetSockFamilyKey is the attribute Key conforming to the - // "net.sock.family" semantic conventions. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: deprecated - // Deprecated: use `network.transport` and `network.type`. - NetSockFamilyKey = attribute.Key("net.sock.family") - - // NetSockHostAddrKey is the attribute Key conforming to the - // "net.sock.host.addr" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: '/var/my.sock' - // Deprecated: use `network.local.address`. - NetSockHostAddrKey = attribute.Key("net.sock.host.addr") - - // NetSockHostPortKey is the attribute Key conforming to the - // "net.sock.host.port" semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 8080 - // Deprecated: use `network.local.port`. - NetSockHostPortKey = attribute.Key("net.sock.host.port") - - // NetSockPeerAddrKey is the attribute Key conforming to the - // "net.sock.peer.addr" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: '192.168.0.1' - // Deprecated: use `network.peer.address`. - NetSockPeerAddrKey = attribute.Key("net.sock.peer.addr") - - // NetSockPeerNameKey is the attribute Key conforming to the - // "net.sock.peer.name" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: '/var/my.sock' - // Deprecated: no replacement at this time. - NetSockPeerNameKey = attribute.Key("net.sock.peer.name") - - // NetSockPeerPortKey is the attribute Key conforming to the - // "net.sock.peer.port" semantic conventions. - // - // Type: int - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 65531 - // Deprecated: use `network.peer.port`. - NetSockPeerPortKey = attribute.Key("net.sock.peer.port") - - // NetTransportKey is the attribute Key conforming to the "net.transport" - // semantic conventions. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: deprecated - // Deprecated: use `network.transport`. - NetTransportKey = attribute.Key("net.transport") -) - -var ( - // IPv4 address - // - // Deprecated: use `network.transport` and `network.type`. - NetSockFamilyInet = NetSockFamilyKey.String("inet") - // IPv6 address - // - // Deprecated: use `network.transport` and `network.type`. - NetSockFamilyInet6 = NetSockFamilyKey.String("inet6") - // Unix domain socket path - // - // Deprecated: use `network.transport` and `network.type`. - NetSockFamilyUnix = NetSockFamilyKey.String("unix") -) - -var ( - // ip_tcp - // - // Deprecated: use `network.transport`. - NetTransportTCP = NetTransportKey.String("ip_tcp") - // ip_udp - // - // Deprecated: use `network.transport`. - NetTransportUDP = NetTransportKey.String("ip_udp") - // Named or anonymous pipe - // - // Deprecated: use `network.transport`. - NetTransportPipe = NetTransportKey.String("pipe") - // In-process communication - // - // Deprecated: use `network.transport`. - NetTransportInProc = NetTransportKey.String("inproc") - // Something else (non IP-based) - // - // Deprecated: use `network.transport`. - NetTransportOther = NetTransportKey.String("other") -) - -// NetHostName returns an attribute KeyValue conforming to the -// "net.host.name" semantic conventions. -// -// Deprecated: use `server.address`. -func NetHostName(val string) attribute.KeyValue { - return NetHostNameKey.String(val) -} - -// NetHostPort returns an attribute KeyValue conforming to the -// "net.host.port" semantic conventions. -// -// Deprecated: use `server.port`. -func NetHostPort(val int) attribute.KeyValue { - return NetHostPortKey.Int(val) -} - -// NetPeerName returns an attribute KeyValue conforming to the -// "net.peer.name" semantic conventions. -// -// Deprecated: use `server.address` on client spans and `client.address` on -// server spans. -func NetPeerName(val string) attribute.KeyValue { - return NetPeerNameKey.String(val) -} - -// NetPeerPort returns an attribute KeyValue conforming to the -// "net.peer.port" semantic conventions. -// -// Deprecated: use `server.port` on client spans and `client.port` on server -// spans. -func NetPeerPort(val int) attribute.KeyValue { - return NetPeerPortKey.Int(val) -} - -// NetProtocolName returns an attribute KeyValue conforming to the -// "net.protocol.name" semantic conventions. -// -// Deprecated: use `network.protocol.name`. -func NetProtocolName(val string) attribute.KeyValue { - return NetProtocolNameKey.String(val) -} - -// NetProtocolVersion returns an attribute KeyValue conforming to the -// "net.protocol.version" semantic conventions. -// -// Deprecated: use `network.protocol.version`. -func NetProtocolVersion(val string) attribute.KeyValue { - return NetProtocolVersionKey.String(val) -} - -// NetSockHostAddr returns an attribute KeyValue conforming to the -// "net.sock.host.addr" semantic conventions. -// -// Deprecated: use `network.local.address`. -func NetSockHostAddr(val string) attribute.KeyValue { - return NetSockHostAddrKey.String(val) -} - -// NetSockHostPort returns an attribute KeyValue conforming to the -// "net.sock.host.port" semantic conventions. -// -// Deprecated: use `network.local.port`. -func NetSockHostPort(val int) attribute.KeyValue { - return NetSockHostPortKey.Int(val) -} - -// NetSockPeerAddr returns an attribute KeyValue conforming to the -// "net.sock.peer.addr" semantic conventions. -// -// Deprecated: use `network.peer.address`. -func NetSockPeerAddr(val string) attribute.KeyValue { - return NetSockPeerAddrKey.String(val) -} - -// NetSockPeerName returns an attribute KeyValue conforming to the -// "net.sock.peer.name" semantic conventions. -// -// Deprecated: no replacement at this time. -func NetSockPeerName(val string) attribute.KeyValue { - return NetSockPeerNameKey.String(val) -} - -// NetSockPeerPort returns an attribute KeyValue conforming to the -// "net.sock.peer.port" semantic conventions. -// -// Deprecated: use `network.peer.port`. -func NetSockPeerPort(val int) attribute.KeyValue { - return NetSockPeerPortKey.Int(val) -} - -// These attributes may be used to describe the receiver of a network -// exchange/packet. These should be used when there is no client/server -// relationship between the two sides, or when that relationship is unknown. -// This covers low-level network interactions (e.g. packet tracing) where you -// don't know if there was a connection or which side initiated it. This also -// covers unidirectional UDP flows and peer-to-peer communication where the -// "user-facing" surface of the protocol / API doesn't expose a clear notion of -// client and server. -const ( - // DestinationAddressKey is the attribute Key conforming to the - // "destination.address" semantic conventions. It represents the - // destination address - domain name if available without reverse DNS - // lookup; otherwise, IP address or Unix domain socket name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'destination.example.com', '10.1.2.80', '/tmp/my.sock' - // Note: When observed from the source side, and when communicating through - // an intermediary, `destination.address` SHOULD represent the destination - // address behind any intermediaries, for example proxies, if it's - // available. - DestinationAddressKey = attribute.Key("destination.address") - - // DestinationPortKey is the attribute Key conforming to the - // "destination.port" semantic conventions. It represents the destination - // port number - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 3389, 2888 - DestinationPortKey = attribute.Key("destination.port") -) - -// DestinationAddress returns an attribute KeyValue conforming to the -// "destination.address" semantic conventions. It represents the destination -// address - domain name if available without reverse DNS lookup; otherwise, IP -// address or Unix domain socket name. -func DestinationAddress(val string) attribute.KeyValue { - return DestinationAddressKey.String(val) -} - -// DestinationPort returns an attribute KeyValue conforming to the -// "destination.port" semantic conventions. It represents the destination port -// number -func DestinationPort(val int) attribute.KeyValue { - return DestinationPortKey.Int(val) -} - -// These attributes may be used for any disk related operation. -const ( - // DiskIoDirectionKey is the attribute Key conforming to the - // "disk.io.direction" semantic conventions. It represents the disk IO - // operation direction. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'read' - DiskIoDirectionKey = attribute.Key("disk.io.direction") -) - -var ( - // read - DiskIoDirectionRead = DiskIoDirectionKey.String("read") - // write - DiskIoDirectionWrite = DiskIoDirectionKey.String("write") -) - -// The shared attributes used to report an error. -const ( - // ErrorTypeKey is the attribute Key conforming to the "error.type" - // semantic conventions. It represents the describes a class of error the - // operation ended with. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: stable - // Examples: 'timeout', 'java.net.UnknownHostException', - // 'server_certificate_invalid', '500' - // Note: The `error.type` SHOULD be predictable and SHOULD have low - // cardinality. - // Instrumentations SHOULD document the list of errors they report. - // - // The cardinality of `error.type` within one instrumentation library - // SHOULD be low. - // Telemetry consumers that aggregate data from multiple instrumentation - // libraries and applications - // should be prepared for `error.type` to have high cardinality at query - // time when no - // additional filters are applied. - // - // If the operation has completed successfully, instrumentations SHOULD NOT - // set `error.type`. - // - // If a specific domain defines its own set of error identifiers (such as - // HTTP or gRPC status codes), - // it's RECOMMENDED to: - // - // * Use a domain-specific attribute - // * Set `error.type` to capture all errors, regardless of whether they are - // defined within the domain-specific set or not. - ErrorTypeKey = attribute.Key("error.type") -) - -var ( - // A fallback error value to be used when the instrumentation doesn't define a custom value - ErrorTypeOther = ErrorTypeKey.String("_OTHER") -) - -// The shared attributes used to report a single exception associated with a -// span or log. -const ( - // ExceptionEscapedKey is the attribute Key conforming to the - // "exception.escaped" semantic conventions. It represents the sHOULD be - // set to true if the exception event is recorded at a point where it is - // known that the exception is escaping the scope of the span. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - // Note: An exception is considered to have escaped (or left) the scope of - // a span, - // if that span is ended while the exception is still logically "in - // flight". - // This may be actually "in flight" in some languages (e.g. if the - // exception - // is passed to a Context manager's `__exit__` method in Python) but will - // usually be caught at the point of recording the exception in most - // languages. - // - // It is usually not possible to determine at the point where an exception - // is thrown - // whether it will escape the scope of a span. - // However, it is trivial to know that an exception - // will escape, if one checks for an active exception just before ending - // the span, - // as done in the [example for recording span - // exceptions](#recording-an-exception). - // - // It follows that an exception may still escape the scope of the span - // even if the `exception.escaped` attribute was not set or set to false, - // since the event might have been recorded at a time where it was not - // clear whether the exception will escape. - ExceptionEscapedKey = attribute.Key("exception.escaped") - - // ExceptionMessageKey is the attribute Key conforming to the - // "exception.message" semantic conventions. It represents the exception - // message. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Division by zero', "Can't convert 'int' object to str - // implicitly" - ExceptionMessageKey = attribute.Key("exception.message") - - // ExceptionStacktraceKey is the attribute Key conforming to the - // "exception.stacktrace" semantic conventions. It represents a stacktrace - // as a string in the natural representation for the language runtime. The - // representation is to be determined and documented by each language SIG. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Exception in thread "main" java.lang.RuntimeException: Test - // exception\\n at ' - // 'com.example.GenerateTrace.methodB(GenerateTrace.java:13)\\n at ' - // 'com.example.GenerateTrace.methodA(GenerateTrace.java:9)\\n at ' - // 'com.example.GenerateTrace.main(GenerateTrace.java:5)' - ExceptionStacktraceKey = attribute.Key("exception.stacktrace") - - // ExceptionTypeKey is the attribute Key conforming to the "exception.type" - // semantic conventions. It represents the type of the exception (its - // fully-qualified class name, if applicable). The dynamic type of the - // exception should be preferred over the static type in languages that - // support it. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'java.net.ConnectException', 'OSError' - ExceptionTypeKey = attribute.Key("exception.type") -) - -// ExceptionEscaped returns an attribute KeyValue conforming to the -// "exception.escaped" semantic conventions. It represents the sHOULD be set to -// true if the exception event is recorded at a point where it is known that -// the exception is escaping the scope of the span. -func ExceptionEscaped(val bool) attribute.KeyValue { - return ExceptionEscapedKey.Bool(val) -} - -// ExceptionMessage returns an attribute KeyValue conforming to the -// "exception.message" semantic conventions. It represents the exception -// message. -func ExceptionMessage(val string) attribute.KeyValue { - return ExceptionMessageKey.String(val) -} - -// ExceptionStacktrace returns an attribute KeyValue conforming to the -// "exception.stacktrace" semantic conventions. It represents a stacktrace as a -// string in the natural representation for the language runtime. The -// representation is to be determined and documented by each language SIG. -func ExceptionStacktrace(val string) attribute.KeyValue { - return ExceptionStacktraceKey.String(val) -} - -// ExceptionType returns an attribute KeyValue conforming to the -// "exception.type" semantic conventions. It represents the type of the -// exception (its fully-qualified class name, if applicable). The dynamic type -// of the exception should be preferred over the static type in languages that -// support it. -func ExceptionType(val string) attribute.KeyValue { - return ExceptionTypeKey.String(val) -} - -// Semantic convention attributes in the HTTP namespace. -const ( - // HTTPRequestBodySizeKey is the attribute Key conforming to the - // "http.request.body.size" semantic conventions. It represents the size of - // the request payload body in bytes. This is the number of bytes - // transferred excluding headers and is often, but not always, present as - // the - // [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length) - // header. For requests using transport encoding, this should be the - // compressed size. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 3495 - HTTPRequestBodySizeKey = attribute.Key("http.request.body.size") - - // HTTPRequestMethodKey is the attribute Key conforming to the - // "http.request.method" semantic conventions. It represents the hTTP - // request method. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: stable - // Examples: 'GET', 'POST', 'HEAD' - // Note: HTTP request method value SHOULD be "known" to the - // instrumentation. - // By default, this convention defines "known" methods as the ones listed - // in [RFC9110](https://www.rfc-editor.org/rfc/rfc9110.html#name-methods) - // and the PATCH method defined in - // [RFC5789](https://www.rfc-editor.org/rfc/rfc5789.html). - // - // If the HTTP request method is not known to instrumentation, it MUST set - // the `http.request.method` attribute to `_OTHER`. - // - // If the HTTP instrumentation could end up converting valid HTTP request - // methods to `_OTHER`, then it MUST provide a way to override - // the list of known HTTP methods. If this override is done via environment - // variable, then the environment variable MUST be named - // OTEL_INSTRUMENTATION_HTTP_KNOWN_METHODS and support a comma-separated - // list of case-sensitive known HTTP methods - // (this list MUST be a full override of the default known method, it is - // not a list of known methods in addition to the defaults). - // - // HTTP method names are case-sensitive and `http.request.method` attribute - // value MUST match a known HTTP method name exactly. - // Instrumentations for specific web frameworks that consider HTTP methods - // to be case insensitive, SHOULD populate a canonical equivalent. - // Tracing instrumentations that do so, MUST also set - // `http.request.method_original` to the original value. - HTTPRequestMethodKey = attribute.Key("http.request.method") - - // HTTPRequestMethodOriginalKey is the attribute Key conforming to the - // "http.request.method_original" semantic conventions. It represents the - // original HTTP method sent by the client in the request line. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'GeT', 'ACL', 'foo' - HTTPRequestMethodOriginalKey = attribute.Key("http.request.method_original") - - // HTTPRequestResendCountKey is the attribute Key conforming to the - // "http.request.resend_count" semantic conventions. It represents the - // ordinal number of request resending attempt (for any reason, including - // redirects). - // - // Type: int - // RequirementLevel: Optional - // Stability: stable - // Examples: 3 - // Note: The resend count SHOULD be updated each time an HTTP request gets - // resent by the client, regardless of what was the cause of the resending - // (e.g. redirection, authorization failure, 503 Server Unavailable, - // network issues, or any other). - HTTPRequestResendCountKey = attribute.Key("http.request.resend_count") - - // HTTPResponseBodySizeKey is the attribute Key conforming to the - // "http.response.body.size" semantic conventions. It represents the size - // of the response payload body in bytes. This is the number of bytes - // transferred excluding headers and is often, but not always, present as - // the - // [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length) - // header. For requests using transport encoding, this should be the - // compressed size. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 3495 - HTTPResponseBodySizeKey = attribute.Key("http.response.body.size") - - // HTTPResponseStatusCodeKey is the attribute Key conforming to the - // "http.response.status_code" semantic conventions. It represents the - // [HTTP response status - // code](https://tools.ietf.org/html/rfc7231#section-6). - // - // Type: int - // RequirementLevel: Optional - // Stability: stable - // Examples: 200 - HTTPResponseStatusCodeKey = attribute.Key("http.response.status_code") - - // HTTPRouteKey is the attribute Key conforming to the "http.route" - // semantic conventions. It represents the matched route, that is, the path - // template in the format used by the respective server framework. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: '/users/:userID?', '{controller}/{action}/{id?}' - // Note: MUST NOT be populated when this is not supported by the HTTP - // server framework as the route attribute should have low-cardinality and - // the URI path can NOT substitute it. - // SHOULD include the [application - // root](/docs/http/http-spans.md#http-server-definitions) if there is one. - HTTPRouteKey = attribute.Key("http.route") -) - -var ( - // CONNECT method - HTTPRequestMethodConnect = HTTPRequestMethodKey.String("CONNECT") - // DELETE method - HTTPRequestMethodDelete = HTTPRequestMethodKey.String("DELETE") - // GET method - HTTPRequestMethodGet = HTTPRequestMethodKey.String("GET") - // HEAD method - HTTPRequestMethodHead = HTTPRequestMethodKey.String("HEAD") - // OPTIONS method - HTTPRequestMethodOptions = HTTPRequestMethodKey.String("OPTIONS") - // PATCH method - HTTPRequestMethodPatch = HTTPRequestMethodKey.String("PATCH") - // POST method - HTTPRequestMethodPost = HTTPRequestMethodKey.String("POST") - // PUT method - HTTPRequestMethodPut = HTTPRequestMethodKey.String("PUT") - // TRACE method - HTTPRequestMethodTrace = HTTPRequestMethodKey.String("TRACE") - // Any HTTP method that the instrumentation has no prior knowledge of - HTTPRequestMethodOther = HTTPRequestMethodKey.String("_OTHER") -) - -// HTTPRequestBodySize returns an attribute KeyValue conforming to the -// "http.request.body.size" semantic conventions. It represents the size of the -// request payload body in bytes. This is the number of bytes transferred -// excluding headers and is often, but not always, present as the -// [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length) -// header. For requests using transport encoding, this should be the compressed -// size. -func HTTPRequestBodySize(val int) attribute.KeyValue { - return HTTPRequestBodySizeKey.Int(val) -} - -// HTTPRequestMethodOriginal returns an attribute KeyValue conforming to the -// "http.request.method_original" semantic conventions. It represents the -// original HTTP method sent by the client in the request line. -func HTTPRequestMethodOriginal(val string) attribute.KeyValue { - return HTTPRequestMethodOriginalKey.String(val) -} - -// HTTPRequestResendCount returns an attribute KeyValue conforming to the -// "http.request.resend_count" semantic conventions. It represents the ordinal -// number of request resending attempt (for any reason, including redirects). -func HTTPRequestResendCount(val int) attribute.KeyValue { - return HTTPRequestResendCountKey.Int(val) -} - -// HTTPResponseBodySize returns an attribute KeyValue conforming to the -// "http.response.body.size" semantic conventions. It represents the size of -// the response payload body in bytes. This is the number of bytes transferred -// excluding headers and is often, but not always, present as the -// [Content-Length](https://www.rfc-editor.org/rfc/rfc9110.html#field.content-length) -// header. For requests using transport encoding, this should be the compressed -// size. -func HTTPResponseBodySize(val int) attribute.KeyValue { - return HTTPResponseBodySizeKey.Int(val) -} - -// HTTPResponseStatusCode returns an attribute KeyValue conforming to the -// "http.response.status_code" semantic conventions. It represents the [HTTP -// response status code](https://tools.ietf.org/html/rfc7231#section-6). -func HTTPResponseStatusCode(val int) attribute.KeyValue { - return HTTPResponseStatusCodeKey.Int(val) -} - -// HTTPRoute returns an attribute KeyValue conforming to the "http.route" -// semantic conventions. It represents the matched route, that is, the path -// template in the format used by the respective server framework. -func HTTPRoute(val string) attribute.KeyValue { - return HTTPRouteKey.String(val) -} - -// Attributes describing telemetry around messaging systems and messaging -// activities. -const ( - // MessagingBatchMessageCountKey is the attribute Key conforming to the - // "messaging.batch.message_count" semantic conventions. It represents the - // number of messages sent, received, or processed in the scope of the - // batching operation. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 0, 1, 2 - // Note: Instrumentations SHOULD NOT set `messaging.batch.message_count` on - // spans that operate with a single message. When a messaging client - // library supports both batch and single-message API for the same - // operation, instrumentations SHOULD use `messaging.batch.message_count` - // for batching APIs and SHOULD NOT use it for single-message APIs. - MessagingBatchMessageCountKey = attribute.Key("messaging.batch.message_count") - - // MessagingClientIDKey is the attribute Key conforming to the - // "messaging.client_id" semantic conventions. It represents a unique - // identifier for the client that consumes or produces a message. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'client-5', 'myhost@8742@s8083jm' - MessagingClientIDKey = attribute.Key("messaging.client_id") - - // MessagingDestinationAnonymousKey is the attribute Key conforming to the - // "messaging.destination.anonymous" semantic conventions. It represents a - // boolean that is true if the message destination is anonymous (could be - // unnamed or have auto-generated name). - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - MessagingDestinationAnonymousKey = attribute.Key("messaging.destination.anonymous") - - // MessagingDestinationNameKey is the attribute Key conforming to the - // "messaging.destination.name" semantic conventions. It represents the - // message destination name - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MyQueue', 'MyTopic' - // Note: Destination name SHOULD uniquely identify a specific queue, topic - // or other entity within the broker. If - // the broker doesn't have such notion, the destination name SHOULD - // uniquely identify the broker. - MessagingDestinationNameKey = attribute.Key("messaging.destination.name") - - // MessagingDestinationTemplateKey is the attribute Key conforming to the - // "messaging.destination.template" semantic conventions. It represents the - // low cardinality representation of the messaging destination name - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/customers/{customerID}' - // Note: Destination names could be constructed from templates. An example - // would be a destination name involving a user name or product id. - // Although the destination name in this case is of high cardinality, the - // underlying template is of low cardinality and can be effectively used - // for grouping and aggregation. - MessagingDestinationTemplateKey = attribute.Key("messaging.destination.template") - - // MessagingDestinationTemporaryKey is the attribute Key conforming to the - // "messaging.destination.temporary" semantic conventions. It represents a - // boolean that is true if the message destination is temporary and might - // not exist anymore after messages are processed. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - MessagingDestinationTemporaryKey = attribute.Key("messaging.destination.temporary") - - // MessagingDestinationPublishAnonymousKey is the attribute Key conforming - // to the "messaging.destination_publish.anonymous" semantic conventions. - // It represents a boolean that is true if the publish message destination - // is anonymous (could be unnamed or have auto-generated name). - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - MessagingDestinationPublishAnonymousKey = attribute.Key("messaging.destination_publish.anonymous") - - // MessagingDestinationPublishNameKey is the attribute Key conforming to - // the "messaging.destination_publish.name" semantic conventions. It - // represents the name of the original destination the message was - // published to - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MyQueue', 'MyTopic' - // Note: The name SHOULD uniquely identify a specific queue, topic, or - // other entity within the broker. If - // the broker doesn't have such notion, the original destination name - // SHOULD uniquely identify the broker. - MessagingDestinationPublishNameKey = attribute.Key("messaging.destination_publish.name") - - // MessagingGCPPubsubMessageOrderingKeyKey is the attribute Key conforming - // to the "messaging.gcp_pubsub.message.ordering_key" semantic conventions. - // It represents the ordering key for a given message. If the attribute is - // not present, the message does not have an ordering key. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'ordering_key' - MessagingGCPPubsubMessageOrderingKeyKey = attribute.Key("messaging.gcp_pubsub.message.ordering_key") - - // MessagingKafkaConsumerGroupKey is the attribute Key conforming to the - // "messaging.kafka.consumer.group" semantic conventions. It represents the - // name of the Kafka Consumer Group that is handling the message. Only - // applies to consumers, not producers. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'my-group' - MessagingKafkaConsumerGroupKey = attribute.Key("messaging.kafka.consumer.group") - - // MessagingKafkaDestinationPartitionKey is the attribute Key conforming to - // the "messaging.kafka.destination.partition" semantic conventions. It - // represents the partition the message is sent to. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 2 - MessagingKafkaDestinationPartitionKey = attribute.Key("messaging.kafka.destination.partition") - - // MessagingKafkaMessageKeyKey is the attribute Key conforming to the - // "messaging.kafka.message.key" semantic conventions. It represents the - // message keys in Kafka are used for grouping alike messages to ensure - // they're processed on the same partition. They differ from - // `messaging.message.id` in that they're not unique. If the key is `null`, - // the attribute MUST NOT be set. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myKey' - // Note: If the key type is not string, it's string representation has to - // be supplied for the attribute. If the key has no unambiguous, canonical - // string form, don't include its value. - MessagingKafkaMessageKeyKey = attribute.Key("messaging.kafka.message.key") - - // MessagingKafkaMessageOffsetKey is the attribute Key conforming to the - // "messaging.kafka.message.offset" semantic conventions. It represents the - // offset of a record in the corresponding Kafka partition. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 42 - MessagingKafkaMessageOffsetKey = attribute.Key("messaging.kafka.message.offset") - - // MessagingKafkaMessageTombstoneKey is the attribute Key conforming to the - // "messaging.kafka.message.tombstone" semantic conventions. It represents - // a boolean that is true if the message is a tombstone. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - MessagingKafkaMessageTombstoneKey = attribute.Key("messaging.kafka.message.tombstone") - - // MessagingMessageBodySizeKey is the attribute Key conforming to the - // "messaging.message.body.size" semantic conventions. It represents the - // size of the message body in bytes. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1439 - // Note: This can refer to both the compressed or uncompressed body size. - // If both sizes are known, the uncompressed - // body size should be used. - MessagingMessageBodySizeKey = attribute.Key("messaging.message.body.size") - - // MessagingMessageConversationIDKey is the attribute Key conforming to the - // "messaging.message.conversation_id" semantic conventions. It represents - // the conversation ID identifying the conversation to which the message - // belongs, represented as a string. Sometimes called "Correlation ID". - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MyConversationID' - MessagingMessageConversationIDKey = attribute.Key("messaging.message.conversation_id") - - // MessagingMessageEnvelopeSizeKey is the attribute Key conforming to the - // "messaging.message.envelope.size" semantic conventions. It represents - // the size of the message body and metadata in bytes. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 2738 - // Note: This can refer to both the compressed or uncompressed size. If - // both sizes are known, the uncompressed - // size should be used. - MessagingMessageEnvelopeSizeKey = attribute.Key("messaging.message.envelope.size") - - // MessagingMessageIDKey is the attribute Key conforming to the - // "messaging.message.id" semantic conventions. It represents a value used - // by the messaging system as an identifier for the message, represented as - // a string. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '452a7c7c7c7048c2f887f61572b18fc2' - MessagingMessageIDKey = attribute.Key("messaging.message.id") - - // MessagingOperationKey is the attribute Key conforming to the - // "messaging.operation" semantic conventions. It represents a string - // identifying the kind of messaging operation. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Note: If a custom value is used, it MUST be of low cardinality. - MessagingOperationKey = attribute.Key("messaging.operation") - - // MessagingRabbitmqDestinationRoutingKeyKey is the attribute Key - // conforming to the "messaging.rabbitmq.destination.routing_key" semantic - // conventions. It represents the rabbitMQ message routing key. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myKey' - MessagingRabbitmqDestinationRoutingKeyKey = attribute.Key("messaging.rabbitmq.destination.routing_key") - - // MessagingRocketmqClientGroupKey is the attribute Key conforming to the - // "messaging.rocketmq.client_group" semantic conventions. It represents - // the name of the RocketMQ producer/consumer group that is handling the - // message. The client type is identified by the SpanKind. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myConsumerGroup' - MessagingRocketmqClientGroupKey = attribute.Key("messaging.rocketmq.client_group") - - // MessagingRocketmqConsumptionModelKey is the attribute Key conforming to - // the "messaging.rocketmq.consumption_model" semantic conventions. It - // represents the model of message consumption. This only applies to - // consumer spans. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - MessagingRocketmqConsumptionModelKey = attribute.Key("messaging.rocketmq.consumption_model") - - // MessagingRocketmqMessageDelayTimeLevelKey is the attribute Key - // conforming to the "messaging.rocketmq.message.delay_time_level" semantic - // conventions. It represents the delay time level for delay message, which - // determines the message delay time. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 3 - MessagingRocketmqMessageDelayTimeLevelKey = attribute.Key("messaging.rocketmq.message.delay_time_level") - - // MessagingRocketmqMessageDeliveryTimestampKey is the attribute Key - // conforming to the "messaging.rocketmq.message.delivery_timestamp" - // semantic conventions. It represents the timestamp in milliseconds that - // the delay message is expected to be delivered to consumer. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1665987217045 - MessagingRocketmqMessageDeliveryTimestampKey = attribute.Key("messaging.rocketmq.message.delivery_timestamp") - - // MessagingRocketmqMessageGroupKey is the attribute Key conforming to the - // "messaging.rocketmq.message.group" semantic conventions. It represents - // the it is essential for FIFO message. Messages that belong to the same - // message group are always processed one by one within the same consumer - // group. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myMessageGroup' - MessagingRocketmqMessageGroupKey = attribute.Key("messaging.rocketmq.message.group") - - // MessagingRocketmqMessageKeysKey is the attribute Key conforming to the - // "messaging.rocketmq.message.keys" semantic conventions. It represents - // the key(s) of message, another way to mark message besides message id. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'keyA', 'keyB' - MessagingRocketmqMessageKeysKey = attribute.Key("messaging.rocketmq.message.keys") - - // MessagingRocketmqMessageTagKey is the attribute Key conforming to the - // "messaging.rocketmq.message.tag" semantic conventions. It represents the - // secondary classifier of message besides topic. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'tagA' - MessagingRocketmqMessageTagKey = attribute.Key("messaging.rocketmq.message.tag") - - // MessagingRocketmqMessageTypeKey is the attribute Key conforming to the - // "messaging.rocketmq.message.type" semantic conventions. It represents - // the type of message. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - MessagingRocketmqMessageTypeKey = attribute.Key("messaging.rocketmq.message.type") - - // MessagingRocketmqNamespaceKey is the attribute Key conforming to the - // "messaging.rocketmq.namespace" semantic conventions. It represents the - // namespace of RocketMQ resources, resources in different namespaces are - // individual. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myNamespace' - MessagingRocketmqNamespaceKey = attribute.Key("messaging.rocketmq.namespace") - - // MessagingSystemKey is the attribute Key conforming to the - // "messaging.system" semantic conventions. It represents an identifier for - // the messaging system being used. See below for a list of well-known - // identifiers. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - MessagingSystemKey = attribute.Key("messaging.system") -) - -var ( - // One or more messages are provided for publishing to an intermediary. If a single message is published, the context of the "Publish" span can be used as the creation context and no "Create" span needs to be created - MessagingOperationPublish = MessagingOperationKey.String("publish") - // A message is created. "Create" spans always refer to a single message and are used to provide a unique creation context for messages in batch publishing scenarios - MessagingOperationCreate = MessagingOperationKey.String("create") - // One or more messages are requested by a consumer. This operation refers to pull-based scenarios, where consumers explicitly call methods of messaging SDKs to receive messages - MessagingOperationReceive = MessagingOperationKey.String("receive") - // One or more messages are passed to a consumer. This operation refers to push-based scenarios, where consumer register callbacks which get called by messaging SDKs - MessagingOperationDeliver = MessagingOperationKey.String("deliver") -) - -var ( - // Clustering consumption model - MessagingRocketmqConsumptionModelClustering = MessagingRocketmqConsumptionModelKey.String("clustering") - // Broadcasting consumption model - MessagingRocketmqConsumptionModelBroadcasting = MessagingRocketmqConsumptionModelKey.String("broadcasting") -) - -var ( - // Normal message - MessagingRocketmqMessageTypeNormal = MessagingRocketmqMessageTypeKey.String("normal") - // FIFO message - MessagingRocketmqMessageTypeFifo = MessagingRocketmqMessageTypeKey.String("fifo") - // Delay message - MessagingRocketmqMessageTypeDelay = MessagingRocketmqMessageTypeKey.String("delay") - // Transaction message - MessagingRocketmqMessageTypeTransaction = MessagingRocketmqMessageTypeKey.String("transaction") -) - -var ( - // Apache ActiveMQ - MessagingSystemActivemq = MessagingSystemKey.String("activemq") - // Amazon Simple Queue Service (SQS) - MessagingSystemAWSSqs = MessagingSystemKey.String("aws_sqs") - // Azure Event Grid - MessagingSystemAzureEventgrid = MessagingSystemKey.String("azure_eventgrid") - // Azure Event Hubs - MessagingSystemAzureEventhubs = MessagingSystemKey.String("azure_eventhubs") - // Azure Service Bus - MessagingSystemAzureServicebus = MessagingSystemKey.String("azure_servicebus") - // Google Cloud Pub/Sub - MessagingSystemGCPPubsub = MessagingSystemKey.String("gcp_pubsub") - // Java Message Service - MessagingSystemJms = MessagingSystemKey.String("jms") - // Apache Kafka - MessagingSystemKafka = MessagingSystemKey.String("kafka") - // RabbitMQ - MessagingSystemRabbitmq = MessagingSystemKey.String("rabbitmq") - // Apache RocketMQ - MessagingSystemRocketmq = MessagingSystemKey.String("rocketmq") -) - -// MessagingBatchMessageCount returns an attribute KeyValue conforming to -// the "messaging.batch.message_count" semantic conventions. It represents the -// number of messages sent, received, or processed in the scope of the batching -// operation. -func MessagingBatchMessageCount(val int) attribute.KeyValue { - return MessagingBatchMessageCountKey.Int(val) -} - -// MessagingClientID returns an attribute KeyValue conforming to the -// "messaging.client_id" semantic conventions. It represents a unique -// identifier for the client that consumes or produces a message. -func MessagingClientID(val string) attribute.KeyValue { - return MessagingClientIDKey.String(val) -} - -// MessagingDestinationAnonymous returns an attribute KeyValue conforming to -// the "messaging.destination.anonymous" semantic conventions. It represents a -// boolean that is true if the message destination is anonymous (could be -// unnamed or have auto-generated name). -func MessagingDestinationAnonymous(val bool) attribute.KeyValue { - return MessagingDestinationAnonymousKey.Bool(val) -} - -// MessagingDestinationName returns an attribute KeyValue conforming to the -// "messaging.destination.name" semantic conventions. It represents the message -// destination name -func MessagingDestinationName(val string) attribute.KeyValue { - return MessagingDestinationNameKey.String(val) -} - -// MessagingDestinationTemplate returns an attribute KeyValue conforming to -// the "messaging.destination.template" semantic conventions. It represents the -// low cardinality representation of the messaging destination name -func MessagingDestinationTemplate(val string) attribute.KeyValue { - return MessagingDestinationTemplateKey.String(val) -} - -// MessagingDestinationTemporary returns an attribute KeyValue conforming to -// the "messaging.destination.temporary" semantic conventions. It represents a -// boolean that is true if the message destination is temporary and might not -// exist anymore after messages are processed. -func MessagingDestinationTemporary(val bool) attribute.KeyValue { - return MessagingDestinationTemporaryKey.Bool(val) -} - -// MessagingDestinationPublishAnonymous returns an attribute KeyValue -// conforming to the "messaging.destination_publish.anonymous" semantic -// conventions. It represents a boolean that is true if the publish message -// destination is anonymous (could be unnamed or have auto-generated name). -func MessagingDestinationPublishAnonymous(val bool) attribute.KeyValue { - return MessagingDestinationPublishAnonymousKey.Bool(val) -} - -// MessagingDestinationPublishName returns an attribute KeyValue conforming -// to the "messaging.destination_publish.name" semantic conventions. It -// represents the name of the original destination the message was published to -func MessagingDestinationPublishName(val string) attribute.KeyValue { - return MessagingDestinationPublishNameKey.String(val) -} - -// MessagingGCPPubsubMessageOrderingKey returns an attribute KeyValue -// conforming to the "messaging.gcp_pubsub.message.ordering_key" semantic -// conventions. It represents the ordering key for a given message. If the -// attribute is not present, the message does not have an ordering key. -func MessagingGCPPubsubMessageOrderingKey(val string) attribute.KeyValue { - return MessagingGCPPubsubMessageOrderingKeyKey.String(val) -} - -// MessagingKafkaConsumerGroup returns an attribute KeyValue conforming to -// the "messaging.kafka.consumer.group" semantic conventions. It represents the -// name of the Kafka Consumer Group that is handling the message. Only applies -// to consumers, not producers. -func MessagingKafkaConsumerGroup(val string) attribute.KeyValue { - return MessagingKafkaConsumerGroupKey.String(val) -} - -// MessagingKafkaDestinationPartition returns an attribute KeyValue -// conforming to the "messaging.kafka.destination.partition" semantic -// conventions. It represents the partition the message is sent to. -func MessagingKafkaDestinationPartition(val int) attribute.KeyValue { - return MessagingKafkaDestinationPartitionKey.Int(val) -} - -// MessagingKafkaMessageKey returns an attribute KeyValue conforming to the -// "messaging.kafka.message.key" semantic conventions. It represents the -// message keys in Kafka are used for grouping alike messages to ensure they're -// processed on the same partition. They differ from `messaging.message.id` in -// that they're not unique. If the key is `null`, the attribute MUST NOT be -// set. -func MessagingKafkaMessageKey(val string) attribute.KeyValue { - return MessagingKafkaMessageKeyKey.String(val) -} - -// MessagingKafkaMessageOffset returns an attribute KeyValue conforming to -// the "messaging.kafka.message.offset" semantic conventions. It represents the -// offset of a record in the corresponding Kafka partition. -func MessagingKafkaMessageOffset(val int) attribute.KeyValue { - return MessagingKafkaMessageOffsetKey.Int(val) -} - -// MessagingKafkaMessageTombstone returns an attribute KeyValue conforming -// to the "messaging.kafka.message.tombstone" semantic conventions. It -// represents a boolean that is true if the message is a tombstone. -func MessagingKafkaMessageTombstone(val bool) attribute.KeyValue { - return MessagingKafkaMessageTombstoneKey.Bool(val) -} - -// MessagingMessageBodySize returns an attribute KeyValue conforming to the -// "messaging.message.body.size" semantic conventions. It represents the size -// of the message body in bytes. -func MessagingMessageBodySize(val int) attribute.KeyValue { - return MessagingMessageBodySizeKey.Int(val) -} - -// MessagingMessageConversationID returns an attribute KeyValue conforming -// to the "messaging.message.conversation_id" semantic conventions. It -// represents the conversation ID identifying the conversation to which the -// message belongs, represented as a string. Sometimes called "Correlation ID". -func MessagingMessageConversationID(val string) attribute.KeyValue { - return MessagingMessageConversationIDKey.String(val) -} - -// MessagingMessageEnvelopeSize returns an attribute KeyValue conforming to -// the "messaging.message.envelope.size" semantic conventions. It represents -// the size of the message body and metadata in bytes. -func MessagingMessageEnvelopeSize(val int) attribute.KeyValue { - return MessagingMessageEnvelopeSizeKey.Int(val) -} - -// MessagingMessageID returns an attribute KeyValue conforming to the -// "messaging.message.id" semantic conventions. It represents a value used by -// the messaging system as an identifier for the message, represented as a -// string. -func MessagingMessageID(val string) attribute.KeyValue { - return MessagingMessageIDKey.String(val) -} - -// MessagingRabbitmqDestinationRoutingKey returns an attribute KeyValue -// conforming to the "messaging.rabbitmq.destination.routing_key" semantic -// conventions. It represents the rabbitMQ message routing key. -func MessagingRabbitmqDestinationRoutingKey(val string) attribute.KeyValue { - return MessagingRabbitmqDestinationRoutingKeyKey.String(val) -} - -// MessagingRocketmqClientGroup returns an attribute KeyValue conforming to -// the "messaging.rocketmq.client_group" semantic conventions. It represents -// the name of the RocketMQ producer/consumer group that is handling the -// message. The client type is identified by the SpanKind. -func MessagingRocketmqClientGroup(val string) attribute.KeyValue { - return MessagingRocketmqClientGroupKey.String(val) -} - -// MessagingRocketmqMessageDelayTimeLevel returns an attribute KeyValue -// conforming to the "messaging.rocketmq.message.delay_time_level" semantic -// conventions. It represents the delay time level for delay message, which -// determines the message delay time. -func MessagingRocketmqMessageDelayTimeLevel(val int) attribute.KeyValue { - return MessagingRocketmqMessageDelayTimeLevelKey.Int(val) -} - -// MessagingRocketmqMessageDeliveryTimestamp returns an attribute KeyValue -// conforming to the "messaging.rocketmq.message.delivery_timestamp" semantic -// conventions. It represents the timestamp in milliseconds that the delay -// message is expected to be delivered to consumer. -func MessagingRocketmqMessageDeliveryTimestamp(val int) attribute.KeyValue { - return MessagingRocketmqMessageDeliveryTimestampKey.Int(val) -} - -// MessagingRocketmqMessageGroup returns an attribute KeyValue conforming to -// the "messaging.rocketmq.message.group" semantic conventions. It represents -// the it is essential for FIFO message. Messages that belong to the same -// message group are always processed one by one within the same consumer -// group. -func MessagingRocketmqMessageGroup(val string) attribute.KeyValue { - return MessagingRocketmqMessageGroupKey.String(val) -} - -// MessagingRocketmqMessageKeys returns an attribute KeyValue conforming to -// the "messaging.rocketmq.message.keys" semantic conventions. It represents -// the key(s) of message, another way to mark message besides message id. -func MessagingRocketmqMessageKeys(val ...string) attribute.KeyValue { - return MessagingRocketmqMessageKeysKey.StringSlice(val) -} - -// MessagingRocketmqMessageTag returns an attribute KeyValue conforming to -// the "messaging.rocketmq.message.tag" semantic conventions. It represents the -// secondary classifier of message besides topic. -func MessagingRocketmqMessageTag(val string) attribute.KeyValue { - return MessagingRocketmqMessageTagKey.String(val) -} - -// MessagingRocketmqNamespace returns an attribute KeyValue conforming to -// the "messaging.rocketmq.namespace" semantic conventions. It represents the -// namespace of RocketMQ resources, resources in different namespaces are -// individual. -func MessagingRocketmqNamespace(val string) attribute.KeyValue { - return MessagingRocketmqNamespaceKey.String(val) -} - -// These attributes may be used for any network related operation. -const ( - // NetworkCarrierIccKey is the attribute Key conforming to the - // "network.carrier.icc" semantic conventions. It represents the ISO 3166-1 - // alpha-2 2-character country code associated with the mobile carrier - // network. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'DE' - NetworkCarrierIccKey = attribute.Key("network.carrier.icc") - - // NetworkCarrierMccKey is the attribute Key conforming to the - // "network.carrier.mcc" semantic conventions. It represents the mobile - // carrier country code. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '310' - NetworkCarrierMccKey = attribute.Key("network.carrier.mcc") - - // NetworkCarrierMncKey is the attribute Key conforming to the - // "network.carrier.mnc" semantic conventions. It represents the mobile - // carrier network code. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '001' - NetworkCarrierMncKey = attribute.Key("network.carrier.mnc") - - // NetworkCarrierNameKey is the attribute Key conforming to the - // "network.carrier.name" semantic conventions. It represents the name of - // the mobile carrier. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'sprint' - NetworkCarrierNameKey = attribute.Key("network.carrier.name") - - // NetworkConnectionSubtypeKey is the attribute Key conforming to the - // "network.connection.subtype" semantic conventions. It represents the - // this describes more details regarding the connection.type. It may be the - // type of cell technology connection, but it could be used for describing - // details about a wifi connection. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'LTE' - NetworkConnectionSubtypeKey = attribute.Key("network.connection.subtype") - - // NetworkConnectionTypeKey is the attribute Key conforming to the - // "network.connection.type" semantic conventions. It represents the - // internet connection type. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'wifi' - NetworkConnectionTypeKey = attribute.Key("network.connection.type") - - // NetworkIoDirectionKey is the attribute Key conforming to the - // "network.io.direction" semantic conventions. It represents the network - // IO operation direction. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'transmit' - NetworkIoDirectionKey = attribute.Key("network.io.direction") - - // NetworkLocalAddressKey is the attribute Key conforming to the - // "network.local.address" semantic conventions. It represents the local - // address of the network connection - IP address or Unix domain socket - // name. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: '10.1.2.80', '/tmp/my.sock' - NetworkLocalAddressKey = attribute.Key("network.local.address") - - // NetworkLocalPortKey is the attribute Key conforming to the - // "network.local.port" semantic conventions. It represents the local port - // number of the network connection. - // - // Type: int - // RequirementLevel: Optional - // Stability: stable - // Examples: 65123 - NetworkLocalPortKey = attribute.Key("network.local.port") - - // NetworkPeerAddressKey is the attribute Key conforming to the - // "network.peer.address" semantic conventions. It represents the peer - // address of the network connection - IP address or Unix domain socket - // name. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: '10.1.2.80', '/tmp/my.sock' - NetworkPeerAddressKey = attribute.Key("network.peer.address") - - // NetworkPeerPortKey is the attribute Key conforming to the - // "network.peer.port" semantic conventions. It represents the peer port - // number of the network connection. - // - // Type: int - // RequirementLevel: Optional - // Stability: stable - // Examples: 65123 - NetworkPeerPortKey = attribute.Key("network.peer.port") - - // NetworkProtocolNameKey is the attribute Key conforming to the - // "network.protocol.name" semantic conventions. It represents the [OSI - // application layer](https://osi-model.com/application-layer/) or non-OSI - // equivalent. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'amqp', 'http', 'mqtt' - // Note: The value SHOULD be normalized to lowercase. - NetworkProtocolNameKey = attribute.Key("network.protocol.name") - - // NetworkProtocolVersionKey is the attribute Key conforming to the - // "network.protocol.version" semantic conventions. It represents the - // version of the protocol specified in `network.protocol.name`. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: '3.1.1' - // Note: `network.protocol.version` refers to the version of the protocol - // used and might be different from the protocol client's version. If the - // HTTP client has a version of `0.27.2`, but sends HTTP version `1.1`, - // this attribute should be set to `1.1`. - NetworkProtocolVersionKey = attribute.Key("network.protocol.version") - - // NetworkTransportKey is the attribute Key conforming to the - // "network.transport" semantic conventions. It represents the [OSI - // transport layer](https://osi-model.com/transport-layer/) or - // [inter-process communication - // method](https://wikipedia.org/wiki/Inter-process_communication). - // - // Type: Enum - // RequirementLevel: Optional - // Stability: stable - // Examples: 'tcp', 'udp' - // Note: The value SHOULD be normalized to lowercase. - // - // Consider always setting the transport when setting a port number, since - // a port number is ambiguous without knowing the transport. For example - // different processes could be listening on TCP port 12345 and UDP port - // 12345. - NetworkTransportKey = attribute.Key("network.transport") - - // NetworkTypeKey is the attribute Key conforming to the "network.type" - // semantic conventions. It represents the [OSI network - // layer](https://osi-model.com/network-layer/) or non-OSI equivalent. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: stable - // Examples: 'ipv4', 'ipv6' - // Note: The value SHOULD be normalized to lowercase. - NetworkTypeKey = attribute.Key("network.type") -) - -var ( - // GPRS - NetworkConnectionSubtypeGprs = NetworkConnectionSubtypeKey.String("gprs") - // EDGE - NetworkConnectionSubtypeEdge = NetworkConnectionSubtypeKey.String("edge") - // UMTS - NetworkConnectionSubtypeUmts = NetworkConnectionSubtypeKey.String("umts") - // CDMA - NetworkConnectionSubtypeCdma = NetworkConnectionSubtypeKey.String("cdma") - // EVDO Rel. 0 - NetworkConnectionSubtypeEvdo0 = NetworkConnectionSubtypeKey.String("evdo_0") - // EVDO Rev. A - NetworkConnectionSubtypeEvdoA = NetworkConnectionSubtypeKey.String("evdo_a") - // CDMA2000 1XRTT - NetworkConnectionSubtypeCdma20001xrtt = NetworkConnectionSubtypeKey.String("cdma2000_1xrtt") - // HSDPA - NetworkConnectionSubtypeHsdpa = NetworkConnectionSubtypeKey.String("hsdpa") - // HSUPA - NetworkConnectionSubtypeHsupa = NetworkConnectionSubtypeKey.String("hsupa") - // HSPA - NetworkConnectionSubtypeHspa = NetworkConnectionSubtypeKey.String("hspa") - // IDEN - NetworkConnectionSubtypeIden = NetworkConnectionSubtypeKey.String("iden") - // EVDO Rev. B - NetworkConnectionSubtypeEvdoB = NetworkConnectionSubtypeKey.String("evdo_b") - // LTE - NetworkConnectionSubtypeLte = NetworkConnectionSubtypeKey.String("lte") - // EHRPD - NetworkConnectionSubtypeEhrpd = NetworkConnectionSubtypeKey.String("ehrpd") - // HSPAP - NetworkConnectionSubtypeHspap = NetworkConnectionSubtypeKey.String("hspap") - // GSM - NetworkConnectionSubtypeGsm = NetworkConnectionSubtypeKey.String("gsm") - // TD-SCDMA - NetworkConnectionSubtypeTdScdma = NetworkConnectionSubtypeKey.String("td_scdma") - // IWLAN - NetworkConnectionSubtypeIwlan = NetworkConnectionSubtypeKey.String("iwlan") - // 5G NR (New Radio) - NetworkConnectionSubtypeNr = NetworkConnectionSubtypeKey.String("nr") - // 5G NRNSA (New Radio Non-Standalone) - NetworkConnectionSubtypeNrnsa = NetworkConnectionSubtypeKey.String("nrnsa") - // LTE CA - NetworkConnectionSubtypeLteCa = NetworkConnectionSubtypeKey.String("lte_ca") -) - -var ( - // wifi - NetworkConnectionTypeWifi = NetworkConnectionTypeKey.String("wifi") - // wired - NetworkConnectionTypeWired = NetworkConnectionTypeKey.String("wired") - // cell - NetworkConnectionTypeCell = NetworkConnectionTypeKey.String("cell") - // unavailable - NetworkConnectionTypeUnavailable = NetworkConnectionTypeKey.String("unavailable") - // unknown - NetworkConnectionTypeUnknown = NetworkConnectionTypeKey.String("unknown") -) - -var ( - // transmit - NetworkIoDirectionTransmit = NetworkIoDirectionKey.String("transmit") - // receive - NetworkIoDirectionReceive = NetworkIoDirectionKey.String("receive") -) - -var ( - // TCP - NetworkTransportTCP = NetworkTransportKey.String("tcp") - // UDP - NetworkTransportUDP = NetworkTransportKey.String("udp") - // Named or anonymous pipe - NetworkTransportPipe = NetworkTransportKey.String("pipe") - // Unix domain socket - NetworkTransportUnix = NetworkTransportKey.String("unix") -) - -var ( - // IPv4 - NetworkTypeIpv4 = NetworkTypeKey.String("ipv4") - // IPv6 - NetworkTypeIpv6 = NetworkTypeKey.String("ipv6") -) - -// NetworkCarrierIcc returns an attribute KeyValue conforming to the -// "network.carrier.icc" semantic conventions. It represents the ISO 3166-1 -// alpha-2 2-character country code associated with the mobile carrier network. -func NetworkCarrierIcc(val string) attribute.KeyValue { - return NetworkCarrierIccKey.String(val) -} - -// NetworkCarrierMcc returns an attribute KeyValue conforming to the -// "network.carrier.mcc" semantic conventions. It represents the mobile carrier -// country code. -func NetworkCarrierMcc(val string) attribute.KeyValue { - return NetworkCarrierMccKey.String(val) -} - -// NetworkCarrierMnc returns an attribute KeyValue conforming to the -// "network.carrier.mnc" semantic conventions. It represents the mobile carrier -// network code. -func NetworkCarrierMnc(val string) attribute.KeyValue { - return NetworkCarrierMncKey.String(val) -} - -// NetworkCarrierName returns an attribute KeyValue conforming to the -// "network.carrier.name" semantic conventions. It represents the name of the -// mobile carrier. -func NetworkCarrierName(val string) attribute.KeyValue { - return NetworkCarrierNameKey.String(val) -} - -// NetworkLocalAddress returns an attribute KeyValue conforming to the -// "network.local.address" semantic conventions. It represents the local -// address of the network connection - IP address or Unix domain socket name. -func NetworkLocalAddress(val string) attribute.KeyValue { - return NetworkLocalAddressKey.String(val) -} - -// NetworkLocalPort returns an attribute KeyValue conforming to the -// "network.local.port" semantic conventions. It represents the local port -// number of the network connection. -func NetworkLocalPort(val int) attribute.KeyValue { - return NetworkLocalPortKey.Int(val) -} - -// NetworkPeerAddress returns an attribute KeyValue conforming to the -// "network.peer.address" semantic conventions. It represents the peer address -// of the network connection - IP address or Unix domain socket name. -func NetworkPeerAddress(val string) attribute.KeyValue { - return NetworkPeerAddressKey.String(val) -} - -// NetworkPeerPort returns an attribute KeyValue conforming to the -// "network.peer.port" semantic conventions. It represents the peer port number -// of the network connection. -func NetworkPeerPort(val int) attribute.KeyValue { - return NetworkPeerPortKey.Int(val) -} - -// NetworkProtocolName returns an attribute KeyValue conforming to the -// "network.protocol.name" semantic conventions. It represents the [OSI -// application layer](https://osi-model.com/application-layer/) or non-OSI -// equivalent. -func NetworkProtocolName(val string) attribute.KeyValue { - return NetworkProtocolNameKey.String(val) -} - -// NetworkProtocolVersion returns an attribute KeyValue conforming to the -// "network.protocol.version" semantic conventions. It represents the version -// of the protocol specified in `network.protocol.name`. -func NetworkProtocolVersion(val string) attribute.KeyValue { - return NetworkProtocolVersionKey.String(val) -} - -// Attributes for remote procedure calls. -const ( - // RPCConnectRPCErrorCodeKey is the attribute Key conforming to the - // "rpc.connect_rpc.error_code" semantic conventions. It represents the - // [error codes](https://connect.build/docs/protocol/#error-codes) of the - // Connect request. Error codes are always string values. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - RPCConnectRPCErrorCodeKey = attribute.Key("rpc.connect_rpc.error_code") - - // RPCGRPCStatusCodeKey is the attribute Key conforming to the - // "rpc.grpc.status_code" semantic conventions. It represents the [numeric - // status - // code](https://github.com/grpc/grpc/blob/v1.33.2/doc/statuscodes.md) of - // the gRPC request. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - RPCGRPCStatusCodeKey = attribute.Key("rpc.grpc.status_code") - - // RPCJsonrpcErrorCodeKey is the attribute Key conforming to the - // "rpc.jsonrpc.error_code" semantic conventions. It represents the - // `error.code` property of response if it is an error response. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: -32700, 100 - RPCJsonrpcErrorCodeKey = attribute.Key("rpc.jsonrpc.error_code") - - // RPCJsonrpcErrorMessageKey is the attribute Key conforming to the - // "rpc.jsonrpc.error_message" semantic conventions. It represents the - // `error.message` property of response if it is an error response. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Parse error', 'User already exists' - RPCJsonrpcErrorMessageKey = attribute.Key("rpc.jsonrpc.error_message") - - // RPCJsonrpcRequestIDKey is the attribute Key conforming to the - // "rpc.jsonrpc.request_id" semantic conventions. It represents the `id` - // property of request or response. Since protocol allows id to be int, - // string, `null` or missing (for notifications), value is expected to be - // cast to string for simplicity. Use empty string in case of `null` value. - // Omit entirely if this is a notification. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '10', 'request-7', '' - RPCJsonrpcRequestIDKey = attribute.Key("rpc.jsonrpc.request_id") - - // RPCJsonrpcVersionKey is the attribute Key conforming to the - // "rpc.jsonrpc.version" semantic conventions. It represents the protocol - // version as in `jsonrpc` property of request/response. Since JSON-RPC 1.0 - // doesn't specify this, the value can be omitted. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2.0', '1.0' - RPCJsonrpcVersionKey = attribute.Key("rpc.jsonrpc.version") - - // RPCMethodKey is the attribute Key conforming to the "rpc.method" - // semantic conventions. It represents the name of the (logical) method - // being called, must be equal to the $method part in the span name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'exampleMethod' - // Note: This is the logical name of the method from the RPC interface - // perspective, which can be different from the name of any implementing - // method/function. The `code.function` attribute may be used to store the - // latter (e.g., method actually executing the call on the server side, RPC - // client stub method on the client side). - RPCMethodKey = attribute.Key("rpc.method") - - // RPCServiceKey is the attribute Key conforming to the "rpc.service" - // semantic conventions. It represents the full (logical) name of the - // service being called, including its package name, if applicable. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myservice.EchoService' - // Note: This is the logical name of the service from the RPC interface - // perspective, which can be different from the name of any implementing - // class. The `code.namespace` attribute may be used to store the latter - // (despite the attribute name, it may include a class name; e.g., class - // with method actually executing the call on the server side, RPC client - // stub class on the client side). - RPCServiceKey = attribute.Key("rpc.service") - - // RPCSystemKey is the attribute Key conforming to the "rpc.system" - // semantic conventions. It represents a string identifying the remoting - // system. See below for a list of well-known identifiers. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - RPCSystemKey = attribute.Key("rpc.system") -) - -var ( - // cancelled - RPCConnectRPCErrorCodeCancelled = RPCConnectRPCErrorCodeKey.String("cancelled") - // unknown - RPCConnectRPCErrorCodeUnknown = RPCConnectRPCErrorCodeKey.String("unknown") - // invalid_argument - RPCConnectRPCErrorCodeInvalidArgument = RPCConnectRPCErrorCodeKey.String("invalid_argument") - // deadline_exceeded - RPCConnectRPCErrorCodeDeadlineExceeded = RPCConnectRPCErrorCodeKey.String("deadline_exceeded") - // not_found - RPCConnectRPCErrorCodeNotFound = RPCConnectRPCErrorCodeKey.String("not_found") - // already_exists - RPCConnectRPCErrorCodeAlreadyExists = RPCConnectRPCErrorCodeKey.String("already_exists") - // permission_denied - RPCConnectRPCErrorCodePermissionDenied = RPCConnectRPCErrorCodeKey.String("permission_denied") - // resource_exhausted - RPCConnectRPCErrorCodeResourceExhausted = RPCConnectRPCErrorCodeKey.String("resource_exhausted") - // failed_precondition - RPCConnectRPCErrorCodeFailedPrecondition = RPCConnectRPCErrorCodeKey.String("failed_precondition") - // aborted - RPCConnectRPCErrorCodeAborted = RPCConnectRPCErrorCodeKey.String("aborted") - // out_of_range - RPCConnectRPCErrorCodeOutOfRange = RPCConnectRPCErrorCodeKey.String("out_of_range") - // unimplemented - RPCConnectRPCErrorCodeUnimplemented = RPCConnectRPCErrorCodeKey.String("unimplemented") - // internal - RPCConnectRPCErrorCodeInternal = RPCConnectRPCErrorCodeKey.String("internal") - // unavailable - RPCConnectRPCErrorCodeUnavailable = RPCConnectRPCErrorCodeKey.String("unavailable") - // data_loss - RPCConnectRPCErrorCodeDataLoss = RPCConnectRPCErrorCodeKey.String("data_loss") - // unauthenticated - RPCConnectRPCErrorCodeUnauthenticated = RPCConnectRPCErrorCodeKey.String("unauthenticated") -) - -var ( - // OK - RPCGRPCStatusCodeOk = RPCGRPCStatusCodeKey.Int(0) - // CANCELLED - RPCGRPCStatusCodeCancelled = RPCGRPCStatusCodeKey.Int(1) - // UNKNOWN - RPCGRPCStatusCodeUnknown = RPCGRPCStatusCodeKey.Int(2) - // INVALID_ARGUMENT - RPCGRPCStatusCodeInvalidArgument = RPCGRPCStatusCodeKey.Int(3) - // DEADLINE_EXCEEDED - RPCGRPCStatusCodeDeadlineExceeded = RPCGRPCStatusCodeKey.Int(4) - // NOT_FOUND - RPCGRPCStatusCodeNotFound = RPCGRPCStatusCodeKey.Int(5) - // ALREADY_EXISTS - RPCGRPCStatusCodeAlreadyExists = RPCGRPCStatusCodeKey.Int(6) - // PERMISSION_DENIED - RPCGRPCStatusCodePermissionDenied = RPCGRPCStatusCodeKey.Int(7) - // RESOURCE_EXHAUSTED - RPCGRPCStatusCodeResourceExhausted = RPCGRPCStatusCodeKey.Int(8) - // FAILED_PRECONDITION - RPCGRPCStatusCodeFailedPrecondition = RPCGRPCStatusCodeKey.Int(9) - // ABORTED - RPCGRPCStatusCodeAborted = RPCGRPCStatusCodeKey.Int(10) - // OUT_OF_RANGE - RPCGRPCStatusCodeOutOfRange = RPCGRPCStatusCodeKey.Int(11) - // UNIMPLEMENTED - RPCGRPCStatusCodeUnimplemented = RPCGRPCStatusCodeKey.Int(12) - // INTERNAL - RPCGRPCStatusCodeInternal = RPCGRPCStatusCodeKey.Int(13) - // UNAVAILABLE - RPCGRPCStatusCodeUnavailable = RPCGRPCStatusCodeKey.Int(14) - // DATA_LOSS - RPCGRPCStatusCodeDataLoss = RPCGRPCStatusCodeKey.Int(15) - // UNAUTHENTICATED - RPCGRPCStatusCodeUnauthenticated = RPCGRPCStatusCodeKey.Int(16) -) - -var ( - // gRPC - RPCSystemGRPC = RPCSystemKey.String("grpc") - // Java RMI - RPCSystemJavaRmi = RPCSystemKey.String("java_rmi") - // .NET WCF - RPCSystemDotnetWcf = RPCSystemKey.String("dotnet_wcf") - // Apache Dubbo - RPCSystemApacheDubbo = RPCSystemKey.String("apache_dubbo") - // Connect RPC - RPCSystemConnectRPC = RPCSystemKey.String("connect_rpc") -) - -// RPCJsonrpcErrorCode returns an attribute KeyValue conforming to the -// "rpc.jsonrpc.error_code" semantic conventions. It represents the -// `error.code` property of response if it is an error response. -func RPCJsonrpcErrorCode(val int) attribute.KeyValue { - return RPCJsonrpcErrorCodeKey.Int(val) -} - -// RPCJsonrpcErrorMessage returns an attribute KeyValue conforming to the -// "rpc.jsonrpc.error_message" semantic conventions. It represents the -// `error.message` property of response if it is an error response. -func RPCJsonrpcErrorMessage(val string) attribute.KeyValue { - return RPCJsonrpcErrorMessageKey.String(val) -} - -// RPCJsonrpcRequestID returns an attribute KeyValue conforming to the -// "rpc.jsonrpc.request_id" semantic conventions. It represents the `id` -// property of request or response. Since protocol allows id to be int, string, -// `null` or missing (for notifications), value is expected to be cast to -// string for simplicity. Use empty string in case of `null` value. Omit -// entirely if this is a notification. -func RPCJsonrpcRequestID(val string) attribute.KeyValue { - return RPCJsonrpcRequestIDKey.String(val) -} - -// RPCJsonrpcVersion returns an attribute KeyValue conforming to the -// "rpc.jsonrpc.version" semantic conventions. It represents the protocol -// version as in `jsonrpc` property of request/response. Since JSON-RPC 1.0 -// doesn't specify this, the value can be omitted. -func RPCJsonrpcVersion(val string) attribute.KeyValue { - return RPCJsonrpcVersionKey.String(val) -} - -// RPCMethod returns an attribute KeyValue conforming to the "rpc.method" -// semantic conventions. It represents the name of the (logical) method being -// called, must be equal to the $method part in the span name. -func RPCMethod(val string) attribute.KeyValue { - return RPCMethodKey.String(val) -} - -// RPCService returns an attribute KeyValue conforming to the "rpc.service" -// semantic conventions. It represents the full (logical) name of the service -// being called, including its package name, if applicable. -func RPCService(val string) attribute.KeyValue { - return RPCServiceKey.String(val) -} - -// These attributes may be used to describe the server in a connection-based -// network interaction where there is one side that initiates the connection -// (the client is the side that initiates the connection). This covers all TCP -// network interactions since TCP is connection-based and one side initiates -// the connection (an exception is made for peer-to-peer communication over TCP -// where the "user-facing" surface of the protocol / API doesn't expose a clear -// notion of client and server). This also covers UDP network interactions -// where one side initiates the interaction, e.g. QUIC (HTTP/3) and DNS. -const ( - // ServerAddressKey is the attribute Key conforming to the "server.address" - // semantic conventions. It represents the server domain name if available - // without reverse DNS lookup; otherwise, IP address or Unix domain socket - // name. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'example.com', '10.1.2.80', '/tmp/my.sock' - // Note: When observed from the client side, and when communicating through - // an intermediary, `server.address` SHOULD represent the server address - // behind any intermediaries, for example proxies, if it's available. - ServerAddressKey = attribute.Key("server.address") - - // ServerPortKey is the attribute Key conforming to the "server.port" - // semantic conventions. It represents the server port number. - // - // Type: int - // RequirementLevel: Optional - // Stability: stable - // Examples: 80, 8080, 443 - // Note: When observed from the client side, and when communicating through - // an intermediary, `server.port` SHOULD represent the server port behind - // any intermediaries, for example proxies, if it's available. - ServerPortKey = attribute.Key("server.port") -) - -// ServerAddress returns an attribute KeyValue conforming to the -// "server.address" semantic conventions. It represents the server domain name -// if available without reverse DNS lookup; otherwise, IP address or Unix -// domain socket name. -func ServerAddress(val string) attribute.KeyValue { - return ServerAddressKey.String(val) -} - -// ServerPort returns an attribute KeyValue conforming to the "server.port" -// semantic conventions. It represents the server port number. -func ServerPort(val int) attribute.KeyValue { - return ServerPortKey.Int(val) -} - -// These attributes may be used to describe the sender of a network -// exchange/packet. These should be used when there is no client/server -// relationship between the two sides, or when that relationship is unknown. -// This covers low-level network interactions (e.g. packet tracing) where you -// don't know if there was a connection or which side initiated it. This also -// covers unidirectional UDP flows and peer-to-peer communication where the -// "user-facing" surface of the protocol / API doesn't expose a clear notion of -// client and server. -const ( - // SourceAddressKey is the attribute Key conforming to the "source.address" - // semantic conventions. It represents the source address - domain name if - // available without reverse DNS lookup; otherwise, IP address or Unix - // domain socket name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'source.example.com', '10.1.2.80', '/tmp/my.sock' - // Note: When observed from the destination side, and when communicating - // through an intermediary, `source.address` SHOULD represent the source - // address behind any intermediaries, for example proxies, if it's - // available. - SourceAddressKey = attribute.Key("source.address") - - // SourcePortKey is the attribute Key conforming to the "source.port" - // semantic conventions. It represents the source port number - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 3389, 2888 - SourcePortKey = attribute.Key("source.port") -) - -// SourceAddress returns an attribute KeyValue conforming to the -// "source.address" semantic conventions. It represents the source address - -// domain name if available without reverse DNS lookup; otherwise, IP address -// or Unix domain socket name. -func SourceAddress(val string) attribute.KeyValue { - return SourceAddressKey.String(val) -} - -// SourcePort returns an attribute KeyValue conforming to the "source.port" -// semantic conventions. It represents the source port number -func SourcePort(val int) attribute.KeyValue { - return SourcePortKey.Int(val) -} - -// Semantic convention attributes in the TLS namespace. -const ( - // TLSCipherKey is the attribute Key conforming to the "tls.cipher" - // semantic conventions. It represents the string indicating the - // [cipher](https://datatracker.ietf.org/doc/html/rfc5246#appendix-A.5) - // used during the current connection. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'TLS_RSA_WITH_3DES_EDE_CBC_SHA', - // 'TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256' - // Note: The values allowed for `tls.cipher` MUST be one of the - // `Descriptions` of the [registered TLS Cipher - // Suits](https://www.iana.org/assignments/tls-parameters/tls-parameters.xhtml#table-tls-parameters-4). - TLSCipherKey = attribute.Key("tls.cipher") - - // TLSClientCertificateKey is the attribute Key conforming to the - // "tls.client.certificate" semantic conventions. It represents the - // pEM-encoded stand-alone certificate offered by the client. This is - // usually mutually-exclusive of `client.certificate_chain` since this - // value also exists in that list. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MII...' - TLSClientCertificateKey = attribute.Key("tls.client.certificate") - - // TLSClientCertificateChainKey is the attribute Key conforming to the - // "tls.client.certificate_chain" semantic conventions. It represents the - // array of PEM-encoded certificates that make up the certificate chain - // offered by the client. This is usually mutually-exclusive of - // `client.certificate` since that value should be the first certificate in - // the chain. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MII...', 'MI...' - TLSClientCertificateChainKey = attribute.Key("tls.client.certificate_chain") - - // TLSClientHashMd5Key is the attribute Key conforming to the - // "tls.client.hash.md5" semantic conventions. It represents the - // certificate fingerprint using the MD5 digest of DER-encoded version of - // certificate offered by the client. For consistency with other hash - // values, this value should be formatted as an uppercase hash. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '0F76C7F2C55BFD7D8E8B8F4BFBF0C9EC' - TLSClientHashMd5Key = attribute.Key("tls.client.hash.md5") - - // TLSClientHashSha1Key is the attribute Key conforming to the - // "tls.client.hash.sha1" semantic conventions. It represents the - // certificate fingerprint using the SHA1 digest of DER-encoded version of - // certificate offered by the client. For consistency with other hash - // values, this value should be formatted as an uppercase hash. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '9E393D93138888D288266C2D915214D1D1CCEB2A' - TLSClientHashSha1Key = attribute.Key("tls.client.hash.sha1") - - // TLSClientHashSha256Key is the attribute Key conforming to the - // "tls.client.hash.sha256" semantic conventions. It represents the - // certificate fingerprint using the SHA256 digest of DER-encoded version - // of certificate offered by the client. For consistency with other hash - // values, this value should be formatted as an uppercase hash. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // '0687F666A054EF17A08E2F2162EAB4CBC0D265E1D7875BE74BF3C712CA92DAF0' - TLSClientHashSha256Key = attribute.Key("tls.client.hash.sha256") - - // TLSClientIssuerKey is the attribute Key conforming to the - // "tls.client.issuer" semantic conventions. It represents the - // distinguished name of - // [subject](https://datatracker.ietf.org/doc/html/rfc5280#section-4.1.2.6) - // of the issuer of the x.509 certificate presented by the client. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'CN=Example Root CA, OU=Infrastructure Team, DC=example, - // DC=com' - TLSClientIssuerKey = attribute.Key("tls.client.issuer") - - // TLSClientJa3Key is the attribute Key conforming to the "tls.client.ja3" - // semantic conventions. It represents a hash that identifies clients based - // on how they perform an SSL/TLS handshake. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'd4e5b18d6b55c71272893221c96ba240' - TLSClientJa3Key = attribute.Key("tls.client.ja3") - - // TLSClientNotAfterKey is the attribute Key conforming to the - // "tls.client.not_after" semantic conventions. It represents the date/Time - // indicating when client certificate is no longer considered valid. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2021-01-01T00:00:00.000Z' - TLSClientNotAfterKey = attribute.Key("tls.client.not_after") - - // TLSClientNotBeforeKey is the attribute Key conforming to the - // "tls.client.not_before" semantic conventions. It represents the - // date/Time indicating when client certificate is first considered valid. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1970-01-01T00:00:00.000Z' - TLSClientNotBeforeKey = attribute.Key("tls.client.not_before") - - // TLSClientServerNameKey is the attribute Key conforming to the - // "tls.client.server_name" semantic conventions. It represents the also - // called an SNI, this tells the server which hostname to which the client - // is attempting to connect to. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry.io' - TLSClientServerNameKey = attribute.Key("tls.client.server_name") - - // TLSClientSubjectKey is the attribute Key conforming to the - // "tls.client.subject" semantic conventions. It represents the - // distinguished name of subject of the x.509 certificate presented by the - // client. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'CN=myclient, OU=Documentation Team, DC=example, DC=com' - TLSClientSubjectKey = attribute.Key("tls.client.subject") - - // TLSClientSupportedCiphersKey is the attribute Key conforming to the - // "tls.client.supported_ciphers" semantic conventions. It represents the - // array of ciphers offered by the client during the client hello. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '"TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384", - // "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384", "..."' - TLSClientSupportedCiphersKey = attribute.Key("tls.client.supported_ciphers") - - // TLSCurveKey is the attribute Key conforming to the "tls.curve" semantic - // conventions. It represents the string indicating the curve used for the - // given cipher, when applicable - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'secp256r1' - TLSCurveKey = attribute.Key("tls.curve") - - // TLSEstablishedKey is the attribute Key conforming to the - // "tls.established" semantic conventions. It represents the boolean flag - // indicating if the TLS negotiation was successful and transitioned to an - // encrypted tunnel. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - // Examples: True - TLSEstablishedKey = attribute.Key("tls.established") - - // TLSNextProtocolKey is the attribute Key conforming to the - // "tls.next_protocol" semantic conventions. It represents the string - // indicating the protocol being tunneled. Per the values in the [IANA - // registry](https://www.iana.org/assignments/tls-extensiontype-values/tls-extensiontype-values.xhtml#alpn-protocol-ids), - // this string should be lower case. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'http/1.1' - TLSNextProtocolKey = attribute.Key("tls.next_protocol") - - // TLSProtocolNameKey is the attribute Key conforming to the - // "tls.protocol.name" semantic conventions. It represents the normalized - // lowercase protocol name parsed from original string of the negotiated - // [SSL/TLS protocol - // version](https://www.openssl.org/docs/man1.1.1/man3/SSL_get_version.html#RETURN-VALUES) - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - TLSProtocolNameKey = attribute.Key("tls.protocol.name") - - // TLSProtocolVersionKey is the attribute Key conforming to the - // "tls.protocol.version" semantic conventions. It represents the numeric - // part of the version parsed from the original string of the negotiated - // [SSL/TLS protocol - // version](https://www.openssl.org/docs/man1.1.1/man3/SSL_get_version.html#RETURN-VALUES) - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1.2', '3' - TLSProtocolVersionKey = attribute.Key("tls.protocol.version") - - // TLSResumedKey is the attribute Key conforming to the "tls.resumed" - // semantic conventions. It represents the boolean flag indicating if this - // TLS connection was resumed from an existing TLS negotiation. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - // Examples: True - TLSResumedKey = attribute.Key("tls.resumed") - - // TLSServerCertificateKey is the attribute Key conforming to the - // "tls.server.certificate" semantic conventions. It represents the - // pEM-encoded stand-alone certificate offered by the server. This is - // usually mutually-exclusive of `server.certificate_chain` since this - // value also exists in that list. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MII...' - TLSServerCertificateKey = attribute.Key("tls.server.certificate") - - // TLSServerCertificateChainKey is the attribute Key conforming to the - // "tls.server.certificate_chain" semantic conventions. It represents the - // array of PEM-encoded certificates that make up the certificate chain - // offered by the server. This is usually mutually-exclusive of - // `server.certificate` since that value should be the first certificate in - // the chain. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'MII...', 'MI...' - TLSServerCertificateChainKey = attribute.Key("tls.server.certificate_chain") - - // TLSServerHashMd5Key is the attribute Key conforming to the - // "tls.server.hash.md5" semantic conventions. It represents the - // certificate fingerprint using the MD5 digest of DER-encoded version of - // certificate offered by the server. For consistency with other hash - // values, this value should be formatted as an uppercase hash. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '0F76C7F2C55BFD7D8E8B8F4BFBF0C9EC' - TLSServerHashMd5Key = attribute.Key("tls.server.hash.md5") - - // TLSServerHashSha1Key is the attribute Key conforming to the - // "tls.server.hash.sha1" semantic conventions. It represents the - // certificate fingerprint using the SHA1 digest of DER-encoded version of - // certificate offered by the server. For consistency with other hash - // values, this value should be formatted as an uppercase hash. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '9E393D93138888D288266C2D915214D1D1CCEB2A' - TLSServerHashSha1Key = attribute.Key("tls.server.hash.sha1") - - // TLSServerHashSha256Key is the attribute Key conforming to the - // "tls.server.hash.sha256" semantic conventions. It represents the - // certificate fingerprint using the SHA256 digest of DER-encoded version - // of certificate offered by the server. For consistency with other hash - // values, this value should be formatted as an uppercase hash. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // '0687F666A054EF17A08E2F2162EAB4CBC0D265E1D7875BE74BF3C712CA92DAF0' - TLSServerHashSha256Key = attribute.Key("tls.server.hash.sha256") - - // TLSServerIssuerKey is the attribute Key conforming to the - // "tls.server.issuer" semantic conventions. It represents the - // distinguished name of - // [subject](https://datatracker.ietf.org/doc/html/rfc5280#section-4.1.2.6) - // of the issuer of the x.509 certificate presented by the client. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'CN=Example Root CA, OU=Infrastructure Team, DC=example, - // DC=com' - TLSServerIssuerKey = attribute.Key("tls.server.issuer") - - // TLSServerJa3sKey is the attribute Key conforming to the - // "tls.server.ja3s" semantic conventions. It represents a hash that - // identifies servers based on how they perform an SSL/TLS handshake. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'd4e5b18d6b55c71272893221c96ba240' - TLSServerJa3sKey = attribute.Key("tls.server.ja3s") - - // TLSServerNotAfterKey is the attribute Key conforming to the - // "tls.server.not_after" semantic conventions. It represents the date/Time - // indicating when server certificate is no longer considered valid. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2021-01-01T00:00:00.000Z' - TLSServerNotAfterKey = attribute.Key("tls.server.not_after") - - // TLSServerNotBeforeKey is the attribute Key conforming to the - // "tls.server.not_before" semantic conventions. It represents the - // date/Time indicating when server certificate is first considered valid. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1970-01-01T00:00:00.000Z' - TLSServerNotBeforeKey = attribute.Key("tls.server.not_before") - - // TLSServerSubjectKey is the attribute Key conforming to the - // "tls.server.subject" semantic conventions. It represents the - // distinguished name of subject of the x.509 certificate presented by the - // server. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'CN=myserver, OU=Documentation Team, DC=example, DC=com' - TLSServerSubjectKey = attribute.Key("tls.server.subject") -) - -var ( - // ssl - TLSProtocolNameSsl = TLSProtocolNameKey.String("ssl") - // tls - TLSProtocolNameTLS = TLSProtocolNameKey.String("tls") -) - -// TLSCipher returns an attribute KeyValue conforming to the "tls.cipher" -// semantic conventions. It represents the string indicating the -// [cipher](https://datatracker.ietf.org/doc/html/rfc5246#appendix-A.5) used -// during the current connection. -func TLSCipher(val string) attribute.KeyValue { - return TLSCipherKey.String(val) -} - -// TLSClientCertificate returns an attribute KeyValue conforming to the -// "tls.client.certificate" semantic conventions. It represents the pEM-encoded -// stand-alone certificate offered by the client. This is usually -// mutually-exclusive of `client.certificate_chain` since this value also -// exists in that list. -func TLSClientCertificate(val string) attribute.KeyValue { - return TLSClientCertificateKey.String(val) -} - -// TLSClientCertificateChain returns an attribute KeyValue conforming to the -// "tls.client.certificate_chain" semantic conventions. It represents the array -// of PEM-encoded certificates that make up the certificate chain offered by -// the client. This is usually mutually-exclusive of `client.certificate` since -// that value should be the first certificate in the chain. -func TLSClientCertificateChain(val ...string) attribute.KeyValue { - return TLSClientCertificateChainKey.StringSlice(val) -} - -// TLSClientHashMd5 returns an attribute KeyValue conforming to the -// "tls.client.hash.md5" semantic conventions. It represents the certificate -// fingerprint using the MD5 digest of DER-encoded version of certificate -// offered by the client. For consistency with other hash values, this value -// should be formatted as an uppercase hash. -func TLSClientHashMd5(val string) attribute.KeyValue { - return TLSClientHashMd5Key.String(val) -} - -// TLSClientHashSha1 returns an attribute KeyValue conforming to the -// "tls.client.hash.sha1" semantic conventions. It represents the certificate -// fingerprint using the SHA1 digest of DER-encoded version of certificate -// offered by the client. For consistency with other hash values, this value -// should be formatted as an uppercase hash. -func TLSClientHashSha1(val string) attribute.KeyValue { - return TLSClientHashSha1Key.String(val) -} - -// TLSClientHashSha256 returns an attribute KeyValue conforming to the -// "tls.client.hash.sha256" semantic conventions. It represents the certificate -// fingerprint using the SHA256 digest of DER-encoded version of certificate -// offered by the client. For consistency with other hash values, this value -// should be formatted as an uppercase hash. -func TLSClientHashSha256(val string) attribute.KeyValue { - return TLSClientHashSha256Key.String(val) -} - -// TLSClientIssuer returns an attribute KeyValue conforming to the -// "tls.client.issuer" semantic conventions. It represents the distinguished -// name of -// [subject](https://datatracker.ietf.org/doc/html/rfc5280#section-4.1.2.6) of -// the issuer of the x.509 certificate presented by the client. -func TLSClientIssuer(val string) attribute.KeyValue { - return TLSClientIssuerKey.String(val) -} - -// TLSClientJa3 returns an attribute KeyValue conforming to the -// "tls.client.ja3" semantic conventions. It represents a hash that identifies -// clients based on how they perform an SSL/TLS handshake. -func TLSClientJa3(val string) attribute.KeyValue { - return TLSClientJa3Key.String(val) -} - -// TLSClientNotAfter returns an attribute KeyValue conforming to the -// "tls.client.not_after" semantic conventions. It represents the date/Time -// indicating when client certificate is no longer considered valid. -func TLSClientNotAfter(val string) attribute.KeyValue { - return TLSClientNotAfterKey.String(val) -} - -// TLSClientNotBefore returns an attribute KeyValue conforming to the -// "tls.client.not_before" semantic conventions. It represents the date/Time -// indicating when client certificate is first considered valid. -func TLSClientNotBefore(val string) attribute.KeyValue { - return TLSClientNotBeforeKey.String(val) -} - -// TLSClientServerName returns an attribute KeyValue conforming to the -// "tls.client.server_name" semantic conventions. It represents the also called -// an SNI, this tells the server which hostname to which the client is -// attempting to connect to. -func TLSClientServerName(val string) attribute.KeyValue { - return TLSClientServerNameKey.String(val) -} - -// TLSClientSubject returns an attribute KeyValue conforming to the -// "tls.client.subject" semantic conventions. It represents the distinguished -// name of subject of the x.509 certificate presented by the client. -func TLSClientSubject(val string) attribute.KeyValue { - return TLSClientSubjectKey.String(val) -} - -// TLSClientSupportedCiphers returns an attribute KeyValue conforming to the -// "tls.client.supported_ciphers" semantic conventions. It represents the array -// of ciphers offered by the client during the client hello. -func TLSClientSupportedCiphers(val ...string) attribute.KeyValue { - return TLSClientSupportedCiphersKey.StringSlice(val) -} - -// TLSCurve returns an attribute KeyValue conforming to the "tls.curve" -// semantic conventions. It represents the string indicating the curve used for -// the given cipher, when applicable -func TLSCurve(val string) attribute.KeyValue { - return TLSCurveKey.String(val) -} - -// TLSEstablished returns an attribute KeyValue conforming to the -// "tls.established" semantic conventions. It represents the boolean flag -// indicating if the TLS negotiation was successful and transitioned to an -// encrypted tunnel. -func TLSEstablished(val bool) attribute.KeyValue { - return TLSEstablishedKey.Bool(val) -} - -// TLSNextProtocol returns an attribute KeyValue conforming to the -// "tls.next_protocol" semantic conventions. It represents the string -// indicating the protocol being tunneled. Per the values in the [IANA -// registry](https://www.iana.org/assignments/tls-extensiontype-values/tls-extensiontype-values.xhtml#alpn-protocol-ids), -// this string should be lower case. -func TLSNextProtocol(val string) attribute.KeyValue { - return TLSNextProtocolKey.String(val) -} - -// TLSProtocolVersion returns an attribute KeyValue conforming to the -// "tls.protocol.version" semantic conventions. It represents the numeric part -// of the version parsed from the original string of the negotiated [SSL/TLS -// protocol -// version](https://www.openssl.org/docs/man1.1.1/man3/SSL_get_version.html#RETURN-VALUES) -func TLSProtocolVersion(val string) attribute.KeyValue { - return TLSProtocolVersionKey.String(val) -} - -// TLSResumed returns an attribute KeyValue conforming to the "tls.resumed" -// semantic conventions. It represents the boolean flag indicating if this TLS -// connection was resumed from an existing TLS negotiation. -func TLSResumed(val bool) attribute.KeyValue { - return TLSResumedKey.Bool(val) -} - -// TLSServerCertificate returns an attribute KeyValue conforming to the -// "tls.server.certificate" semantic conventions. It represents the pEM-encoded -// stand-alone certificate offered by the server. This is usually -// mutually-exclusive of `server.certificate_chain` since this value also -// exists in that list. -func TLSServerCertificate(val string) attribute.KeyValue { - return TLSServerCertificateKey.String(val) -} - -// TLSServerCertificateChain returns an attribute KeyValue conforming to the -// "tls.server.certificate_chain" semantic conventions. It represents the array -// of PEM-encoded certificates that make up the certificate chain offered by -// the server. This is usually mutually-exclusive of `server.certificate` since -// that value should be the first certificate in the chain. -func TLSServerCertificateChain(val ...string) attribute.KeyValue { - return TLSServerCertificateChainKey.StringSlice(val) -} - -// TLSServerHashMd5 returns an attribute KeyValue conforming to the -// "tls.server.hash.md5" semantic conventions. It represents the certificate -// fingerprint using the MD5 digest of DER-encoded version of certificate -// offered by the server. For consistency with other hash values, this value -// should be formatted as an uppercase hash. -func TLSServerHashMd5(val string) attribute.KeyValue { - return TLSServerHashMd5Key.String(val) -} - -// TLSServerHashSha1 returns an attribute KeyValue conforming to the -// "tls.server.hash.sha1" semantic conventions. It represents the certificate -// fingerprint using the SHA1 digest of DER-encoded version of certificate -// offered by the server. For consistency with other hash values, this value -// should be formatted as an uppercase hash. -func TLSServerHashSha1(val string) attribute.KeyValue { - return TLSServerHashSha1Key.String(val) -} - -// TLSServerHashSha256 returns an attribute KeyValue conforming to the -// "tls.server.hash.sha256" semantic conventions. It represents the certificate -// fingerprint using the SHA256 digest of DER-encoded version of certificate -// offered by the server. For consistency with other hash values, this value -// should be formatted as an uppercase hash. -func TLSServerHashSha256(val string) attribute.KeyValue { - return TLSServerHashSha256Key.String(val) -} - -// TLSServerIssuer returns an attribute KeyValue conforming to the -// "tls.server.issuer" semantic conventions. It represents the distinguished -// name of -// [subject](https://datatracker.ietf.org/doc/html/rfc5280#section-4.1.2.6) of -// the issuer of the x.509 certificate presented by the client. -func TLSServerIssuer(val string) attribute.KeyValue { - return TLSServerIssuerKey.String(val) -} - -// TLSServerJa3s returns an attribute KeyValue conforming to the -// "tls.server.ja3s" semantic conventions. It represents a hash that identifies -// servers based on how they perform an SSL/TLS handshake. -func TLSServerJa3s(val string) attribute.KeyValue { - return TLSServerJa3sKey.String(val) -} - -// TLSServerNotAfter returns an attribute KeyValue conforming to the -// "tls.server.not_after" semantic conventions. It represents the date/Time -// indicating when server certificate is no longer considered valid. -func TLSServerNotAfter(val string) attribute.KeyValue { - return TLSServerNotAfterKey.String(val) -} - -// TLSServerNotBefore returns an attribute KeyValue conforming to the -// "tls.server.not_before" semantic conventions. It represents the date/Time -// indicating when server certificate is first considered valid. -func TLSServerNotBefore(val string) attribute.KeyValue { - return TLSServerNotBeforeKey.String(val) -} - -// TLSServerSubject returns an attribute KeyValue conforming to the -// "tls.server.subject" semantic conventions. It represents the distinguished -// name of subject of the x.509 certificate presented by the server. -func TLSServerSubject(val string) attribute.KeyValue { - return TLSServerSubjectKey.String(val) -} - -// Attributes describing URL. -const ( - // URLFragmentKey is the attribute Key conforming to the "url.fragment" - // semantic conventions. It represents the [URI - // fragment](https://www.rfc-editor.org/rfc/rfc3986#section-3.5) component - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'SemConv' - URLFragmentKey = attribute.Key("url.fragment") - - // URLFullKey is the attribute Key conforming to the "url.full" semantic - // conventions. It represents the absolute URL describing a network - // resource according to [RFC3986](https://www.rfc-editor.org/rfc/rfc3986) - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'https://www.foo.bar/search?q=OpenTelemetry#SemConv', - // '//localhost' - // Note: For network calls, URL usually has - // `scheme://host[:port][path][?query][#fragment]` format, where the - // fragment is not transmitted over HTTP, but if it is known, it SHOULD be - // included nevertheless. - // `url.full` MUST NOT contain credentials passed via URL in form of - // `https://username:password@www.example.com/`. In such case username and - // password SHOULD be redacted and attribute's value SHOULD be - // `https://REDACTED:REDACTED@www.example.com/`. - // `url.full` SHOULD capture the absolute URL when it is available (or can - // be reconstructed) and SHOULD NOT be validated or modified except for - // sanitizing purposes. - URLFullKey = attribute.Key("url.full") - - // URLPathKey is the attribute Key conforming to the "url.path" semantic - // conventions. It represents the [URI - // path](https://www.rfc-editor.org/rfc/rfc3986#section-3.3) component - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: '/search' - URLPathKey = attribute.Key("url.path") - - // URLQueryKey is the attribute Key conforming to the "url.query" semantic - // conventions. It represents the [URI - // query](https://www.rfc-editor.org/rfc/rfc3986#section-3.4) component - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'q=OpenTelemetry' - // Note: Sensitive content provided in query string SHOULD be scrubbed when - // instrumentations can identify it. - URLQueryKey = attribute.Key("url.query") - - // URLSchemeKey is the attribute Key conforming to the "url.scheme" - // semantic conventions. It represents the [URI - // scheme](https://www.rfc-editor.org/rfc/rfc3986#section-3.1) component - // identifying the used protocol. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'https', 'ftp', 'telnet' - URLSchemeKey = attribute.Key("url.scheme") -) - -// URLFragment returns an attribute KeyValue conforming to the -// "url.fragment" semantic conventions. It represents the [URI -// fragment](https://www.rfc-editor.org/rfc/rfc3986#section-3.5) component -func URLFragment(val string) attribute.KeyValue { - return URLFragmentKey.String(val) -} - -// URLFull returns an attribute KeyValue conforming to the "url.full" -// semantic conventions. It represents the absolute URL describing a network -// resource according to [RFC3986](https://www.rfc-editor.org/rfc/rfc3986) -func URLFull(val string) attribute.KeyValue { - return URLFullKey.String(val) -} - -// URLPath returns an attribute KeyValue conforming to the "url.path" -// semantic conventions. It represents the [URI -// path](https://www.rfc-editor.org/rfc/rfc3986#section-3.3) component -func URLPath(val string) attribute.KeyValue { - return URLPathKey.String(val) -} - -// URLQuery returns an attribute KeyValue conforming to the "url.query" -// semantic conventions. It represents the [URI -// query](https://www.rfc-editor.org/rfc/rfc3986#section-3.4) component -func URLQuery(val string) attribute.KeyValue { - return URLQueryKey.String(val) -} - -// URLScheme returns an attribute KeyValue conforming to the "url.scheme" -// semantic conventions. It represents the [URI -// scheme](https://www.rfc-editor.org/rfc/rfc3986#section-3.1) component -// identifying the used protocol. -func URLScheme(val string) attribute.KeyValue { - return URLSchemeKey.String(val) -} - -// Describes user-agent attributes. -const ( - // UserAgentOriginalKey is the attribute Key conforming to the - // "user_agent.original" semantic conventions. It represents the value of - // the [HTTP - // User-Agent](https://www.rfc-editor.org/rfc/rfc9110.html#field.user-agent) - // header sent by the client. - // - // Type: string - // RequirementLevel: Optional - // Stability: stable - // Examples: 'CERN-LineMode/2.15 libwww/2.17b3', 'Mozilla/5.0 (iPhone; CPU - // iPhone OS 14_7_1 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) - // Version/14.1.2 Mobile/15E148 Safari/604.1' - UserAgentOriginalKey = attribute.Key("user_agent.original") -) - -// UserAgentOriginal returns an attribute KeyValue conforming to the -// "user_agent.original" semantic conventions. It represents the value of the -// [HTTP -// User-Agent](https://www.rfc-editor.org/rfc/rfc9110.html#field.user-agent) -// header sent by the client. -func UserAgentOriginal(val string) attribute.KeyValue { - return UserAgentOriginalKey.String(val) -} - -// Session is defined as the period of time encompassing all activities -// performed by the application and the actions executed by the end user. -// Consequently, a Session is represented as a collection of Logs, Events, and -// Spans emitted by the Client Application throughout the Session's duration. -// Each Session is assigned a unique identifier, which is included as an -// attribute in the Logs, Events, and Spans generated during the Session's -// lifecycle. -// When a session reaches end of life, typically due to user inactivity or -// session timeout, a new session identifier will be assigned. The previous -// session identifier may be provided by the instrumentation so that telemetry -// backends can link the two sessions. -const ( - // SessionIDKey is the attribute Key conforming to the "session.id" - // semantic conventions. It represents a unique id to identify a session. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '00112233-4455-6677-8899-aabbccddeeff' - SessionIDKey = attribute.Key("session.id") - - // SessionPreviousIDKey is the attribute Key conforming to the - // "session.previous_id" semantic conventions. It represents the previous - // `session.id` for this user, when known. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '00112233-4455-6677-8899-aabbccddeeff' - SessionPreviousIDKey = attribute.Key("session.previous_id") -) - -// SessionID returns an attribute KeyValue conforming to the "session.id" -// semantic conventions. It represents a unique id to identify a session. -func SessionID(val string) attribute.KeyValue { - return SessionIDKey.String(val) -} - -// SessionPreviousID returns an attribute KeyValue conforming to the -// "session.previous_id" semantic conventions. It represents the previous -// `session.id` for this user, when known. -func SessionPreviousID(val string) attribute.KeyValue { - return SessionPreviousIDKey.String(val) -} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/doc.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/doc.go deleted file mode 100644 index d27e8a8f8b3..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/doc.go +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -// Package semconv implements OpenTelemetry semantic conventions. -// -// OpenTelemetry semantic conventions are agreed standardized naming -// patterns for OpenTelemetry things. This package represents the v1.24.0 -// version of the OpenTelemetry semantic conventions. -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/event.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/event.go deleted file mode 100644 index 6c019aafc3e..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/event.go +++ /dev/null @@ -1,200 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -// Code generated from semantic convention specification. DO NOT EDIT. - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -import "go.opentelemetry.io/otel/attribute" - -// This event represents an occurrence of a lifecycle transition on the iOS -// platform. -const ( - // IosStateKey is the attribute Key conforming to the "ios.state" semantic - // conventions. It represents the this attribute represents the state the - // application has transitioned into at the occurrence of the event. - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - // Note: The iOS lifecycle states are defined in the [UIApplicationDelegate - // documentation](https://developer.apple.com/documentation/uikit/uiapplicationdelegate#1656902), - // and from which the `OS terminology` column values are derived. - IosStateKey = attribute.Key("ios.state") -) - -var ( - // The app has become `active`. Associated with UIKit notification `applicationDidBecomeActive` - IosStateActive = IosStateKey.String("active") - // The app is now `inactive`. Associated with UIKit notification `applicationWillResignActive` - IosStateInactive = IosStateKey.String("inactive") - // The app is now in the background. This value is associated with UIKit notification `applicationDidEnterBackground` - IosStateBackground = IosStateKey.String("background") - // The app is now in the foreground. This value is associated with UIKit notification `applicationWillEnterForeground` - IosStateForeground = IosStateKey.String("foreground") - // The app is about to terminate. Associated with UIKit notification `applicationWillTerminate` - IosStateTerminate = IosStateKey.String("terminate") -) - -// This event represents an occurrence of a lifecycle transition on the Android -// platform. -const ( - // AndroidStateKey is the attribute Key conforming to the "android.state" - // semantic conventions. It represents the this attribute represents the - // state the application has transitioned into at the occurrence of the - // event. - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - // Note: The Android lifecycle states are defined in [Activity lifecycle - // callbacks](https://developer.android.com/guide/components/activities/activity-lifecycle#lc), - // and from which the `OS identifiers` are derived. - AndroidStateKey = attribute.Key("android.state") -) - -var ( - // Any time before Activity.onResume() or, if the app has no Activity, Context.startService() has been called in the app for the first time - AndroidStateCreated = AndroidStateKey.String("created") - // Any time after Activity.onPause() or, if the app has no Activity, Context.stopService() has been called when the app was in the foreground state - AndroidStateBackground = AndroidStateKey.String("background") - // Any time after Activity.onResume() or, if the app has no Activity, Context.startService() has been called when the app was in either the created or background states - AndroidStateForeground = AndroidStateKey.String("foreground") -) - -// This semantic convention defines the attributes used to represent a feature -// flag evaluation as an event. -const ( - // FeatureFlagKeyKey is the attribute Key conforming to the - // "feature_flag.key" semantic conventions. It represents the unique - // identifier of the feature flag. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'logo-color' - FeatureFlagKeyKey = attribute.Key("feature_flag.key") - - // FeatureFlagProviderNameKey is the attribute Key conforming to the - // "feature_flag.provider_name" semantic conventions. It represents the - // name of the service provider that performs the flag evaluation. - // - // Type: string - // RequirementLevel: Recommended - // Stability: experimental - // Examples: 'Flag Manager' - FeatureFlagProviderNameKey = attribute.Key("feature_flag.provider_name") - - // FeatureFlagVariantKey is the attribute Key conforming to the - // "feature_flag.variant" semantic conventions. It represents the sHOULD be - // a semantic identifier for a value. If one is unavailable, a stringified - // version of the value can be used. - // - // Type: string - // RequirementLevel: Recommended - // Stability: experimental - // Examples: 'red', 'true', 'on' - // Note: A semantic identifier, commonly referred to as a variant, provides - // a means - // for referring to a value without including the value itself. This can - // provide additional context for understanding the meaning behind a value. - // For example, the variant `red` maybe be used for the value `#c05543`. - // - // A stringified version of the value can be used in situations where a - // semantic identifier is unavailable. String representation of the value - // should be determined by the implementer. - FeatureFlagVariantKey = attribute.Key("feature_flag.variant") -) - -// FeatureFlagKey returns an attribute KeyValue conforming to the -// "feature_flag.key" semantic conventions. It represents the unique identifier -// of the feature flag. -func FeatureFlagKey(val string) attribute.KeyValue { - return FeatureFlagKeyKey.String(val) -} - -// FeatureFlagProviderName returns an attribute KeyValue conforming to the -// "feature_flag.provider_name" semantic conventions. It represents the name of -// the service provider that performs the flag evaluation. -func FeatureFlagProviderName(val string) attribute.KeyValue { - return FeatureFlagProviderNameKey.String(val) -} - -// FeatureFlagVariant returns an attribute KeyValue conforming to the -// "feature_flag.variant" semantic conventions. It represents the sHOULD be a -// semantic identifier for a value. If one is unavailable, a stringified -// version of the value can be used. -func FeatureFlagVariant(val string) attribute.KeyValue { - return FeatureFlagVariantKey.String(val) -} - -// RPC received/sent message. -const ( - // MessageCompressedSizeKey is the attribute Key conforming to the - // "message.compressed_size" semantic conventions. It represents the - // compressed size of the message in bytes. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - MessageCompressedSizeKey = attribute.Key("message.compressed_size") - - // MessageIDKey is the attribute Key conforming to the "message.id" - // semantic conventions. It represents the mUST be calculated as two - // different counters starting from `1` one for sent messages and one for - // received message. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Note: This way we guarantee that the values will be consistent between - // different implementations. - MessageIDKey = attribute.Key("message.id") - - // MessageTypeKey is the attribute Key conforming to the "message.type" - // semantic conventions. It represents the whether this is a received or - // sent message. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - MessageTypeKey = attribute.Key("message.type") - - // MessageUncompressedSizeKey is the attribute Key conforming to the - // "message.uncompressed_size" semantic conventions. It represents the - // uncompressed size of the message in bytes. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - MessageUncompressedSizeKey = attribute.Key("message.uncompressed_size") -) - -var ( - // sent - MessageTypeSent = MessageTypeKey.String("SENT") - // received - MessageTypeReceived = MessageTypeKey.String("RECEIVED") -) - -// MessageCompressedSize returns an attribute KeyValue conforming to the -// "message.compressed_size" semantic conventions. It represents the compressed -// size of the message in bytes. -func MessageCompressedSize(val int) attribute.KeyValue { - return MessageCompressedSizeKey.Int(val) -} - -// MessageID returns an attribute KeyValue conforming to the "message.id" -// semantic conventions. It represents the mUST be calculated as two different -// counters starting from `1` one for sent messages and one for received -// message. -func MessageID(val int) attribute.KeyValue { - return MessageIDKey.Int(val) -} - -// MessageUncompressedSize returns an attribute KeyValue conforming to the -// "message.uncompressed_size" semantic conventions. It represents the -// uncompressed size of the message in bytes. -func MessageUncompressedSize(val int) attribute.KeyValue { - return MessageUncompressedSizeKey.Int(val) -} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/exception.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/exception.go deleted file mode 100644 index 7235bb51d9a..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/exception.go +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -const ( - // ExceptionEventName is the name of the Span event representing an exception. - ExceptionEventName = "exception" -) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/metric.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/metric.go deleted file mode 100644 index a6b953f625e..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/metric.go +++ /dev/null @@ -1,1071 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -// Code generated from semantic convention specification. DO NOT EDIT. - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -const ( - - // DBClientConnectionsUsage is the metric conforming to the - // "db.client.connections.usage" semantic conventions. It represents the number - // of connections that are currently in state described by the `state` - // attribute. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - DBClientConnectionsUsageName = "db.client.connections.usage" - DBClientConnectionsUsageUnit = "{connection}" - DBClientConnectionsUsageDescription = "The number of connections that are currently in state described by the `state` attribute" - - // DBClientConnectionsIdleMax is the metric conforming to the - // "db.client.connections.idle.max" semantic conventions. It represents the - // maximum number of idle open connections allowed. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - DBClientConnectionsIdleMaxName = "db.client.connections.idle.max" - DBClientConnectionsIdleMaxUnit = "{connection}" - DBClientConnectionsIdleMaxDescription = "The maximum number of idle open connections allowed" - - // DBClientConnectionsIdleMin is the metric conforming to the - // "db.client.connections.idle.min" semantic conventions. It represents the - // minimum number of idle open connections allowed. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - DBClientConnectionsIdleMinName = "db.client.connections.idle.min" - DBClientConnectionsIdleMinUnit = "{connection}" - DBClientConnectionsIdleMinDescription = "The minimum number of idle open connections allowed" - - // DBClientConnectionsMax is the metric conforming to the - // "db.client.connections.max" semantic conventions. It represents the maximum - // number of open connections allowed. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - DBClientConnectionsMaxName = "db.client.connections.max" - DBClientConnectionsMaxUnit = "{connection}" - DBClientConnectionsMaxDescription = "The maximum number of open connections allowed" - - // DBClientConnectionsPendingRequests is the metric conforming to the - // "db.client.connections.pending_requests" semantic conventions. It represents - // the number of pending requests for an open connection, cumulative for the - // entire pool. - // Instrument: updowncounter - // Unit: {request} - // Stability: Experimental - DBClientConnectionsPendingRequestsName = "db.client.connections.pending_requests" - DBClientConnectionsPendingRequestsUnit = "{request}" - DBClientConnectionsPendingRequestsDescription = "The number of pending requests for an open connection, cumulative for the entire pool" - - // DBClientConnectionsTimeouts is the metric conforming to the - // "db.client.connections.timeouts" semantic conventions. It represents the - // number of connection timeouts that have occurred trying to obtain a - // connection from the pool. - // Instrument: counter - // Unit: {timeout} - // Stability: Experimental - DBClientConnectionsTimeoutsName = "db.client.connections.timeouts" - DBClientConnectionsTimeoutsUnit = "{timeout}" - DBClientConnectionsTimeoutsDescription = "The number of connection timeouts that have occurred trying to obtain a connection from the pool" - - // DBClientConnectionsCreateTime is the metric conforming to the - // "db.client.connections.create_time" semantic conventions. It represents the - // time it took to create a new connection. - // Instrument: histogram - // Unit: ms - // Stability: Experimental - DBClientConnectionsCreateTimeName = "db.client.connections.create_time" - DBClientConnectionsCreateTimeUnit = "ms" - DBClientConnectionsCreateTimeDescription = "The time it took to create a new connection" - - // DBClientConnectionsWaitTime is the metric conforming to the - // "db.client.connections.wait_time" semantic conventions. It represents the - // time it took to obtain an open connection from the pool. - // Instrument: histogram - // Unit: ms - // Stability: Experimental - DBClientConnectionsWaitTimeName = "db.client.connections.wait_time" - DBClientConnectionsWaitTimeUnit = "ms" - DBClientConnectionsWaitTimeDescription = "The time it took to obtain an open connection from the pool" - - // DBClientConnectionsUseTime is the metric conforming to the - // "db.client.connections.use_time" semantic conventions. It represents the - // time between borrowing a connection and returning it to the pool. - // Instrument: histogram - // Unit: ms - // Stability: Experimental - DBClientConnectionsUseTimeName = "db.client.connections.use_time" - DBClientConnectionsUseTimeUnit = "ms" - DBClientConnectionsUseTimeDescription = "The time between borrowing a connection and returning it to the pool" - - // AspnetcoreRoutingMatchAttempts is the metric conforming to the - // "aspnetcore.routing.match_attempts" semantic conventions. It represents the - // number of requests that were attempted to be matched to an endpoint. - // Instrument: counter - // Unit: {match_attempt} - // Stability: Experimental - AspnetcoreRoutingMatchAttemptsName = "aspnetcore.routing.match_attempts" - AspnetcoreRoutingMatchAttemptsUnit = "{match_attempt}" - AspnetcoreRoutingMatchAttemptsDescription = "Number of requests that were attempted to be matched to an endpoint." - - // AspnetcoreDiagnosticsExceptions is the metric conforming to the - // "aspnetcore.diagnostics.exceptions" semantic conventions. It represents the - // number of exceptions caught by exception handling middleware. - // Instrument: counter - // Unit: {exception} - // Stability: Experimental - AspnetcoreDiagnosticsExceptionsName = "aspnetcore.diagnostics.exceptions" - AspnetcoreDiagnosticsExceptionsUnit = "{exception}" - AspnetcoreDiagnosticsExceptionsDescription = "Number of exceptions caught by exception handling middleware." - - // AspnetcoreRateLimitingActiveRequestLeases is the metric conforming to the - // "aspnetcore.rate_limiting.active_request_leases" semantic conventions. It - // represents the number of requests that are currently active on the server - // that hold a rate limiting lease. - // Instrument: updowncounter - // Unit: {request} - // Stability: Experimental - AspnetcoreRateLimitingActiveRequestLeasesName = "aspnetcore.rate_limiting.active_request_leases" - AspnetcoreRateLimitingActiveRequestLeasesUnit = "{request}" - AspnetcoreRateLimitingActiveRequestLeasesDescription = "Number of requests that are currently active on the server that hold a rate limiting lease." - - // AspnetcoreRateLimitingRequestLeaseDuration is the metric conforming to the - // "aspnetcore.rate_limiting.request_lease.duration" semantic conventions. It - // represents the duration of rate limiting lease held by requests on the - // server. - // Instrument: histogram - // Unit: s - // Stability: Experimental - AspnetcoreRateLimitingRequestLeaseDurationName = "aspnetcore.rate_limiting.request_lease.duration" - AspnetcoreRateLimitingRequestLeaseDurationUnit = "s" - AspnetcoreRateLimitingRequestLeaseDurationDescription = "The duration of rate limiting lease held by requests on the server." - - // AspnetcoreRateLimitingRequestTimeInQueue is the metric conforming to the - // "aspnetcore.rate_limiting.request.time_in_queue" semantic conventions. It - // represents the time the request spent in a queue waiting to acquire a rate - // limiting lease. - // Instrument: histogram - // Unit: s - // Stability: Experimental - AspnetcoreRateLimitingRequestTimeInQueueName = "aspnetcore.rate_limiting.request.time_in_queue" - AspnetcoreRateLimitingRequestTimeInQueueUnit = "s" - AspnetcoreRateLimitingRequestTimeInQueueDescription = "The time the request spent in a queue waiting to acquire a rate limiting lease." - - // AspnetcoreRateLimitingQueuedRequests is the metric conforming to the - // "aspnetcore.rate_limiting.queued_requests" semantic conventions. It - // represents the number of requests that are currently queued, waiting to - // acquire a rate limiting lease. - // Instrument: updowncounter - // Unit: {request} - // Stability: Experimental - AspnetcoreRateLimitingQueuedRequestsName = "aspnetcore.rate_limiting.queued_requests" - AspnetcoreRateLimitingQueuedRequestsUnit = "{request}" - AspnetcoreRateLimitingQueuedRequestsDescription = "Number of requests that are currently queued, waiting to acquire a rate limiting lease." - - // AspnetcoreRateLimitingRequests is the metric conforming to the - // "aspnetcore.rate_limiting.requests" semantic conventions. It represents the - // number of requests that tried to acquire a rate limiting lease. - // Instrument: counter - // Unit: {request} - // Stability: Experimental - AspnetcoreRateLimitingRequestsName = "aspnetcore.rate_limiting.requests" - AspnetcoreRateLimitingRequestsUnit = "{request}" - AspnetcoreRateLimitingRequestsDescription = "Number of requests that tried to acquire a rate limiting lease." - - // DNSLookupDuration is the metric conforming to the "dns.lookup.duration" - // semantic conventions. It represents the measures the time taken to perform a - // DNS lookup. - // Instrument: histogram - // Unit: s - // Stability: Experimental - DNSLookupDurationName = "dns.lookup.duration" - DNSLookupDurationUnit = "s" - DNSLookupDurationDescription = "Measures the time taken to perform a DNS lookup." - - // HTTPClientOpenConnections is the metric conforming to the - // "http.client.open_connections" semantic conventions. It represents the - // number of outbound HTTP connections that are currently active or idle on the - // client. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - HTTPClientOpenConnectionsName = "http.client.open_connections" - HTTPClientOpenConnectionsUnit = "{connection}" - HTTPClientOpenConnectionsDescription = "Number of outbound HTTP connections that are currently active or idle on the client." - - // HTTPClientConnectionDuration is the metric conforming to the - // "http.client.connection.duration" semantic conventions. It represents the - // duration of the successfully established outbound HTTP connections. - // Instrument: histogram - // Unit: s - // Stability: Experimental - HTTPClientConnectionDurationName = "http.client.connection.duration" - HTTPClientConnectionDurationUnit = "s" - HTTPClientConnectionDurationDescription = "The duration of the successfully established outbound HTTP connections." - - // HTTPClientActiveRequests is the metric conforming to the - // "http.client.active_requests" semantic conventions. It represents the number - // of active HTTP requests. - // Instrument: updowncounter - // Unit: {request} - // Stability: Experimental - HTTPClientActiveRequestsName = "http.client.active_requests" - HTTPClientActiveRequestsUnit = "{request}" - HTTPClientActiveRequestsDescription = "Number of active HTTP requests." - - // HTTPClientRequestTimeInQueue is the metric conforming to the - // "http.client.request.time_in_queue" semantic conventions. It represents the - // amount of time requests spent on a queue waiting for an available - // connection. - // Instrument: histogram - // Unit: s - // Stability: Experimental - HTTPClientRequestTimeInQueueName = "http.client.request.time_in_queue" - HTTPClientRequestTimeInQueueUnit = "s" - HTTPClientRequestTimeInQueueDescription = "The amount of time requests spent on a queue waiting for an available connection." - - // KestrelActiveConnections is the metric conforming to the - // "kestrel.active_connections" semantic conventions. It represents the number - // of connections that are currently active on the server. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - KestrelActiveConnectionsName = "kestrel.active_connections" - KestrelActiveConnectionsUnit = "{connection}" - KestrelActiveConnectionsDescription = "Number of connections that are currently active on the server." - - // KestrelConnectionDuration is the metric conforming to the - // "kestrel.connection.duration" semantic conventions. It represents the - // duration of connections on the server. - // Instrument: histogram - // Unit: s - // Stability: Experimental - KestrelConnectionDurationName = "kestrel.connection.duration" - KestrelConnectionDurationUnit = "s" - KestrelConnectionDurationDescription = "The duration of connections on the server." - - // KestrelRejectedConnections is the metric conforming to the - // "kestrel.rejected_connections" semantic conventions. It represents the - // number of connections rejected by the server. - // Instrument: counter - // Unit: {connection} - // Stability: Experimental - KestrelRejectedConnectionsName = "kestrel.rejected_connections" - KestrelRejectedConnectionsUnit = "{connection}" - KestrelRejectedConnectionsDescription = "Number of connections rejected by the server." - - // KestrelQueuedConnections is the metric conforming to the - // "kestrel.queued_connections" semantic conventions. It represents the number - // of connections that are currently queued and are waiting to start. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - KestrelQueuedConnectionsName = "kestrel.queued_connections" - KestrelQueuedConnectionsUnit = "{connection}" - KestrelQueuedConnectionsDescription = "Number of connections that are currently queued and are waiting to start." - - // KestrelQueuedRequests is the metric conforming to the - // "kestrel.queued_requests" semantic conventions. It represents the number of - // HTTP requests on multiplexed connections (HTTP/2 and HTTP/3) that are - // currently queued and are waiting to start. - // Instrument: updowncounter - // Unit: {request} - // Stability: Experimental - KestrelQueuedRequestsName = "kestrel.queued_requests" - KestrelQueuedRequestsUnit = "{request}" - KestrelQueuedRequestsDescription = "Number of HTTP requests on multiplexed connections (HTTP/2 and HTTP/3) that are currently queued and are waiting to start." - - // KestrelUpgradedConnections is the metric conforming to the - // "kestrel.upgraded_connections" semantic conventions. It represents the - // number of connections that are currently upgraded (WebSockets). . - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - KestrelUpgradedConnectionsName = "kestrel.upgraded_connections" - KestrelUpgradedConnectionsUnit = "{connection}" - KestrelUpgradedConnectionsDescription = "Number of connections that are currently upgraded (WebSockets). ." - - // KestrelTLSHandshakeDuration is the metric conforming to the - // "kestrel.tls_handshake.duration" semantic conventions. It represents the - // duration of TLS handshakes on the server. - // Instrument: histogram - // Unit: s - // Stability: Experimental - KestrelTLSHandshakeDurationName = "kestrel.tls_handshake.duration" - KestrelTLSHandshakeDurationUnit = "s" - KestrelTLSHandshakeDurationDescription = "The duration of TLS handshakes on the server." - - // KestrelActiveTLSHandshakes is the metric conforming to the - // "kestrel.active_tls_handshakes" semantic conventions. It represents the - // number of TLS handshakes that are currently in progress on the server. - // Instrument: updowncounter - // Unit: {handshake} - // Stability: Experimental - KestrelActiveTLSHandshakesName = "kestrel.active_tls_handshakes" - KestrelActiveTLSHandshakesUnit = "{handshake}" - KestrelActiveTLSHandshakesDescription = "Number of TLS handshakes that are currently in progress on the server." - - // SignalrServerConnectionDuration is the metric conforming to the - // "signalr.server.connection.duration" semantic conventions. It represents the - // duration of connections on the server. - // Instrument: histogram - // Unit: s - // Stability: Experimental - SignalrServerConnectionDurationName = "signalr.server.connection.duration" - SignalrServerConnectionDurationUnit = "s" - SignalrServerConnectionDurationDescription = "The duration of connections on the server." - - // SignalrServerActiveConnections is the metric conforming to the - // "signalr.server.active_connections" semantic conventions. It represents the - // number of connections that are currently active on the server. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - SignalrServerActiveConnectionsName = "signalr.server.active_connections" - SignalrServerActiveConnectionsUnit = "{connection}" - SignalrServerActiveConnectionsDescription = "Number of connections that are currently active on the server." - - // FaaSInvokeDuration is the metric conforming to the "faas.invoke_duration" - // semantic conventions. It represents the measures the duration of the - // function's logic execution. - // Instrument: histogram - // Unit: s - // Stability: Experimental - FaaSInvokeDurationName = "faas.invoke_duration" - FaaSInvokeDurationUnit = "s" - FaaSInvokeDurationDescription = "Measures the duration of the function's logic execution" - - // FaaSInitDuration is the metric conforming to the "faas.init_duration" - // semantic conventions. It represents the measures the duration of the - // function's initialization, such as a cold start. - // Instrument: histogram - // Unit: s - // Stability: Experimental - FaaSInitDurationName = "faas.init_duration" - FaaSInitDurationUnit = "s" - FaaSInitDurationDescription = "Measures the duration of the function's initialization, such as a cold start" - - // FaaSColdstarts is the metric conforming to the "faas.coldstarts" semantic - // conventions. It represents the number of invocation cold starts. - // Instrument: counter - // Unit: {coldstart} - // Stability: Experimental - FaaSColdstartsName = "faas.coldstarts" - FaaSColdstartsUnit = "{coldstart}" - FaaSColdstartsDescription = "Number of invocation cold starts" - - // FaaSErrors is the metric conforming to the "faas.errors" semantic - // conventions. It represents the number of invocation errors. - // Instrument: counter - // Unit: {error} - // Stability: Experimental - FaaSErrorsName = "faas.errors" - FaaSErrorsUnit = "{error}" - FaaSErrorsDescription = "Number of invocation errors" - - // FaaSInvocations is the metric conforming to the "faas.invocations" semantic - // conventions. It represents the number of successful invocations. - // Instrument: counter - // Unit: {invocation} - // Stability: Experimental - FaaSInvocationsName = "faas.invocations" - FaaSInvocationsUnit = "{invocation}" - FaaSInvocationsDescription = "Number of successful invocations" - - // FaaSTimeouts is the metric conforming to the "faas.timeouts" semantic - // conventions. It represents the number of invocation timeouts. - // Instrument: counter - // Unit: {timeout} - // Stability: Experimental - FaaSTimeoutsName = "faas.timeouts" - FaaSTimeoutsUnit = "{timeout}" - FaaSTimeoutsDescription = "Number of invocation timeouts" - - // FaaSMemUsage is the metric conforming to the "faas.mem_usage" semantic - // conventions. It represents the distribution of max memory usage per - // invocation. - // Instrument: histogram - // Unit: By - // Stability: Experimental - FaaSMemUsageName = "faas.mem_usage" - FaaSMemUsageUnit = "By" - FaaSMemUsageDescription = "Distribution of max memory usage per invocation" - - // FaaSCPUUsage is the metric conforming to the "faas.cpu_usage" semantic - // conventions. It represents the distribution of CPU usage per invocation. - // Instrument: histogram - // Unit: s - // Stability: Experimental - FaaSCPUUsageName = "faas.cpu_usage" - FaaSCPUUsageUnit = "s" - FaaSCPUUsageDescription = "Distribution of CPU usage per invocation" - - // FaaSNetIo is the metric conforming to the "faas.net_io" semantic - // conventions. It represents the distribution of net I/O usage per invocation. - // Instrument: histogram - // Unit: By - // Stability: Experimental - FaaSNetIoName = "faas.net_io" - FaaSNetIoUnit = "By" - FaaSNetIoDescription = "Distribution of net I/O usage per invocation" - - // HTTPServerRequestDuration is the metric conforming to the - // "http.server.request.duration" semantic conventions. It represents the - // duration of HTTP server requests. - // Instrument: histogram - // Unit: s - // Stability: Stable - HTTPServerRequestDurationName = "http.server.request.duration" - HTTPServerRequestDurationUnit = "s" - HTTPServerRequestDurationDescription = "Duration of HTTP server requests." - - // HTTPServerActiveRequests is the metric conforming to the - // "http.server.active_requests" semantic conventions. It represents the number - // of active HTTP server requests. - // Instrument: updowncounter - // Unit: {request} - // Stability: Experimental - HTTPServerActiveRequestsName = "http.server.active_requests" - HTTPServerActiveRequestsUnit = "{request}" - HTTPServerActiveRequestsDescription = "Number of active HTTP server requests." - - // HTTPServerRequestBodySize is the metric conforming to the - // "http.server.request.body.size" semantic conventions. It represents the size - // of HTTP server request bodies. - // Instrument: histogram - // Unit: By - // Stability: Experimental - HTTPServerRequestBodySizeName = "http.server.request.body.size" - HTTPServerRequestBodySizeUnit = "By" - HTTPServerRequestBodySizeDescription = "Size of HTTP server request bodies." - - // HTTPServerResponseBodySize is the metric conforming to the - // "http.server.response.body.size" semantic conventions. It represents the - // size of HTTP server response bodies. - // Instrument: histogram - // Unit: By - // Stability: Experimental - HTTPServerResponseBodySizeName = "http.server.response.body.size" - HTTPServerResponseBodySizeUnit = "By" - HTTPServerResponseBodySizeDescription = "Size of HTTP server response bodies." - - // HTTPClientRequestDuration is the metric conforming to the - // "http.client.request.duration" semantic conventions. It represents the - // duration of HTTP client requests. - // Instrument: histogram - // Unit: s - // Stability: Stable - HTTPClientRequestDurationName = "http.client.request.duration" - HTTPClientRequestDurationUnit = "s" - HTTPClientRequestDurationDescription = "Duration of HTTP client requests." - - // HTTPClientRequestBodySize is the metric conforming to the - // "http.client.request.body.size" semantic conventions. It represents the size - // of HTTP client request bodies. - // Instrument: histogram - // Unit: By - // Stability: Experimental - HTTPClientRequestBodySizeName = "http.client.request.body.size" - HTTPClientRequestBodySizeUnit = "By" - HTTPClientRequestBodySizeDescription = "Size of HTTP client request bodies." - - // HTTPClientResponseBodySize is the metric conforming to the - // "http.client.response.body.size" semantic conventions. It represents the - // size of HTTP client response bodies. - // Instrument: histogram - // Unit: By - // Stability: Experimental - HTTPClientResponseBodySizeName = "http.client.response.body.size" - HTTPClientResponseBodySizeUnit = "By" - HTTPClientResponseBodySizeDescription = "Size of HTTP client response bodies." - - // JvmMemoryInit is the metric conforming to the "jvm.memory.init" semantic - // conventions. It represents the measure of initial memory requested. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - JvmMemoryInitName = "jvm.memory.init" - JvmMemoryInitUnit = "By" - JvmMemoryInitDescription = "Measure of initial memory requested." - - // JvmSystemCPUUtilization is the metric conforming to the - // "jvm.system.cpu.utilization" semantic conventions. It represents the recent - // CPU utilization for the whole system as reported by the JVM. - // Instrument: gauge - // Unit: 1 - // Stability: Experimental - JvmSystemCPUUtilizationName = "jvm.system.cpu.utilization" - JvmSystemCPUUtilizationUnit = "1" - JvmSystemCPUUtilizationDescription = "Recent CPU utilization for the whole system as reported by the JVM." - - // JvmSystemCPULoad1m is the metric conforming to the "jvm.system.cpu.load_1m" - // semantic conventions. It represents the average CPU load of the whole system - // for the last minute as reported by the JVM. - // Instrument: gauge - // Unit: {run_queue_item} - // Stability: Experimental - JvmSystemCPULoad1mName = "jvm.system.cpu.load_1m" - JvmSystemCPULoad1mUnit = "{run_queue_item}" - JvmSystemCPULoad1mDescription = "Average CPU load of the whole system for the last minute as reported by the JVM." - - // JvmBufferMemoryUsage is the metric conforming to the - // "jvm.buffer.memory.usage" semantic conventions. It represents the measure of - // memory used by buffers. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - JvmBufferMemoryUsageName = "jvm.buffer.memory.usage" - JvmBufferMemoryUsageUnit = "By" - JvmBufferMemoryUsageDescription = "Measure of memory used by buffers." - - // JvmBufferMemoryLimit is the metric conforming to the - // "jvm.buffer.memory.limit" semantic conventions. It represents the measure of - // total memory capacity of buffers. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - JvmBufferMemoryLimitName = "jvm.buffer.memory.limit" - JvmBufferMemoryLimitUnit = "By" - JvmBufferMemoryLimitDescription = "Measure of total memory capacity of buffers." - - // JvmBufferCount is the metric conforming to the "jvm.buffer.count" semantic - // conventions. It represents the number of buffers in the pool. - // Instrument: updowncounter - // Unit: {buffer} - // Stability: Experimental - JvmBufferCountName = "jvm.buffer.count" - JvmBufferCountUnit = "{buffer}" - JvmBufferCountDescription = "Number of buffers in the pool." - - // JvmMemoryUsed is the metric conforming to the "jvm.memory.used" semantic - // conventions. It represents the measure of memory used. - // Instrument: updowncounter - // Unit: By - // Stability: Stable - JvmMemoryUsedName = "jvm.memory.used" - JvmMemoryUsedUnit = "By" - JvmMemoryUsedDescription = "Measure of memory used." - - // JvmMemoryCommitted is the metric conforming to the "jvm.memory.committed" - // semantic conventions. It represents the measure of memory committed. - // Instrument: updowncounter - // Unit: By - // Stability: Stable - JvmMemoryCommittedName = "jvm.memory.committed" - JvmMemoryCommittedUnit = "By" - JvmMemoryCommittedDescription = "Measure of memory committed." - - // JvmMemoryLimit is the metric conforming to the "jvm.memory.limit" semantic - // conventions. It represents the measure of max obtainable memory. - // Instrument: updowncounter - // Unit: By - // Stability: Stable - JvmMemoryLimitName = "jvm.memory.limit" - JvmMemoryLimitUnit = "By" - JvmMemoryLimitDescription = "Measure of max obtainable memory." - - // JvmMemoryUsedAfterLastGc is the metric conforming to the - // "jvm.memory.used_after_last_gc" semantic conventions. It represents the - // measure of memory used, as measured after the most recent garbage collection - // event on this pool. - // Instrument: updowncounter - // Unit: By - // Stability: Stable - JvmMemoryUsedAfterLastGcName = "jvm.memory.used_after_last_gc" - JvmMemoryUsedAfterLastGcUnit = "By" - JvmMemoryUsedAfterLastGcDescription = "Measure of memory used, as measured after the most recent garbage collection event on this pool." - - // JvmGcDuration is the metric conforming to the "jvm.gc.duration" semantic - // conventions. It represents the duration of JVM garbage collection actions. - // Instrument: histogram - // Unit: s - // Stability: Stable - JvmGcDurationName = "jvm.gc.duration" - JvmGcDurationUnit = "s" - JvmGcDurationDescription = "Duration of JVM garbage collection actions." - - // JvmThreadCount is the metric conforming to the "jvm.thread.count" semantic - // conventions. It represents the number of executing platform threads. - // Instrument: updowncounter - // Unit: {thread} - // Stability: Stable - JvmThreadCountName = "jvm.thread.count" - JvmThreadCountUnit = "{thread}" - JvmThreadCountDescription = "Number of executing platform threads." - - // JvmClassLoaded is the metric conforming to the "jvm.class.loaded" semantic - // conventions. It represents the number of classes loaded since JVM start. - // Instrument: counter - // Unit: {class} - // Stability: Stable - JvmClassLoadedName = "jvm.class.loaded" - JvmClassLoadedUnit = "{class}" - JvmClassLoadedDescription = "Number of classes loaded since JVM start." - - // JvmClassUnloaded is the metric conforming to the "jvm.class.unloaded" - // semantic conventions. It represents the number of classes unloaded since JVM - // start. - // Instrument: counter - // Unit: {class} - // Stability: Stable - JvmClassUnloadedName = "jvm.class.unloaded" - JvmClassUnloadedUnit = "{class}" - JvmClassUnloadedDescription = "Number of classes unloaded since JVM start." - - // JvmClassCount is the metric conforming to the "jvm.class.count" semantic - // conventions. It represents the number of classes currently loaded. - // Instrument: updowncounter - // Unit: {class} - // Stability: Stable - JvmClassCountName = "jvm.class.count" - JvmClassCountUnit = "{class}" - JvmClassCountDescription = "Number of classes currently loaded." - - // JvmCPUCount is the metric conforming to the "jvm.cpu.count" semantic - // conventions. It represents the number of processors available to the Java - // virtual machine. - // Instrument: updowncounter - // Unit: {cpu} - // Stability: Stable - JvmCPUCountName = "jvm.cpu.count" - JvmCPUCountUnit = "{cpu}" - JvmCPUCountDescription = "Number of processors available to the Java virtual machine." - - // JvmCPUTime is the metric conforming to the "jvm.cpu.time" semantic - // conventions. It represents the cPU time used by the process as reported by - // the JVM. - // Instrument: counter - // Unit: s - // Stability: Stable - JvmCPUTimeName = "jvm.cpu.time" - JvmCPUTimeUnit = "s" - JvmCPUTimeDescription = "CPU time used by the process as reported by the JVM." - - // JvmCPURecentUtilization is the metric conforming to the - // "jvm.cpu.recent_utilization" semantic conventions. It represents the recent - // CPU utilization for the process as reported by the JVM. - // Instrument: gauge - // Unit: 1 - // Stability: Stable - JvmCPURecentUtilizationName = "jvm.cpu.recent_utilization" - JvmCPURecentUtilizationUnit = "1" - JvmCPURecentUtilizationDescription = "Recent CPU utilization for the process as reported by the JVM." - - // MessagingPublishDuration is the metric conforming to the - // "messaging.publish.duration" semantic conventions. It represents the - // measures the duration of publish operation. - // Instrument: histogram - // Unit: s - // Stability: Experimental - MessagingPublishDurationName = "messaging.publish.duration" - MessagingPublishDurationUnit = "s" - MessagingPublishDurationDescription = "Measures the duration of publish operation." - - // MessagingReceiveDuration is the metric conforming to the - // "messaging.receive.duration" semantic conventions. It represents the - // measures the duration of receive operation. - // Instrument: histogram - // Unit: s - // Stability: Experimental - MessagingReceiveDurationName = "messaging.receive.duration" - MessagingReceiveDurationUnit = "s" - MessagingReceiveDurationDescription = "Measures the duration of receive operation." - - // MessagingDeliverDuration is the metric conforming to the - // "messaging.deliver.duration" semantic conventions. It represents the - // measures the duration of deliver operation. - // Instrument: histogram - // Unit: s - // Stability: Experimental - MessagingDeliverDurationName = "messaging.deliver.duration" - MessagingDeliverDurationUnit = "s" - MessagingDeliverDurationDescription = "Measures the duration of deliver operation." - - // MessagingPublishMessages is the metric conforming to the - // "messaging.publish.messages" semantic conventions. It represents the - // measures the number of published messages. - // Instrument: counter - // Unit: {message} - // Stability: Experimental - MessagingPublishMessagesName = "messaging.publish.messages" - MessagingPublishMessagesUnit = "{message}" - MessagingPublishMessagesDescription = "Measures the number of published messages." - - // MessagingReceiveMessages is the metric conforming to the - // "messaging.receive.messages" semantic conventions. It represents the - // measures the number of received messages. - // Instrument: counter - // Unit: {message} - // Stability: Experimental - MessagingReceiveMessagesName = "messaging.receive.messages" - MessagingReceiveMessagesUnit = "{message}" - MessagingReceiveMessagesDescription = "Measures the number of received messages." - - // MessagingDeliverMessages is the metric conforming to the - // "messaging.deliver.messages" semantic conventions. It represents the - // measures the number of delivered messages. - // Instrument: counter - // Unit: {message} - // Stability: Experimental - MessagingDeliverMessagesName = "messaging.deliver.messages" - MessagingDeliverMessagesUnit = "{message}" - MessagingDeliverMessagesDescription = "Measures the number of delivered messages." - - // RPCServerDuration is the metric conforming to the "rpc.server.duration" - // semantic conventions. It represents the measures the duration of inbound - // RPC. - // Instrument: histogram - // Unit: ms - // Stability: Experimental - RPCServerDurationName = "rpc.server.duration" - RPCServerDurationUnit = "ms" - RPCServerDurationDescription = "Measures the duration of inbound RPC." - - // RPCServerRequestSize is the metric conforming to the - // "rpc.server.request.size" semantic conventions. It represents the measures - // the size of RPC request messages (uncompressed). - // Instrument: histogram - // Unit: By - // Stability: Experimental - RPCServerRequestSizeName = "rpc.server.request.size" - RPCServerRequestSizeUnit = "By" - RPCServerRequestSizeDescription = "Measures the size of RPC request messages (uncompressed)." - - // RPCServerResponseSize is the metric conforming to the - // "rpc.server.response.size" semantic conventions. It represents the measures - // the size of RPC response messages (uncompressed). - // Instrument: histogram - // Unit: By - // Stability: Experimental - RPCServerResponseSizeName = "rpc.server.response.size" - RPCServerResponseSizeUnit = "By" - RPCServerResponseSizeDescription = "Measures the size of RPC response messages (uncompressed)." - - // RPCServerRequestsPerRPC is the metric conforming to the - // "rpc.server.requests_per_rpc" semantic conventions. It represents the - // measures the number of messages received per RPC. - // Instrument: histogram - // Unit: {count} - // Stability: Experimental - RPCServerRequestsPerRPCName = "rpc.server.requests_per_rpc" - RPCServerRequestsPerRPCUnit = "{count}" - RPCServerRequestsPerRPCDescription = "Measures the number of messages received per RPC." - - // RPCServerResponsesPerRPC is the metric conforming to the - // "rpc.server.responses_per_rpc" semantic conventions. It represents the - // measures the number of messages sent per RPC. - // Instrument: histogram - // Unit: {count} - // Stability: Experimental - RPCServerResponsesPerRPCName = "rpc.server.responses_per_rpc" - RPCServerResponsesPerRPCUnit = "{count}" - RPCServerResponsesPerRPCDescription = "Measures the number of messages sent per RPC." - - // RPCClientDuration is the metric conforming to the "rpc.client.duration" - // semantic conventions. It represents the measures the duration of outbound - // RPC. - // Instrument: histogram - // Unit: ms - // Stability: Experimental - RPCClientDurationName = "rpc.client.duration" - RPCClientDurationUnit = "ms" - RPCClientDurationDescription = "Measures the duration of outbound RPC." - - // RPCClientRequestSize is the metric conforming to the - // "rpc.client.request.size" semantic conventions. It represents the measures - // the size of RPC request messages (uncompressed). - // Instrument: histogram - // Unit: By - // Stability: Experimental - RPCClientRequestSizeName = "rpc.client.request.size" - RPCClientRequestSizeUnit = "By" - RPCClientRequestSizeDescription = "Measures the size of RPC request messages (uncompressed)." - - // RPCClientResponseSize is the metric conforming to the - // "rpc.client.response.size" semantic conventions. It represents the measures - // the size of RPC response messages (uncompressed). - // Instrument: histogram - // Unit: By - // Stability: Experimental - RPCClientResponseSizeName = "rpc.client.response.size" - RPCClientResponseSizeUnit = "By" - RPCClientResponseSizeDescription = "Measures the size of RPC response messages (uncompressed)." - - // RPCClientRequestsPerRPC is the metric conforming to the - // "rpc.client.requests_per_rpc" semantic conventions. It represents the - // measures the number of messages received per RPC. - // Instrument: histogram - // Unit: {count} - // Stability: Experimental - RPCClientRequestsPerRPCName = "rpc.client.requests_per_rpc" - RPCClientRequestsPerRPCUnit = "{count}" - RPCClientRequestsPerRPCDescription = "Measures the number of messages received per RPC." - - // RPCClientResponsesPerRPC is the metric conforming to the - // "rpc.client.responses_per_rpc" semantic conventions. It represents the - // measures the number of messages sent per RPC. - // Instrument: histogram - // Unit: {count} - // Stability: Experimental - RPCClientResponsesPerRPCName = "rpc.client.responses_per_rpc" - RPCClientResponsesPerRPCUnit = "{count}" - RPCClientResponsesPerRPCDescription = "Measures the number of messages sent per RPC." - - // SystemCPUTime is the metric conforming to the "system.cpu.time" semantic - // conventions. It represents the seconds each logical CPU spent on each mode. - // Instrument: counter - // Unit: s - // Stability: Experimental - SystemCPUTimeName = "system.cpu.time" - SystemCPUTimeUnit = "s" - SystemCPUTimeDescription = "Seconds each logical CPU spent on each mode" - - // SystemCPUUtilization is the metric conforming to the - // "system.cpu.utilization" semantic conventions. It represents the difference - // in system.cpu.time since the last measurement, divided by the elapsed time - // and number of logical CPUs. - // Instrument: gauge - // Unit: 1 - // Stability: Experimental - SystemCPUUtilizationName = "system.cpu.utilization" - SystemCPUUtilizationUnit = "1" - SystemCPUUtilizationDescription = "Difference in system.cpu.time since the last measurement, divided by the elapsed time and number of logical CPUs" - - // SystemCPUFrequency is the metric conforming to the "system.cpu.frequency" - // semantic conventions. It represents the reports the current frequency of the - // CPU in Hz. - // Instrument: gauge - // Unit: {Hz} - // Stability: Experimental - SystemCPUFrequencyName = "system.cpu.frequency" - SystemCPUFrequencyUnit = "{Hz}" - SystemCPUFrequencyDescription = "Reports the current frequency of the CPU in Hz" - - // SystemCPUPhysicalCount is the metric conforming to the - // "system.cpu.physical.count" semantic conventions. It represents the reports - // the number of actual physical processor cores on the hardware. - // Instrument: updowncounter - // Unit: {cpu} - // Stability: Experimental - SystemCPUPhysicalCountName = "system.cpu.physical.count" - SystemCPUPhysicalCountUnit = "{cpu}" - SystemCPUPhysicalCountDescription = "Reports the number of actual physical processor cores on the hardware" - - // SystemCPULogicalCount is the metric conforming to the - // "system.cpu.logical.count" semantic conventions. It represents the reports - // the number of logical (virtual) processor cores created by the operating - // system to manage multitasking. - // Instrument: updowncounter - // Unit: {cpu} - // Stability: Experimental - SystemCPULogicalCountName = "system.cpu.logical.count" - SystemCPULogicalCountUnit = "{cpu}" - SystemCPULogicalCountDescription = "Reports the number of logical (virtual) processor cores created by the operating system to manage multitasking" - - // SystemMemoryUsage is the metric conforming to the "system.memory.usage" - // semantic conventions. It represents the reports memory in use by state. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - SystemMemoryUsageName = "system.memory.usage" - SystemMemoryUsageUnit = "By" - SystemMemoryUsageDescription = "Reports memory in use by state." - - // SystemMemoryLimit is the metric conforming to the "system.memory.limit" - // semantic conventions. It represents the total memory available in the - // system. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - SystemMemoryLimitName = "system.memory.limit" - SystemMemoryLimitUnit = "By" - SystemMemoryLimitDescription = "Total memory available in the system." - - // SystemMemoryUtilization is the metric conforming to the - // "system.memory.utilization" semantic conventions. - // Instrument: gauge - // Unit: 1 - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemMemoryUtilizationName = "system.memory.utilization" - SystemMemoryUtilizationUnit = "1" - - // SystemPagingUsage is the metric conforming to the "system.paging.usage" - // semantic conventions. It represents the unix swap or windows pagefile usage. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - SystemPagingUsageName = "system.paging.usage" - SystemPagingUsageUnit = "By" - SystemPagingUsageDescription = "Unix swap or windows pagefile usage" - - // SystemPagingUtilization is the metric conforming to the - // "system.paging.utilization" semantic conventions. - // Instrument: gauge - // Unit: 1 - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemPagingUtilizationName = "system.paging.utilization" - SystemPagingUtilizationUnit = "1" - - // SystemPagingFaults is the metric conforming to the "system.paging.faults" - // semantic conventions. - // Instrument: counter - // Unit: {fault} - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemPagingFaultsName = "system.paging.faults" - SystemPagingFaultsUnit = "{fault}" - - // SystemPagingOperations is the metric conforming to the - // "system.paging.operations" semantic conventions. - // Instrument: counter - // Unit: {operation} - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemPagingOperationsName = "system.paging.operations" - SystemPagingOperationsUnit = "{operation}" - - // SystemDiskIo is the metric conforming to the "system.disk.io" semantic - // conventions. - // Instrument: counter - // Unit: By - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemDiskIoName = "system.disk.io" - SystemDiskIoUnit = "By" - - // SystemDiskOperations is the metric conforming to the - // "system.disk.operations" semantic conventions. - // Instrument: counter - // Unit: {operation} - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemDiskOperationsName = "system.disk.operations" - SystemDiskOperationsUnit = "{operation}" - - // SystemDiskIoTime is the metric conforming to the "system.disk.io_time" - // semantic conventions. It represents the time disk spent activated. - // Instrument: counter - // Unit: s - // Stability: Experimental - SystemDiskIoTimeName = "system.disk.io_time" - SystemDiskIoTimeUnit = "s" - SystemDiskIoTimeDescription = "Time disk spent activated" - - // SystemDiskOperationTime is the metric conforming to the - // "system.disk.operation_time" semantic conventions. It represents the sum of - // the time each operation took to complete. - // Instrument: counter - // Unit: s - // Stability: Experimental - SystemDiskOperationTimeName = "system.disk.operation_time" - SystemDiskOperationTimeUnit = "s" - SystemDiskOperationTimeDescription = "Sum of the time each operation took to complete" - - // SystemDiskMerged is the metric conforming to the "system.disk.merged" - // semantic conventions. - // Instrument: counter - // Unit: {operation} - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemDiskMergedName = "system.disk.merged" - SystemDiskMergedUnit = "{operation}" - - // SystemFilesystemUsage is the metric conforming to the - // "system.filesystem.usage" semantic conventions. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemFilesystemUsageName = "system.filesystem.usage" - SystemFilesystemUsageUnit = "By" - - // SystemFilesystemUtilization is the metric conforming to the - // "system.filesystem.utilization" semantic conventions. - // Instrument: gauge - // Unit: 1 - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemFilesystemUtilizationName = "system.filesystem.utilization" - SystemFilesystemUtilizationUnit = "1" - - // SystemNetworkDropped is the metric conforming to the - // "system.network.dropped" semantic conventions. It represents the count of - // packets that are dropped or discarded even though there was no error. - // Instrument: counter - // Unit: {packet} - // Stability: Experimental - SystemNetworkDroppedName = "system.network.dropped" - SystemNetworkDroppedUnit = "{packet}" - SystemNetworkDroppedDescription = "Count of packets that are dropped or discarded even though there was no error" - - // SystemNetworkPackets is the metric conforming to the - // "system.network.packets" semantic conventions. - // Instrument: counter - // Unit: {packet} - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemNetworkPacketsName = "system.network.packets" - SystemNetworkPacketsUnit = "{packet}" - - // SystemNetworkErrors is the metric conforming to the "system.network.errors" - // semantic conventions. It represents the count of network errors detected. - // Instrument: counter - // Unit: {error} - // Stability: Experimental - SystemNetworkErrorsName = "system.network.errors" - SystemNetworkErrorsUnit = "{error}" - SystemNetworkErrorsDescription = "Count of network errors detected" - - // SystemNetworkIo is the metric conforming to the "system.network.io" semantic - // conventions. - // Instrument: counter - // Unit: By - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemNetworkIoName = "system.network.io" - SystemNetworkIoUnit = "By" - - // SystemNetworkConnections is the metric conforming to the - // "system.network.connections" semantic conventions. - // Instrument: updowncounter - // Unit: {connection} - // Stability: Experimental - // NOTE: The description (brief) for this metric is not defined in the semantic-conventions repository. - SystemNetworkConnectionsName = "system.network.connections" - SystemNetworkConnectionsUnit = "{connection}" - - // SystemProcessesCount is the metric conforming to the - // "system.processes.count" semantic conventions. It represents the total - // number of processes in each state. - // Instrument: updowncounter - // Unit: {process} - // Stability: Experimental - SystemProcessesCountName = "system.processes.count" - SystemProcessesCountUnit = "{process}" - SystemProcessesCountDescription = "Total number of processes in each state" - - // SystemProcessesCreated is the metric conforming to the - // "system.processes.created" semantic conventions. It represents the total - // number of processes created over uptime of the host. - // Instrument: counter - // Unit: {process} - // Stability: Experimental - SystemProcessesCreatedName = "system.processes.created" - SystemProcessesCreatedUnit = "{process}" - SystemProcessesCreatedDescription = "Total number of processes created over uptime of the host" - - // SystemLinuxMemoryAvailable is the metric conforming to the - // "system.linux.memory.available" semantic conventions. It represents an - // estimate of how much memory is available for starting new applications, - // without causing swapping. - // Instrument: updowncounter - // Unit: By - // Stability: Experimental - SystemLinuxMemoryAvailableName = "system.linux.memory.available" - SystemLinuxMemoryAvailableUnit = "By" - SystemLinuxMemoryAvailableDescription = "An estimate of how much memory is available for starting new applications, without causing swapping" -) diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/resource.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/resource.go deleted file mode 100644 index d66bbe9c23d..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/resource.go +++ /dev/null @@ -1,2545 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -// Code generated from semantic convention specification. DO NOT EDIT. - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -import "go.opentelemetry.io/otel/attribute" - -// A cloud environment (e.g. GCP, Azure, AWS). -const ( - // CloudAccountIDKey is the attribute Key conforming to the - // "cloud.account.id" semantic conventions. It represents the cloud account - // ID the resource is assigned to. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '111111111111', 'opentelemetry' - CloudAccountIDKey = attribute.Key("cloud.account.id") - - // CloudAvailabilityZoneKey is the attribute Key conforming to the - // "cloud.availability_zone" semantic conventions. It represents the cloud - // regions often have multiple, isolated locations known as zones to - // increase availability. Availability zone represents the zone where the - // resource is running. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'us-east-1c' - // Note: Availability zones are called "zones" on Alibaba Cloud and Google - // Cloud. - CloudAvailabilityZoneKey = attribute.Key("cloud.availability_zone") - - // CloudPlatformKey is the attribute Key conforming to the "cloud.platform" - // semantic conventions. It represents the cloud platform in use. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Note: The prefix of the service SHOULD match the one specified in - // `cloud.provider`. - CloudPlatformKey = attribute.Key("cloud.platform") - - // CloudProviderKey is the attribute Key conforming to the "cloud.provider" - // semantic conventions. It represents the name of the cloud provider. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - CloudProviderKey = attribute.Key("cloud.provider") - - // CloudRegionKey is the attribute Key conforming to the "cloud.region" - // semantic conventions. It represents the geographical region the resource - // is running. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'us-central1', 'us-east-1' - // Note: Refer to your provider's docs to see the available regions, for - // example [Alibaba Cloud - // regions](https://www.alibabacloud.com/help/doc-detail/40654.htm), [AWS - // regions](https://aws.amazon.com/about-aws/global-infrastructure/regions_az/), - // [Azure - // regions](https://azure.microsoft.com/global-infrastructure/geographies/), - // [Google Cloud regions](https://cloud.google.com/about/locations), or - // [Tencent Cloud - // regions](https://www.tencentcloud.com/document/product/213/6091). - CloudRegionKey = attribute.Key("cloud.region") - - // CloudResourceIDKey is the attribute Key conforming to the - // "cloud.resource_id" semantic conventions. It represents the cloud - // provider-specific native identifier of the monitored cloud resource - // (e.g. an - // [ARN](https://docs.aws.amazon.com/general/latest/gr/aws-arns-and-namespaces.html) - // on AWS, a [fully qualified resource - // ID](https://learn.microsoft.com/rest/api/resources/resources/get-by-id) - // on Azure, a [full resource - // name](https://cloud.google.com/apis/design/resource_names#full_resource_name) - // on GCP) - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'arn:aws:lambda:REGION:ACCOUNT_ID:function:my-function', - // '//run.googleapis.com/projects/PROJECT_ID/locations/LOCATION_ID/services/SERVICE_ID', - // '/subscriptions//resourceGroups//providers/Microsoft.Web/sites//functions/' - // Note: On some cloud providers, it may not be possible to determine the - // full ID at startup, - // so it may be necessary to set `cloud.resource_id` as a span attribute - // instead. - // - // The exact value to use for `cloud.resource_id` depends on the cloud - // provider. - // The following well-known definitions MUST be used if you set this - // attribute and they apply: - // - // * **AWS Lambda:** The function - // [ARN](https://docs.aws.amazon.com/general/latest/gr/aws-arns-and-namespaces.html). - // Take care not to use the "invoked ARN" directly but replace any - // [alias - // suffix](https://docs.aws.amazon.com/lambda/latest/dg/configuration-aliases.html) - // with the resolved function version, as the same runtime instance may - // be invokable with - // multiple different aliases. - // * **GCP:** The [URI of the - // resource](https://cloud.google.com/iam/docs/full-resource-names) - // * **Azure:** The [Fully Qualified Resource - // ID](https://docs.microsoft.com/rest/api/resources/resources/get-by-id) - // of the invoked function, - // *not* the function app, having the form - // `/subscriptions//resourceGroups//providers/Microsoft.Web/sites//functions/`. - // This means that a span attribute MUST be used, as an Azure function - // app can host multiple functions that would usually share - // a TracerProvider. - CloudResourceIDKey = attribute.Key("cloud.resource_id") -) - -var ( - // Alibaba Cloud Elastic Compute Service - CloudPlatformAlibabaCloudECS = CloudPlatformKey.String("alibaba_cloud_ecs") - // Alibaba Cloud Function Compute - CloudPlatformAlibabaCloudFc = CloudPlatformKey.String("alibaba_cloud_fc") - // Red Hat OpenShift on Alibaba Cloud - CloudPlatformAlibabaCloudOpenshift = CloudPlatformKey.String("alibaba_cloud_openshift") - // AWS Elastic Compute Cloud - CloudPlatformAWSEC2 = CloudPlatformKey.String("aws_ec2") - // AWS Elastic Container Service - CloudPlatformAWSECS = CloudPlatformKey.String("aws_ecs") - // AWS Elastic Kubernetes Service - CloudPlatformAWSEKS = CloudPlatformKey.String("aws_eks") - // AWS Lambda - CloudPlatformAWSLambda = CloudPlatformKey.String("aws_lambda") - // AWS Elastic Beanstalk - CloudPlatformAWSElasticBeanstalk = CloudPlatformKey.String("aws_elastic_beanstalk") - // AWS App Runner - CloudPlatformAWSAppRunner = CloudPlatformKey.String("aws_app_runner") - // Red Hat OpenShift on AWS (ROSA) - CloudPlatformAWSOpenshift = CloudPlatformKey.String("aws_openshift") - // Azure Virtual Machines - CloudPlatformAzureVM = CloudPlatformKey.String("azure_vm") - // Azure Container Instances - CloudPlatformAzureContainerInstances = CloudPlatformKey.String("azure_container_instances") - // Azure Kubernetes Service - CloudPlatformAzureAKS = CloudPlatformKey.String("azure_aks") - // Azure Functions - CloudPlatformAzureFunctions = CloudPlatformKey.String("azure_functions") - // Azure App Service - CloudPlatformAzureAppService = CloudPlatformKey.String("azure_app_service") - // Azure Red Hat OpenShift - CloudPlatformAzureOpenshift = CloudPlatformKey.String("azure_openshift") - // Google Bare Metal Solution (BMS) - CloudPlatformGCPBareMetalSolution = CloudPlatformKey.String("gcp_bare_metal_solution") - // Google Cloud Compute Engine (GCE) - CloudPlatformGCPComputeEngine = CloudPlatformKey.String("gcp_compute_engine") - // Google Cloud Run - CloudPlatformGCPCloudRun = CloudPlatformKey.String("gcp_cloud_run") - // Google Cloud Kubernetes Engine (GKE) - CloudPlatformGCPKubernetesEngine = CloudPlatformKey.String("gcp_kubernetes_engine") - // Google Cloud Functions (GCF) - CloudPlatformGCPCloudFunctions = CloudPlatformKey.String("gcp_cloud_functions") - // Google Cloud App Engine (GAE) - CloudPlatformGCPAppEngine = CloudPlatformKey.String("gcp_app_engine") - // Red Hat OpenShift on Google Cloud - CloudPlatformGCPOpenshift = CloudPlatformKey.String("gcp_openshift") - // Red Hat OpenShift on IBM Cloud - CloudPlatformIbmCloudOpenshift = CloudPlatformKey.String("ibm_cloud_openshift") - // Tencent Cloud Cloud Virtual Machine (CVM) - CloudPlatformTencentCloudCvm = CloudPlatformKey.String("tencent_cloud_cvm") - // Tencent Cloud Elastic Kubernetes Service (EKS) - CloudPlatformTencentCloudEKS = CloudPlatformKey.String("tencent_cloud_eks") - // Tencent Cloud Serverless Cloud Function (SCF) - CloudPlatformTencentCloudScf = CloudPlatformKey.String("tencent_cloud_scf") -) - -var ( - // Alibaba Cloud - CloudProviderAlibabaCloud = CloudProviderKey.String("alibaba_cloud") - // Amazon Web Services - CloudProviderAWS = CloudProviderKey.String("aws") - // Microsoft Azure - CloudProviderAzure = CloudProviderKey.String("azure") - // Google Cloud Platform - CloudProviderGCP = CloudProviderKey.String("gcp") - // Heroku Platform as a Service - CloudProviderHeroku = CloudProviderKey.String("heroku") - // IBM Cloud - CloudProviderIbmCloud = CloudProviderKey.String("ibm_cloud") - // Tencent Cloud - CloudProviderTencentCloud = CloudProviderKey.String("tencent_cloud") -) - -// CloudAccountID returns an attribute KeyValue conforming to the -// "cloud.account.id" semantic conventions. It represents the cloud account ID -// the resource is assigned to. -func CloudAccountID(val string) attribute.KeyValue { - return CloudAccountIDKey.String(val) -} - -// CloudAvailabilityZone returns an attribute KeyValue conforming to the -// "cloud.availability_zone" semantic conventions. It represents the cloud -// regions often have multiple, isolated locations known as zones to increase -// availability. Availability zone represents the zone where the resource is -// running. -func CloudAvailabilityZone(val string) attribute.KeyValue { - return CloudAvailabilityZoneKey.String(val) -} - -// CloudRegion returns an attribute KeyValue conforming to the -// "cloud.region" semantic conventions. It represents the geographical region -// the resource is running. -func CloudRegion(val string) attribute.KeyValue { - return CloudRegionKey.String(val) -} - -// CloudResourceID returns an attribute KeyValue conforming to the -// "cloud.resource_id" semantic conventions. It represents the cloud -// provider-specific native identifier of the monitored cloud resource (e.g. an -// [ARN](https://docs.aws.amazon.com/general/latest/gr/aws-arns-and-namespaces.html) -// on AWS, a [fully qualified resource -// ID](https://learn.microsoft.com/rest/api/resources/resources/get-by-id) on -// Azure, a [full resource -// name](https://cloud.google.com/apis/design/resource_names#full_resource_name) -// on GCP) -func CloudResourceID(val string) attribute.KeyValue { - return CloudResourceIDKey.String(val) -} - -// A container instance. -const ( - // ContainerCommandKey is the attribute Key conforming to the - // "container.command" semantic conventions. It represents the command used - // to run the container (i.e. the command name). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'otelcontribcol' - // Note: If using embedded credentials or sensitive data, it is recommended - // to remove them to prevent potential leakage. - ContainerCommandKey = attribute.Key("container.command") - - // ContainerCommandArgsKey is the attribute Key conforming to the - // "container.command_args" semantic conventions. It represents the all the - // command arguments (including the command/executable itself) run by the - // container. [2] - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'otelcontribcol, --config, config.yaml' - ContainerCommandArgsKey = attribute.Key("container.command_args") - - // ContainerCommandLineKey is the attribute Key conforming to the - // "container.command_line" semantic conventions. It represents the full - // command run by the container as a single string representing the full - // command. [2] - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'otelcontribcol --config config.yaml' - ContainerCommandLineKey = attribute.Key("container.command_line") - - // ContainerIDKey is the attribute Key conforming to the "container.id" - // semantic conventions. It represents the container ID. Usually a UUID, as - // for example used to [identify Docker - // containers](https://docs.docker.com/engine/reference/run/#container-identification). - // The UUID might be abbreviated. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'a3bf90e006b2' - ContainerIDKey = attribute.Key("container.id") - - // ContainerImageIDKey is the attribute Key conforming to the - // "container.image.id" semantic conventions. It represents the runtime - // specific image identifier. Usually a hash algorithm followed by a UUID. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'sha256:19c92d0a00d1b66d897bceaa7319bee0dd38a10a851c60bcec9474aa3f01e50f' - // Note: Docker defines a sha256 of the image id; `container.image.id` - // corresponds to the `Image` field from the Docker container inspect - // [API](https://docs.docker.com/engine/api/v1.43/#tag/Container/operation/ContainerInspect) - // endpoint. - // K8S defines a link to the container registry repository with digest - // `"imageID": "registry.azurecr.io - // /namespace/service/dockerfile@sha256:bdeabd40c3a8a492eaf9e8e44d0ebbb84bac7ee25ac0cf8a7159d25f62555625"`. - // The ID is assinged by the container runtime and can vary in different - // environments. Consider using `oci.manifest.digest` if it is important to - // identify the same image in different environments/runtimes. - ContainerImageIDKey = attribute.Key("container.image.id") - - // ContainerImageNameKey is the attribute Key conforming to the - // "container.image.name" semantic conventions. It represents the name of - // the image the container was built on. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'gcr.io/opentelemetry/operator' - ContainerImageNameKey = attribute.Key("container.image.name") - - // ContainerImageRepoDigestsKey is the attribute Key conforming to the - // "container.image.repo_digests" semantic conventions. It represents the - // repo digests of the container image as provided by the container - // runtime. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'example@sha256:afcc7f1ac1b49db317a7196c902e61c6c3c4607d63599ee1a82d702d249a0ccb', - // 'internal.registry.example.com:5000/example@sha256:b69959407d21e8a062e0416bf13405bb2b71ed7a84dde4158ebafacfa06f5578' - // Note: - // [Docker](https://docs.docker.com/engine/api/v1.43/#tag/Image/operation/ImageInspect) - // and - // [CRI](https://github.com/kubernetes/cri-api/blob/c75ef5b473bbe2d0a4fc92f82235efd665ea8e9f/pkg/apis/runtime/v1/api.proto#L1237-L1238) - // report those under the `RepoDigests` field. - ContainerImageRepoDigestsKey = attribute.Key("container.image.repo_digests") - - // ContainerImageTagsKey is the attribute Key conforming to the - // "container.image.tags" semantic conventions. It represents the container - // image tags. An example can be found in [Docker Image - // Inspect](https://docs.docker.com/engine/api/v1.43/#tag/Image/operation/ImageInspect). - // Should be only the `` section of the full name for example from - // `registry.example.com/my-org/my-image:`. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'v1.27.1', '3.5.7-0' - ContainerImageTagsKey = attribute.Key("container.image.tags") - - // ContainerNameKey is the attribute Key conforming to the "container.name" - // semantic conventions. It represents the container name used by container - // runtime. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry-autoconf' - ContainerNameKey = attribute.Key("container.name") - - // ContainerRuntimeKey is the attribute Key conforming to the - // "container.runtime" semantic conventions. It represents the container - // runtime managing this container. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'docker', 'containerd', 'rkt' - ContainerRuntimeKey = attribute.Key("container.runtime") -) - -// ContainerCommand returns an attribute KeyValue conforming to the -// "container.command" semantic conventions. It represents the command used to -// run the container (i.e. the command name). -func ContainerCommand(val string) attribute.KeyValue { - return ContainerCommandKey.String(val) -} - -// ContainerCommandArgs returns an attribute KeyValue conforming to the -// "container.command_args" semantic conventions. It represents the all the -// command arguments (including the command/executable itself) run by the -// container. [2] -func ContainerCommandArgs(val ...string) attribute.KeyValue { - return ContainerCommandArgsKey.StringSlice(val) -} - -// ContainerCommandLine returns an attribute KeyValue conforming to the -// "container.command_line" semantic conventions. It represents the full -// command run by the container as a single string representing the full -// command. [2] -func ContainerCommandLine(val string) attribute.KeyValue { - return ContainerCommandLineKey.String(val) -} - -// ContainerID returns an attribute KeyValue conforming to the -// "container.id" semantic conventions. It represents the container ID. Usually -// a UUID, as for example used to [identify Docker -// containers](https://docs.docker.com/engine/reference/run/#container-identification). -// The UUID might be abbreviated. -func ContainerID(val string) attribute.KeyValue { - return ContainerIDKey.String(val) -} - -// ContainerImageID returns an attribute KeyValue conforming to the -// "container.image.id" semantic conventions. It represents the runtime -// specific image identifier. Usually a hash algorithm followed by a UUID. -func ContainerImageID(val string) attribute.KeyValue { - return ContainerImageIDKey.String(val) -} - -// ContainerImageName returns an attribute KeyValue conforming to the -// "container.image.name" semantic conventions. It represents the name of the -// image the container was built on. -func ContainerImageName(val string) attribute.KeyValue { - return ContainerImageNameKey.String(val) -} - -// ContainerImageRepoDigests returns an attribute KeyValue conforming to the -// "container.image.repo_digests" semantic conventions. It represents the repo -// digests of the container image as provided by the container runtime. -func ContainerImageRepoDigests(val ...string) attribute.KeyValue { - return ContainerImageRepoDigestsKey.StringSlice(val) -} - -// ContainerImageTags returns an attribute KeyValue conforming to the -// "container.image.tags" semantic conventions. It represents the container -// image tags. An example can be found in [Docker Image -// Inspect](https://docs.docker.com/engine/api/v1.43/#tag/Image/operation/ImageInspect). -// Should be only the `` section of the full name for example from -// `registry.example.com/my-org/my-image:`. -func ContainerImageTags(val ...string) attribute.KeyValue { - return ContainerImageTagsKey.StringSlice(val) -} - -// ContainerName returns an attribute KeyValue conforming to the -// "container.name" semantic conventions. It represents the container name used -// by container runtime. -func ContainerName(val string) attribute.KeyValue { - return ContainerNameKey.String(val) -} - -// ContainerRuntime returns an attribute KeyValue conforming to the -// "container.runtime" semantic conventions. It represents the container -// runtime managing this container. -func ContainerRuntime(val string) attribute.KeyValue { - return ContainerRuntimeKey.String(val) -} - -// Describes device attributes. -const ( - // DeviceIDKey is the attribute Key conforming to the "device.id" semantic - // conventions. It represents a unique identifier representing the device - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2ab2916d-a51f-4ac8-80ee-45ac31a28092' - // Note: The device identifier MUST only be defined using the values - // outlined below. This value is not an advertising identifier and MUST NOT - // be used as such. On iOS (Swift or Objective-C), this value MUST be equal - // to the [vendor - // identifier](https://developer.apple.com/documentation/uikit/uidevice/1620059-identifierforvendor). - // On Android (Java or Kotlin), this value MUST be equal to the Firebase - // Installation ID or a globally unique UUID which is persisted across - // sessions in your application. More information can be found - // [here](https://developer.android.com/training/articles/user-data-ids) on - // best practices and exact implementation details. Caution should be taken - // when storing personal data or anything which can identify a user. GDPR - // and data protection laws may apply, ensure you do your own due - // diligence. - DeviceIDKey = attribute.Key("device.id") - - // DeviceManufacturerKey is the attribute Key conforming to the - // "device.manufacturer" semantic conventions. It represents the name of - // the device manufacturer - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Apple', 'Samsung' - // Note: The Android OS provides this field via - // [Build](https://developer.android.com/reference/android/os/Build#MANUFACTURER). - // iOS apps SHOULD hardcode the value `Apple`. - DeviceManufacturerKey = attribute.Key("device.manufacturer") - - // DeviceModelIdentifierKey is the attribute Key conforming to the - // "device.model.identifier" semantic conventions. It represents the model - // identifier for the device - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'iPhone3,4', 'SM-G920F' - // Note: It's recommended this value represents a machine-readable version - // of the model identifier rather than the market or consumer-friendly name - // of the device. - DeviceModelIdentifierKey = attribute.Key("device.model.identifier") - - // DeviceModelNameKey is the attribute Key conforming to the - // "device.model.name" semantic conventions. It represents the marketing - // name for the device model - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'iPhone 6s Plus', 'Samsung Galaxy S6' - // Note: It's recommended this value represents a human-readable version of - // the device model rather than a machine-readable alternative. - DeviceModelNameKey = attribute.Key("device.model.name") -) - -// DeviceID returns an attribute KeyValue conforming to the "device.id" -// semantic conventions. It represents a unique identifier representing the -// device -func DeviceID(val string) attribute.KeyValue { - return DeviceIDKey.String(val) -} - -// DeviceManufacturer returns an attribute KeyValue conforming to the -// "device.manufacturer" semantic conventions. It represents the name of the -// device manufacturer -func DeviceManufacturer(val string) attribute.KeyValue { - return DeviceManufacturerKey.String(val) -} - -// DeviceModelIdentifier returns an attribute KeyValue conforming to the -// "device.model.identifier" semantic conventions. It represents the model -// identifier for the device -func DeviceModelIdentifier(val string) attribute.KeyValue { - return DeviceModelIdentifierKey.String(val) -} - -// DeviceModelName returns an attribute KeyValue conforming to the -// "device.model.name" semantic conventions. It represents the marketing name -// for the device model -func DeviceModelName(val string) attribute.KeyValue { - return DeviceModelNameKey.String(val) -} - -// A host is defined as a computing instance. For example, physical servers, -// virtual machines, switches or disk array. -const ( - // HostArchKey is the attribute Key conforming to the "host.arch" semantic - // conventions. It represents the CPU architecture the host system is - // running on. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - HostArchKey = attribute.Key("host.arch") - - // HostCPUCacheL2SizeKey is the attribute Key conforming to the - // "host.cpu.cache.l2.size" semantic conventions. It represents the amount - // of level 2 memory cache available to the processor (in Bytes). - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 12288000 - HostCPUCacheL2SizeKey = attribute.Key("host.cpu.cache.l2.size") - - // HostCPUFamilyKey is the attribute Key conforming to the - // "host.cpu.family" semantic conventions. It represents the family or - // generation of the CPU. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '6', 'PA-RISC 1.1e' - HostCPUFamilyKey = attribute.Key("host.cpu.family") - - // HostCPUModelIDKey is the attribute Key conforming to the - // "host.cpu.model.id" semantic conventions. It represents the model - // identifier. It provides more granular information about the CPU, - // distinguishing it from other CPUs within the same family. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '6', '9000/778/B180L' - HostCPUModelIDKey = attribute.Key("host.cpu.model.id") - - // HostCPUModelNameKey is the attribute Key conforming to the - // "host.cpu.model.name" semantic conventions. It represents the model - // designation of the processor. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '11th Gen Intel(R) Core(TM) i7-1185G7 @ 3.00GHz' - HostCPUModelNameKey = attribute.Key("host.cpu.model.name") - - // HostCPUSteppingKey is the attribute Key conforming to the - // "host.cpu.stepping" semantic conventions. It represents the stepping or - // core revisions. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1 - HostCPUSteppingKey = attribute.Key("host.cpu.stepping") - - // HostCPUVendorIDKey is the attribute Key conforming to the - // "host.cpu.vendor.id" semantic conventions. It represents the processor - // manufacturer identifier. A maximum 12-character string. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'GenuineIntel' - // Note: [CPUID](https://wiki.osdev.org/CPUID) command returns the vendor - // ID string in EBX, EDX and ECX registers. Writing these to memory in this - // order results in a 12-character string. - HostCPUVendorIDKey = attribute.Key("host.cpu.vendor.id") - - // HostIDKey is the attribute Key conforming to the "host.id" semantic - // conventions. It represents the unique host ID. For Cloud, this must be - // the instance_id assigned by the cloud provider. For non-containerized - // systems, this should be the `machine-id`. See the table below for the - // sources to use to determine the `machine-id` based on operating system. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'fdbf79e8af94cb7f9e8df36789187052' - HostIDKey = attribute.Key("host.id") - - // HostImageIDKey is the attribute Key conforming to the "host.image.id" - // semantic conventions. It represents the vM image ID or host OS image ID. - // For Cloud, this value is from the provider. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'ami-07b06b442921831e5' - HostImageIDKey = attribute.Key("host.image.id") - - // HostImageNameKey is the attribute Key conforming to the - // "host.image.name" semantic conventions. It represents the name of the VM - // image or OS install the host was instantiated from. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'infra-ami-eks-worker-node-7d4ec78312', 'CentOS-8-x86_64-1905' - HostImageNameKey = attribute.Key("host.image.name") - - // HostImageVersionKey is the attribute Key conforming to the - // "host.image.version" semantic conventions. It represents the version - // string of the VM image or host OS as defined in [Version - // Attributes](/docs/resource/README.md#version-attributes). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '0.1' - HostImageVersionKey = attribute.Key("host.image.version") - - // HostIPKey is the attribute Key conforming to the "host.ip" semantic - // conventions. It represents the available IP addresses of the host, - // excluding loopback interfaces. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '192.168.1.140', 'fe80::abc2:4a28:737a:609e' - // Note: IPv4 Addresses MUST be specified in dotted-quad notation. IPv6 - // addresses MUST be specified in the [RFC - // 5952](https://www.rfc-editor.org/rfc/rfc5952.html) format. - HostIPKey = attribute.Key("host.ip") - - // HostMacKey is the attribute Key conforming to the "host.mac" semantic - // conventions. It represents the available MAC addresses of the host, - // excluding loopback interfaces. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'AC-DE-48-23-45-67', 'AC-DE-48-23-45-67-01-9F' - // Note: MAC Addresses MUST be represented in [IEEE RA hexadecimal - // form](https://standards.ieee.org/wp-content/uploads/import/documents/tutorials/eui.pdf): - // as hyphen-separated octets in uppercase hexadecimal form from most to - // least significant. - HostMacKey = attribute.Key("host.mac") - - // HostNameKey is the attribute Key conforming to the "host.name" semantic - // conventions. It represents the name of the host. On Unix systems, it may - // contain what the hostname command returns, or the fully qualified - // hostname, or another name specified by the user. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry-test' - HostNameKey = attribute.Key("host.name") - - // HostTypeKey is the attribute Key conforming to the "host.type" semantic - // conventions. It represents the type of host. For Cloud, this must be the - // machine type. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'n1-standard-1' - HostTypeKey = attribute.Key("host.type") -) - -var ( - // AMD64 - HostArchAMD64 = HostArchKey.String("amd64") - // ARM32 - HostArchARM32 = HostArchKey.String("arm32") - // ARM64 - HostArchARM64 = HostArchKey.String("arm64") - // Itanium - HostArchIA64 = HostArchKey.String("ia64") - // 32-bit PowerPC - HostArchPPC32 = HostArchKey.String("ppc32") - // 64-bit PowerPC - HostArchPPC64 = HostArchKey.String("ppc64") - // IBM z/Architecture - HostArchS390x = HostArchKey.String("s390x") - // 32-bit x86 - HostArchX86 = HostArchKey.String("x86") -) - -// HostCPUCacheL2Size returns an attribute KeyValue conforming to the -// "host.cpu.cache.l2.size" semantic conventions. It represents the amount of -// level 2 memory cache available to the processor (in Bytes). -func HostCPUCacheL2Size(val int) attribute.KeyValue { - return HostCPUCacheL2SizeKey.Int(val) -} - -// HostCPUFamily returns an attribute KeyValue conforming to the -// "host.cpu.family" semantic conventions. It represents the family or -// generation of the CPU. -func HostCPUFamily(val string) attribute.KeyValue { - return HostCPUFamilyKey.String(val) -} - -// HostCPUModelID returns an attribute KeyValue conforming to the -// "host.cpu.model.id" semantic conventions. It represents the model -// identifier. It provides more granular information about the CPU, -// distinguishing it from other CPUs within the same family. -func HostCPUModelID(val string) attribute.KeyValue { - return HostCPUModelIDKey.String(val) -} - -// HostCPUModelName returns an attribute KeyValue conforming to the -// "host.cpu.model.name" semantic conventions. It represents the model -// designation of the processor. -func HostCPUModelName(val string) attribute.KeyValue { - return HostCPUModelNameKey.String(val) -} - -// HostCPUStepping returns an attribute KeyValue conforming to the -// "host.cpu.stepping" semantic conventions. It represents the stepping or core -// revisions. -func HostCPUStepping(val int) attribute.KeyValue { - return HostCPUSteppingKey.Int(val) -} - -// HostCPUVendorID returns an attribute KeyValue conforming to the -// "host.cpu.vendor.id" semantic conventions. It represents the processor -// manufacturer identifier. A maximum 12-character string. -func HostCPUVendorID(val string) attribute.KeyValue { - return HostCPUVendorIDKey.String(val) -} - -// HostID returns an attribute KeyValue conforming to the "host.id" semantic -// conventions. It represents the unique host ID. For Cloud, this must be the -// instance_id assigned by the cloud provider. For non-containerized systems, -// this should be the `machine-id`. See the table below for the sources to use -// to determine the `machine-id` based on operating system. -func HostID(val string) attribute.KeyValue { - return HostIDKey.String(val) -} - -// HostImageID returns an attribute KeyValue conforming to the -// "host.image.id" semantic conventions. It represents the vM image ID or host -// OS image ID. For Cloud, this value is from the provider. -func HostImageID(val string) attribute.KeyValue { - return HostImageIDKey.String(val) -} - -// HostImageName returns an attribute KeyValue conforming to the -// "host.image.name" semantic conventions. It represents the name of the VM -// image or OS install the host was instantiated from. -func HostImageName(val string) attribute.KeyValue { - return HostImageNameKey.String(val) -} - -// HostImageVersion returns an attribute KeyValue conforming to the -// "host.image.version" semantic conventions. It represents the version string -// of the VM image or host OS as defined in [Version -// Attributes](/docs/resource/README.md#version-attributes). -func HostImageVersion(val string) attribute.KeyValue { - return HostImageVersionKey.String(val) -} - -// HostIP returns an attribute KeyValue conforming to the "host.ip" semantic -// conventions. It represents the available IP addresses of the host, excluding -// loopback interfaces. -func HostIP(val ...string) attribute.KeyValue { - return HostIPKey.StringSlice(val) -} - -// HostMac returns an attribute KeyValue conforming to the "host.mac" -// semantic conventions. It represents the available MAC addresses of the host, -// excluding loopback interfaces. -func HostMac(val ...string) attribute.KeyValue { - return HostMacKey.StringSlice(val) -} - -// HostName returns an attribute KeyValue conforming to the "host.name" -// semantic conventions. It represents the name of the host. On Unix systems, -// it may contain what the hostname command returns, or the fully qualified -// hostname, or another name specified by the user. -func HostName(val string) attribute.KeyValue { - return HostNameKey.String(val) -} - -// HostType returns an attribute KeyValue conforming to the "host.type" -// semantic conventions. It represents the type of host. For Cloud, this must -// be the machine type. -func HostType(val string) attribute.KeyValue { - return HostTypeKey.String(val) -} - -// Kubernetes resource attributes. -const ( - // K8SClusterNameKey is the attribute Key conforming to the - // "k8s.cluster.name" semantic conventions. It represents the name of the - // cluster. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry-cluster' - K8SClusterNameKey = attribute.Key("k8s.cluster.name") - - // K8SClusterUIDKey is the attribute Key conforming to the - // "k8s.cluster.uid" semantic conventions. It represents a pseudo-ID for - // the cluster, set to the UID of the `kube-system` namespace. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '218fc5a9-a5f1-4b54-aa05-46717d0ab26d' - // Note: K8S doesn't have support for obtaining a cluster ID. If this is - // ever - // added, we will recommend collecting the `k8s.cluster.uid` through the - // official APIs. In the meantime, we are able to use the `uid` of the - // `kube-system` namespace as a proxy for cluster ID. Read on for the - // rationale. - // - // Every object created in a K8S cluster is assigned a distinct UID. The - // `kube-system` namespace is used by Kubernetes itself and will exist - // for the lifetime of the cluster. Using the `uid` of the `kube-system` - // namespace is a reasonable proxy for the K8S ClusterID as it will only - // change if the cluster is rebuilt. Furthermore, Kubernetes UIDs are - // UUIDs as standardized by - // [ISO/IEC 9834-8 and ITU-T - // X.667](https://www.itu.int/ITU-T/studygroups/com17/oid.html). - // Which states: - // - // > If generated according to one of the mechanisms defined in Rec. - // ITU-T X.667 | ISO/IEC 9834-8, a UUID is either guaranteed to be - // different from all other UUIDs generated before 3603 A.D., or is - // extremely likely to be different (depending on the mechanism chosen). - // - // Therefore, UIDs between clusters should be extremely unlikely to - // conflict. - K8SClusterUIDKey = attribute.Key("k8s.cluster.uid") - - // K8SContainerNameKey is the attribute Key conforming to the - // "k8s.container.name" semantic conventions. It represents the name of the - // Container from Pod specification, must be unique within a Pod. Container - // runtime usually uses different globally unique name (`container.name`). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'redis' - K8SContainerNameKey = attribute.Key("k8s.container.name") - - // K8SContainerRestartCountKey is the attribute Key conforming to the - // "k8s.container.restart_count" semantic conventions. It represents the - // number of times the container was restarted. This attribute can be used - // to identify a particular container (running or stopped) within a - // container spec. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 0, 2 - K8SContainerRestartCountKey = attribute.Key("k8s.container.restart_count") - - // K8SCronJobNameKey is the attribute Key conforming to the - // "k8s.cronjob.name" semantic conventions. It represents the name of the - // CronJob. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry' - K8SCronJobNameKey = attribute.Key("k8s.cronjob.name") - - // K8SCronJobUIDKey is the attribute Key conforming to the - // "k8s.cronjob.uid" semantic conventions. It represents the UID of the - // CronJob. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SCronJobUIDKey = attribute.Key("k8s.cronjob.uid") - - // K8SDaemonSetNameKey is the attribute Key conforming to the - // "k8s.daemonset.name" semantic conventions. It represents the name of the - // DaemonSet. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry' - K8SDaemonSetNameKey = attribute.Key("k8s.daemonset.name") - - // K8SDaemonSetUIDKey is the attribute Key conforming to the - // "k8s.daemonset.uid" semantic conventions. It represents the UID of the - // DaemonSet. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SDaemonSetUIDKey = attribute.Key("k8s.daemonset.uid") - - // K8SDeploymentNameKey is the attribute Key conforming to the - // "k8s.deployment.name" semantic conventions. It represents the name of - // the Deployment. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry' - K8SDeploymentNameKey = attribute.Key("k8s.deployment.name") - - // K8SDeploymentUIDKey is the attribute Key conforming to the - // "k8s.deployment.uid" semantic conventions. It represents the UID of the - // Deployment. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SDeploymentUIDKey = attribute.Key("k8s.deployment.uid") - - // K8SJobNameKey is the attribute Key conforming to the "k8s.job.name" - // semantic conventions. It represents the name of the Job. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry' - K8SJobNameKey = attribute.Key("k8s.job.name") - - // K8SJobUIDKey is the attribute Key conforming to the "k8s.job.uid" - // semantic conventions. It represents the UID of the Job. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SJobUIDKey = attribute.Key("k8s.job.uid") - - // K8SNamespaceNameKey is the attribute Key conforming to the - // "k8s.namespace.name" semantic conventions. It represents the name of the - // namespace that the pod is running in. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'default' - K8SNamespaceNameKey = attribute.Key("k8s.namespace.name") - - // K8SNodeNameKey is the attribute Key conforming to the "k8s.node.name" - // semantic conventions. It represents the name of the Node. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'node-1' - K8SNodeNameKey = attribute.Key("k8s.node.name") - - // K8SNodeUIDKey is the attribute Key conforming to the "k8s.node.uid" - // semantic conventions. It represents the UID of the Node. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1eb3a0c6-0477-4080-a9cb-0cb7db65c6a2' - K8SNodeUIDKey = attribute.Key("k8s.node.uid") - - // K8SPodNameKey is the attribute Key conforming to the "k8s.pod.name" - // semantic conventions. It represents the name of the Pod. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry-pod-autoconf' - K8SPodNameKey = attribute.Key("k8s.pod.name") - - // K8SPodUIDKey is the attribute Key conforming to the "k8s.pod.uid" - // semantic conventions. It represents the UID of the Pod. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SPodUIDKey = attribute.Key("k8s.pod.uid") - - // K8SReplicaSetNameKey is the attribute Key conforming to the - // "k8s.replicaset.name" semantic conventions. It represents the name of - // the ReplicaSet. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry' - K8SReplicaSetNameKey = attribute.Key("k8s.replicaset.name") - - // K8SReplicaSetUIDKey is the attribute Key conforming to the - // "k8s.replicaset.uid" semantic conventions. It represents the UID of the - // ReplicaSet. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SReplicaSetUIDKey = attribute.Key("k8s.replicaset.uid") - - // K8SStatefulSetNameKey is the attribute Key conforming to the - // "k8s.statefulset.name" semantic conventions. It represents the name of - // the StatefulSet. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry' - K8SStatefulSetNameKey = attribute.Key("k8s.statefulset.name") - - // K8SStatefulSetUIDKey is the attribute Key conforming to the - // "k8s.statefulset.uid" semantic conventions. It represents the UID of the - // StatefulSet. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '275ecb36-5aa8-4c2a-9c47-d8bb681b9aff' - K8SStatefulSetUIDKey = attribute.Key("k8s.statefulset.uid") -) - -// K8SClusterName returns an attribute KeyValue conforming to the -// "k8s.cluster.name" semantic conventions. It represents the name of the -// cluster. -func K8SClusterName(val string) attribute.KeyValue { - return K8SClusterNameKey.String(val) -} - -// K8SClusterUID returns an attribute KeyValue conforming to the -// "k8s.cluster.uid" semantic conventions. It represents a pseudo-ID for the -// cluster, set to the UID of the `kube-system` namespace. -func K8SClusterUID(val string) attribute.KeyValue { - return K8SClusterUIDKey.String(val) -} - -// K8SContainerName returns an attribute KeyValue conforming to the -// "k8s.container.name" semantic conventions. It represents the name of the -// Container from Pod specification, must be unique within a Pod. Container -// runtime usually uses different globally unique name (`container.name`). -func K8SContainerName(val string) attribute.KeyValue { - return K8SContainerNameKey.String(val) -} - -// K8SContainerRestartCount returns an attribute KeyValue conforming to the -// "k8s.container.restart_count" semantic conventions. It represents the number -// of times the container was restarted. This attribute can be used to identify -// a particular container (running or stopped) within a container spec. -func K8SContainerRestartCount(val int) attribute.KeyValue { - return K8SContainerRestartCountKey.Int(val) -} - -// K8SCronJobName returns an attribute KeyValue conforming to the -// "k8s.cronjob.name" semantic conventions. It represents the name of the -// CronJob. -func K8SCronJobName(val string) attribute.KeyValue { - return K8SCronJobNameKey.String(val) -} - -// K8SCronJobUID returns an attribute KeyValue conforming to the -// "k8s.cronjob.uid" semantic conventions. It represents the UID of the -// CronJob. -func K8SCronJobUID(val string) attribute.KeyValue { - return K8SCronJobUIDKey.String(val) -} - -// K8SDaemonSetName returns an attribute KeyValue conforming to the -// "k8s.daemonset.name" semantic conventions. It represents the name of the -// DaemonSet. -func K8SDaemonSetName(val string) attribute.KeyValue { - return K8SDaemonSetNameKey.String(val) -} - -// K8SDaemonSetUID returns an attribute KeyValue conforming to the -// "k8s.daemonset.uid" semantic conventions. It represents the UID of the -// DaemonSet. -func K8SDaemonSetUID(val string) attribute.KeyValue { - return K8SDaemonSetUIDKey.String(val) -} - -// K8SDeploymentName returns an attribute KeyValue conforming to the -// "k8s.deployment.name" semantic conventions. It represents the name of the -// Deployment. -func K8SDeploymentName(val string) attribute.KeyValue { - return K8SDeploymentNameKey.String(val) -} - -// K8SDeploymentUID returns an attribute KeyValue conforming to the -// "k8s.deployment.uid" semantic conventions. It represents the UID of the -// Deployment. -func K8SDeploymentUID(val string) attribute.KeyValue { - return K8SDeploymentUIDKey.String(val) -} - -// K8SJobName returns an attribute KeyValue conforming to the "k8s.job.name" -// semantic conventions. It represents the name of the Job. -func K8SJobName(val string) attribute.KeyValue { - return K8SJobNameKey.String(val) -} - -// K8SJobUID returns an attribute KeyValue conforming to the "k8s.job.uid" -// semantic conventions. It represents the UID of the Job. -func K8SJobUID(val string) attribute.KeyValue { - return K8SJobUIDKey.String(val) -} - -// K8SNamespaceName returns an attribute KeyValue conforming to the -// "k8s.namespace.name" semantic conventions. It represents the name of the -// namespace that the pod is running in. -func K8SNamespaceName(val string) attribute.KeyValue { - return K8SNamespaceNameKey.String(val) -} - -// K8SNodeName returns an attribute KeyValue conforming to the -// "k8s.node.name" semantic conventions. It represents the name of the Node. -func K8SNodeName(val string) attribute.KeyValue { - return K8SNodeNameKey.String(val) -} - -// K8SNodeUID returns an attribute KeyValue conforming to the "k8s.node.uid" -// semantic conventions. It represents the UID of the Node. -func K8SNodeUID(val string) attribute.KeyValue { - return K8SNodeUIDKey.String(val) -} - -// K8SPodName returns an attribute KeyValue conforming to the "k8s.pod.name" -// semantic conventions. It represents the name of the Pod. -func K8SPodName(val string) attribute.KeyValue { - return K8SPodNameKey.String(val) -} - -// K8SPodUID returns an attribute KeyValue conforming to the "k8s.pod.uid" -// semantic conventions. It represents the UID of the Pod. -func K8SPodUID(val string) attribute.KeyValue { - return K8SPodUIDKey.String(val) -} - -// K8SReplicaSetName returns an attribute KeyValue conforming to the -// "k8s.replicaset.name" semantic conventions. It represents the name of the -// ReplicaSet. -func K8SReplicaSetName(val string) attribute.KeyValue { - return K8SReplicaSetNameKey.String(val) -} - -// K8SReplicaSetUID returns an attribute KeyValue conforming to the -// "k8s.replicaset.uid" semantic conventions. It represents the UID of the -// ReplicaSet. -func K8SReplicaSetUID(val string) attribute.KeyValue { - return K8SReplicaSetUIDKey.String(val) -} - -// K8SStatefulSetName returns an attribute KeyValue conforming to the -// "k8s.statefulset.name" semantic conventions. It represents the name of the -// StatefulSet. -func K8SStatefulSetName(val string) attribute.KeyValue { - return K8SStatefulSetNameKey.String(val) -} - -// K8SStatefulSetUID returns an attribute KeyValue conforming to the -// "k8s.statefulset.uid" semantic conventions. It represents the UID of the -// StatefulSet. -func K8SStatefulSetUID(val string) attribute.KeyValue { - return K8SStatefulSetUIDKey.String(val) -} - -// An OCI image manifest. -const ( - // OciManifestDigestKey is the attribute Key conforming to the - // "oci.manifest.digest" semantic conventions. It represents the digest of - // the OCI image manifest. For container images specifically is the digest - // by which the container image is known. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'sha256:e4ca62c0d62f3e886e684806dfe9d4e0cda60d54986898173c1083856cfda0f4' - // Note: Follows [OCI Image Manifest - // Specification](https://github.com/opencontainers/image-spec/blob/main/manifest.md), - // and specifically the [Digest - // property](https://github.com/opencontainers/image-spec/blob/main/descriptor.md#digests). - // An example can be found in [Example Image - // Manifest](https://docs.docker.com/registry/spec/manifest-v2-2/#example-image-manifest). - OciManifestDigestKey = attribute.Key("oci.manifest.digest") -) - -// OciManifestDigest returns an attribute KeyValue conforming to the -// "oci.manifest.digest" semantic conventions. It represents the digest of the -// OCI image manifest. For container images specifically is the digest by which -// the container image is known. -func OciManifestDigest(val string) attribute.KeyValue { - return OciManifestDigestKey.String(val) -} - -// The operating system (OS) on which the process represented by this resource -// is running. -const ( - // OSBuildIDKey is the attribute Key conforming to the "os.build_id" - // semantic conventions. It represents the unique identifier for a - // particular build or compilation of the operating system. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'TQ3C.230805.001.B2', '20E247', '22621' - OSBuildIDKey = attribute.Key("os.build_id") - - // OSDescriptionKey is the attribute Key conforming to the "os.description" - // semantic conventions. It represents the human readable (not intended to - // be parsed) OS version information, like e.g. reported by `ver` or - // `lsb_release -a` commands. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Microsoft Windows [Version 10.0.18363.778]', 'Ubuntu 18.04.1 - // LTS' - OSDescriptionKey = attribute.Key("os.description") - - // OSNameKey is the attribute Key conforming to the "os.name" semantic - // conventions. It represents the human readable operating system name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'iOS', 'Android', 'Ubuntu' - OSNameKey = attribute.Key("os.name") - - // OSTypeKey is the attribute Key conforming to the "os.type" semantic - // conventions. It represents the operating system type. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - OSTypeKey = attribute.Key("os.type") - - // OSVersionKey is the attribute Key conforming to the "os.version" - // semantic conventions. It represents the version string of the operating - // system as defined in [Version - // Attributes](/docs/resource/README.md#version-attributes). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '14.2.1', '18.04.1' - OSVersionKey = attribute.Key("os.version") -) - -var ( - // Microsoft Windows - OSTypeWindows = OSTypeKey.String("windows") - // Linux - OSTypeLinux = OSTypeKey.String("linux") - // Apple Darwin - OSTypeDarwin = OSTypeKey.String("darwin") - // FreeBSD - OSTypeFreeBSD = OSTypeKey.String("freebsd") - // NetBSD - OSTypeNetBSD = OSTypeKey.String("netbsd") - // OpenBSD - OSTypeOpenBSD = OSTypeKey.String("openbsd") - // DragonFly BSD - OSTypeDragonflyBSD = OSTypeKey.String("dragonflybsd") - // HP-UX (Hewlett Packard Unix) - OSTypeHPUX = OSTypeKey.String("hpux") - // AIX (Advanced Interactive eXecutive) - OSTypeAIX = OSTypeKey.String("aix") - // SunOS, Oracle Solaris - OSTypeSolaris = OSTypeKey.String("solaris") - // IBM z/OS - OSTypeZOS = OSTypeKey.String("z_os") -) - -// OSBuildID returns an attribute KeyValue conforming to the "os.build_id" -// semantic conventions. It represents the unique identifier for a particular -// build or compilation of the operating system. -func OSBuildID(val string) attribute.KeyValue { - return OSBuildIDKey.String(val) -} - -// OSDescription returns an attribute KeyValue conforming to the -// "os.description" semantic conventions. It represents the human readable (not -// intended to be parsed) OS version information, like e.g. reported by `ver` -// or `lsb_release -a` commands. -func OSDescription(val string) attribute.KeyValue { - return OSDescriptionKey.String(val) -} - -// OSName returns an attribute KeyValue conforming to the "os.name" semantic -// conventions. It represents the human readable operating system name. -func OSName(val string) attribute.KeyValue { - return OSNameKey.String(val) -} - -// OSVersion returns an attribute KeyValue conforming to the "os.version" -// semantic conventions. It represents the version string of the operating -// system as defined in [Version -// Attributes](/docs/resource/README.md#version-attributes). -func OSVersion(val string) attribute.KeyValue { - return OSVersionKey.String(val) -} - -// An operating system process. -const ( - // ProcessCommandKey is the attribute Key conforming to the - // "process.command" semantic conventions. It represents the command used - // to launch the process (i.e. the command name). On Linux based systems, - // can be set to the zeroth string in `proc/[pid]/cmdline`. On Windows, can - // be set to the first parameter extracted from `GetCommandLineW`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'cmd/otelcol' - ProcessCommandKey = attribute.Key("process.command") - - // ProcessCommandArgsKey is the attribute Key conforming to the - // "process.command_args" semantic conventions. It represents the all the - // command arguments (including the command/executable itself) as received - // by the process. On Linux-based systems (and some other Unixoid systems - // supporting procfs), can be set according to the list of null-delimited - // strings extracted from `proc/[pid]/cmdline`. For libc-based executables, - // this would be the full argv vector passed to `main`. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'cmd/otecol', '--config=config.yaml' - ProcessCommandArgsKey = attribute.Key("process.command_args") - - // ProcessCommandLineKey is the attribute Key conforming to the - // "process.command_line" semantic conventions. It represents the full - // command used to launch the process as a single string representing the - // full command. On Windows, can be set to the result of `GetCommandLineW`. - // Do not set this if you have to assemble it just for monitoring; use - // `process.command_args` instead. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'C:\\cmd\\otecol --config="my directory\\config.yaml"' - ProcessCommandLineKey = attribute.Key("process.command_line") - - // ProcessExecutableNameKey is the attribute Key conforming to the - // "process.executable.name" semantic conventions. It represents the name - // of the process executable. On Linux based systems, can be set to the - // `Name` in `proc/[pid]/status`. On Windows, can be set to the base name - // of `GetProcessImageFileNameW`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'otelcol' - ProcessExecutableNameKey = attribute.Key("process.executable.name") - - // ProcessExecutablePathKey is the attribute Key conforming to the - // "process.executable.path" semantic conventions. It represents the full - // path to the process executable. On Linux based systems, can be set to - // the target of `proc/[pid]/exe`. On Windows, can be set to the result of - // `GetProcessImageFileNameW`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/usr/bin/cmd/otelcol' - ProcessExecutablePathKey = attribute.Key("process.executable.path") - - // ProcessOwnerKey is the attribute Key conforming to the "process.owner" - // semantic conventions. It represents the username of the user that owns - // the process. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'root' - ProcessOwnerKey = attribute.Key("process.owner") - - // ProcessParentPIDKey is the attribute Key conforming to the - // "process.parent_pid" semantic conventions. It represents the parent - // Process identifier (PPID). - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 111 - ProcessParentPIDKey = attribute.Key("process.parent_pid") - - // ProcessPIDKey is the attribute Key conforming to the "process.pid" - // semantic conventions. It represents the process identifier (PID). - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1234 - ProcessPIDKey = attribute.Key("process.pid") - - // ProcessRuntimeDescriptionKey is the attribute Key conforming to the - // "process.runtime.description" semantic conventions. It represents an - // additional description about the runtime of the process, for example a - // specific vendor customization of the runtime environment. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Eclipse OpenJ9 Eclipse OpenJ9 VM openj9-0.21.0' - ProcessRuntimeDescriptionKey = attribute.Key("process.runtime.description") - - // ProcessRuntimeNameKey is the attribute Key conforming to the - // "process.runtime.name" semantic conventions. It represents the name of - // the runtime of this process. For compiled native binaries, this SHOULD - // be the name of the compiler. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'OpenJDK Runtime Environment' - ProcessRuntimeNameKey = attribute.Key("process.runtime.name") - - // ProcessRuntimeVersionKey is the attribute Key conforming to the - // "process.runtime.version" semantic conventions. It represents the - // version of the runtime of this process, as returned by the runtime - // without modification. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '14.0.2' - ProcessRuntimeVersionKey = attribute.Key("process.runtime.version") -) - -// ProcessCommand returns an attribute KeyValue conforming to the -// "process.command" semantic conventions. It represents the command used to -// launch the process (i.e. the command name). On Linux based systems, can be -// set to the zeroth string in `proc/[pid]/cmdline`. On Windows, can be set to -// the first parameter extracted from `GetCommandLineW`. -func ProcessCommand(val string) attribute.KeyValue { - return ProcessCommandKey.String(val) -} - -// ProcessCommandArgs returns an attribute KeyValue conforming to the -// "process.command_args" semantic conventions. It represents the all the -// command arguments (including the command/executable itself) as received by -// the process. On Linux-based systems (and some other Unixoid systems -// supporting procfs), can be set according to the list of null-delimited -// strings extracted from `proc/[pid]/cmdline`. For libc-based executables, -// this would be the full argv vector passed to `main`. -func ProcessCommandArgs(val ...string) attribute.KeyValue { - return ProcessCommandArgsKey.StringSlice(val) -} - -// ProcessCommandLine returns an attribute KeyValue conforming to the -// "process.command_line" semantic conventions. It represents the full command -// used to launch the process as a single string representing the full command. -// On Windows, can be set to the result of `GetCommandLineW`. Do not set this -// if you have to assemble it just for monitoring; use `process.command_args` -// instead. -func ProcessCommandLine(val string) attribute.KeyValue { - return ProcessCommandLineKey.String(val) -} - -// ProcessExecutableName returns an attribute KeyValue conforming to the -// "process.executable.name" semantic conventions. It represents the name of -// the process executable. On Linux based systems, can be set to the `Name` in -// `proc/[pid]/status`. On Windows, can be set to the base name of -// `GetProcessImageFileNameW`. -func ProcessExecutableName(val string) attribute.KeyValue { - return ProcessExecutableNameKey.String(val) -} - -// ProcessExecutablePath returns an attribute KeyValue conforming to the -// "process.executable.path" semantic conventions. It represents the full path -// to the process executable. On Linux based systems, can be set to the target -// of `proc/[pid]/exe`. On Windows, can be set to the result of -// `GetProcessImageFileNameW`. -func ProcessExecutablePath(val string) attribute.KeyValue { - return ProcessExecutablePathKey.String(val) -} - -// ProcessOwner returns an attribute KeyValue conforming to the -// "process.owner" semantic conventions. It represents the username of the user -// that owns the process. -func ProcessOwner(val string) attribute.KeyValue { - return ProcessOwnerKey.String(val) -} - -// ProcessParentPID returns an attribute KeyValue conforming to the -// "process.parent_pid" semantic conventions. It represents the parent Process -// identifier (PPID). -func ProcessParentPID(val int) attribute.KeyValue { - return ProcessParentPIDKey.Int(val) -} - -// ProcessPID returns an attribute KeyValue conforming to the "process.pid" -// semantic conventions. It represents the process identifier (PID). -func ProcessPID(val int) attribute.KeyValue { - return ProcessPIDKey.Int(val) -} - -// ProcessRuntimeDescription returns an attribute KeyValue conforming to the -// "process.runtime.description" semantic conventions. It represents an -// additional description about the runtime of the process, for example a -// specific vendor customization of the runtime environment. -func ProcessRuntimeDescription(val string) attribute.KeyValue { - return ProcessRuntimeDescriptionKey.String(val) -} - -// ProcessRuntimeName returns an attribute KeyValue conforming to the -// "process.runtime.name" semantic conventions. It represents the name of the -// runtime of this process. For compiled native binaries, this SHOULD be the -// name of the compiler. -func ProcessRuntimeName(val string) attribute.KeyValue { - return ProcessRuntimeNameKey.String(val) -} - -// ProcessRuntimeVersion returns an attribute KeyValue conforming to the -// "process.runtime.version" semantic conventions. It represents the version of -// the runtime of this process, as returned by the runtime without -// modification. -func ProcessRuntimeVersion(val string) attribute.KeyValue { - return ProcessRuntimeVersionKey.String(val) -} - -// The Android platform on which the Android application is running. -const ( - // AndroidOSAPILevelKey is the attribute Key conforming to the - // "android.os.api_level" semantic conventions. It represents the uniquely - // identifies the framework API revision offered by a version - // (`os.version`) of the android operating system. More information can be - // found - // [here](https://developer.android.com/guide/topics/manifest/uses-sdk-element#APILevels). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '33', '32' - AndroidOSAPILevelKey = attribute.Key("android.os.api_level") -) - -// AndroidOSAPILevel returns an attribute KeyValue conforming to the -// "android.os.api_level" semantic conventions. It represents the uniquely -// identifies the framework API revision offered by a version (`os.version`) of -// the android operating system. More information can be found -// [here](https://developer.android.com/guide/topics/manifest/uses-sdk-element#APILevels). -func AndroidOSAPILevel(val string) attribute.KeyValue { - return AndroidOSAPILevelKey.String(val) -} - -// The web browser in which the application represented by the resource is -// running. The `browser.*` attributes MUST be used only for resources that -// represent applications running in a web browser (regardless of whether -// running on a mobile or desktop device). -const ( - // BrowserBrandsKey is the attribute Key conforming to the "browser.brands" - // semantic conventions. It represents the array of brand name and version - // separated by a space - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: ' Not A;Brand 99', 'Chromium 99', 'Chrome 99' - // Note: This value is intended to be taken from the [UA client hints - // API](https://wicg.github.io/ua-client-hints/#interface) - // (`navigator.userAgentData.brands`). - BrowserBrandsKey = attribute.Key("browser.brands") - - // BrowserLanguageKey is the attribute Key conforming to the - // "browser.language" semantic conventions. It represents the preferred - // language of the user using the browser - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'en', 'en-US', 'fr', 'fr-FR' - // Note: This value is intended to be taken from the Navigator API - // `navigator.language`. - BrowserLanguageKey = attribute.Key("browser.language") - - // BrowserMobileKey is the attribute Key conforming to the "browser.mobile" - // semantic conventions. It represents a boolean that is true if the - // browser is running on a mobile device - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - // Note: This value is intended to be taken from the [UA client hints - // API](https://wicg.github.io/ua-client-hints/#interface) - // (`navigator.userAgentData.mobile`). If unavailable, this attribute - // SHOULD be left unset. - BrowserMobileKey = attribute.Key("browser.mobile") - - // BrowserPlatformKey is the attribute Key conforming to the - // "browser.platform" semantic conventions. It represents the platform on - // which the browser is running - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Windows', 'macOS', 'Android' - // Note: This value is intended to be taken from the [UA client hints - // API](https://wicg.github.io/ua-client-hints/#interface) - // (`navigator.userAgentData.platform`). If unavailable, the legacy - // `navigator.platform` API SHOULD NOT be used instead and this attribute - // SHOULD be left unset in order for the values to be consistent. - // The list of possible values is defined in the [W3C User-Agent Client - // Hints - // specification](https://wicg.github.io/ua-client-hints/#sec-ch-ua-platform). - // Note that some (but not all) of these values can overlap with values in - // the [`os.type` and `os.name` attributes](./os.md). However, for - // consistency, the values in the `browser.platform` attribute should - // capture the exact value that the user agent provides. - BrowserPlatformKey = attribute.Key("browser.platform") -) - -// BrowserBrands returns an attribute KeyValue conforming to the -// "browser.brands" semantic conventions. It represents the array of brand name -// and version separated by a space -func BrowserBrands(val ...string) attribute.KeyValue { - return BrowserBrandsKey.StringSlice(val) -} - -// BrowserLanguage returns an attribute KeyValue conforming to the -// "browser.language" semantic conventions. It represents the preferred -// language of the user using the browser -func BrowserLanguage(val string) attribute.KeyValue { - return BrowserLanguageKey.String(val) -} - -// BrowserMobile returns an attribute KeyValue conforming to the -// "browser.mobile" semantic conventions. It represents a boolean that is true -// if the browser is running on a mobile device -func BrowserMobile(val bool) attribute.KeyValue { - return BrowserMobileKey.Bool(val) -} - -// BrowserPlatform returns an attribute KeyValue conforming to the -// "browser.platform" semantic conventions. It represents the platform on which -// the browser is running -func BrowserPlatform(val string) attribute.KeyValue { - return BrowserPlatformKey.String(val) -} - -// Resources used by AWS Elastic Container Service (ECS). -const ( - // AWSECSClusterARNKey is the attribute Key conforming to the - // "aws.ecs.cluster.arn" semantic conventions. It represents the ARN of an - // [ECS - // cluster](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/clusters.html). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'arn:aws:ecs:us-west-2:123456789123:cluster/my-cluster' - AWSECSClusterARNKey = attribute.Key("aws.ecs.cluster.arn") - - // AWSECSContainerARNKey is the attribute Key conforming to the - // "aws.ecs.container.arn" semantic conventions. It represents the Amazon - // Resource Name (ARN) of an [ECS container - // instance](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/ECS_instances.html). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'arn:aws:ecs:us-west-1:123456789123:container/32624152-9086-4f0e-acae-1a75b14fe4d9' - AWSECSContainerARNKey = attribute.Key("aws.ecs.container.arn") - - // AWSECSLaunchtypeKey is the attribute Key conforming to the - // "aws.ecs.launchtype" semantic conventions. It represents the [launch - // type](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/launch_types.html) - // for an ECS task. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - AWSECSLaunchtypeKey = attribute.Key("aws.ecs.launchtype") - - // AWSECSTaskARNKey is the attribute Key conforming to the - // "aws.ecs.task.arn" semantic conventions. It represents the ARN of an - // [ECS task - // definition](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task_definitions.html). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'arn:aws:ecs:us-west-1:123456789123:task/10838bed-421f-43ef-870a-f43feacbbb5b' - AWSECSTaskARNKey = attribute.Key("aws.ecs.task.arn") - - // AWSECSTaskFamilyKey is the attribute Key conforming to the - // "aws.ecs.task.family" semantic conventions. It represents the task - // definition family this task definition is a member of. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'opentelemetry-family' - AWSECSTaskFamilyKey = attribute.Key("aws.ecs.task.family") - - // AWSECSTaskRevisionKey is the attribute Key conforming to the - // "aws.ecs.task.revision" semantic conventions. It represents the revision - // for this task definition. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '8', '26' - AWSECSTaskRevisionKey = attribute.Key("aws.ecs.task.revision") -) - -var ( - // ec2 - AWSECSLaunchtypeEC2 = AWSECSLaunchtypeKey.String("ec2") - // fargate - AWSECSLaunchtypeFargate = AWSECSLaunchtypeKey.String("fargate") -) - -// AWSECSClusterARN returns an attribute KeyValue conforming to the -// "aws.ecs.cluster.arn" semantic conventions. It represents the ARN of an [ECS -// cluster](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/clusters.html). -func AWSECSClusterARN(val string) attribute.KeyValue { - return AWSECSClusterARNKey.String(val) -} - -// AWSECSContainerARN returns an attribute KeyValue conforming to the -// "aws.ecs.container.arn" semantic conventions. It represents the Amazon -// Resource Name (ARN) of an [ECS container -// instance](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/ECS_instances.html). -func AWSECSContainerARN(val string) attribute.KeyValue { - return AWSECSContainerARNKey.String(val) -} - -// AWSECSTaskARN returns an attribute KeyValue conforming to the -// "aws.ecs.task.arn" semantic conventions. It represents the ARN of an [ECS -// task -// definition](https://docs.aws.amazon.com/AmazonECS/latest/developerguide/task_definitions.html). -func AWSECSTaskARN(val string) attribute.KeyValue { - return AWSECSTaskARNKey.String(val) -} - -// AWSECSTaskFamily returns an attribute KeyValue conforming to the -// "aws.ecs.task.family" semantic conventions. It represents the task -// definition family this task definition is a member of. -func AWSECSTaskFamily(val string) attribute.KeyValue { - return AWSECSTaskFamilyKey.String(val) -} - -// AWSECSTaskRevision returns an attribute KeyValue conforming to the -// "aws.ecs.task.revision" semantic conventions. It represents the revision for -// this task definition. -func AWSECSTaskRevision(val string) attribute.KeyValue { - return AWSECSTaskRevisionKey.String(val) -} - -// Resources used by AWS Elastic Kubernetes Service (EKS). -const ( - // AWSEKSClusterARNKey is the attribute Key conforming to the - // "aws.eks.cluster.arn" semantic conventions. It represents the ARN of an - // EKS cluster. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'arn:aws:ecs:us-west-2:123456789123:cluster/my-cluster' - AWSEKSClusterARNKey = attribute.Key("aws.eks.cluster.arn") -) - -// AWSEKSClusterARN returns an attribute KeyValue conforming to the -// "aws.eks.cluster.arn" semantic conventions. It represents the ARN of an EKS -// cluster. -func AWSEKSClusterARN(val string) attribute.KeyValue { - return AWSEKSClusterARNKey.String(val) -} - -// Resources specific to Amazon Web Services. -const ( - // AWSLogGroupARNsKey is the attribute Key conforming to the - // "aws.log.group.arns" semantic conventions. It represents the Amazon - // Resource Name(s) (ARN) of the AWS log group(s). - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'arn:aws:logs:us-west-1:123456789012:log-group:/aws/my/group:*' - // Note: See the [log group ARN format - // documentation](https://docs.aws.amazon.com/AmazonCloudWatch/latest/logs/iam-access-control-overview-cwl.html#CWL_ARN_Format). - AWSLogGroupARNsKey = attribute.Key("aws.log.group.arns") - - // AWSLogGroupNamesKey is the attribute Key conforming to the - // "aws.log.group.names" semantic conventions. It represents the name(s) of - // the AWS log group(s) an application is writing to. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/aws/lambda/my-function', 'opentelemetry-service' - // Note: Multiple log groups must be supported for cases like - // multi-container applications, where a single application has sidecar - // containers, and each write to their own log group. - AWSLogGroupNamesKey = attribute.Key("aws.log.group.names") - - // AWSLogStreamARNsKey is the attribute Key conforming to the - // "aws.log.stream.arns" semantic conventions. It represents the ARN(s) of - // the AWS log stream(s). - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'arn:aws:logs:us-west-1:123456789012:log-group:/aws/my/group:log-stream:logs/main/10838bed-421f-43ef-870a-f43feacbbb5b' - // Note: See the [log stream ARN format - // documentation](https://docs.aws.amazon.com/AmazonCloudWatch/latest/logs/iam-access-control-overview-cwl.html#CWL_ARN_Format). - // One log group can contain several log streams, so these ARNs necessarily - // identify both a log group and a log stream. - AWSLogStreamARNsKey = attribute.Key("aws.log.stream.arns") - - // AWSLogStreamNamesKey is the attribute Key conforming to the - // "aws.log.stream.names" semantic conventions. It represents the name(s) - // of the AWS log stream(s) an application is writing to. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'logs/main/10838bed-421f-43ef-870a-f43feacbbb5b' - AWSLogStreamNamesKey = attribute.Key("aws.log.stream.names") -) - -// AWSLogGroupARNs returns an attribute KeyValue conforming to the -// "aws.log.group.arns" semantic conventions. It represents the Amazon Resource -// Name(s) (ARN) of the AWS log group(s). -func AWSLogGroupARNs(val ...string) attribute.KeyValue { - return AWSLogGroupARNsKey.StringSlice(val) -} - -// AWSLogGroupNames returns an attribute KeyValue conforming to the -// "aws.log.group.names" semantic conventions. It represents the name(s) of the -// AWS log group(s) an application is writing to. -func AWSLogGroupNames(val ...string) attribute.KeyValue { - return AWSLogGroupNamesKey.StringSlice(val) -} - -// AWSLogStreamARNs returns an attribute KeyValue conforming to the -// "aws.log.stream.arns" semantic conventions. It represents the ARN(s) of the -// AWS log stream(s). -func AWSLogStreamARNs(val ...string) attribute.KeyValue { - return AWSLogStreamARNsKey.StringSlice(val) -} - -// AWSLogStreamNames returns an attribute KeyValue conforming to the -// "aws.log.stream.names" semantic conventions. It represents the name(s) of -// the AWS log stream(s) an application is writing to. -func AWSLogStreamNames(val ...string) attribute.KeyValue { - return AWSLogStreamNamesKey.StringSlice(val) -} - -// Resource used by Google Cloud Run. -const ( - // GCPCloudRunJobExecutionKey is the attribute Key conforming to the - // "gcp.cloud_run.job.execution" semantic conventions. It represents the - // name of the Cloud Run - // [execution](https://cloud.google.com/run/docs/managing/job-executions) - // being run for the Job, as set by the - // [`CLOUD_RUN_EXECUTION`](https://cloud.google.com/run/docs/container-contract#jobs-env-vars) - // environment variable. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'job-name-xxxx', 'sample-job-mdw84' - GCPCloudRunJobExecutionKey = attribute.Key("gcp.cloud_run.job.execution") - - // GCPCloudRunJobTaskIndexKey is the attribute Key conforming to the - // "gcp.cloud_run.job.task_index" semantic conventions. It represents the - // index for a task within an execution as provided by the - // [`CLOUD_RUN_TASK_INDEX`](https://cloud.google.com/run/docs/container-contract#jobs-env-vars) - // environment variable. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 0, 1 - GCPCloudRunJobTaskIndexKey = attribute.Key("gcp.cloud_run.job.task_index") -) - -// GCPCloudRunJobExecution returns an attribute KeyValue conforming to the -// "gcp.cloud_run.job.execution" semantic conventions. It represents the name -// of the Cloud Run -// [execution](https://cloud.google.com/run/docs/managing/job-executions) being -// run for the Job, as set by the -// [`CLOUD_RUN_EXECUTION`](https://cloud.google.com/run/docs/container-contract#jobs-env-vars) -// environment variable. -func GCPCloudRunJobExecution(val string) attribute.KeyValue { - return GCPCloudRunJobExecutionKey.String(val) -} - -// GCPCloudRunJobTaskIndex returns an attribute KeyValue conforming to the -// "gcp.cloud_run.job.task_index" semantic conventions. It represents the index -// for a task within an execution as provided by the -// [`CLOUD_RUN_TASK_INDEX`](https://cloud.google.com/run/docs/container-contract#jobs-env-vars) -// environment variable. -func GCPCloudRunJobTaskIndex(val int) attribute.KeyValue { - return GCPCloudRunJobTaskIndexKey.Int(val) -} - -// Resources used by Google Compute Engine (GCE). -const ( - // GCPGceInstanceHostnameKey is the attribute Key conforming to the - // "gcp.gce.instance.hostname" semantic conventions. It represents the - // hostname of a GCE instance. This is the full value of the default or - // [custom - // hostname](https://cloud.google.com/compute/docs/instances/custom-hostname-vm). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'my-host1234.example.com', - // 'sample-vm.us-west1-b.c.my-project.internal' - GCPGceInstanceHostnameKey = attribute.Key("gcp.gce.instance.hostname") - - // GCPGceInstanceNameKey is the attribute Key conforming to the - // "gcp.gce.instance.name" semantic conventions. It represents the instance - // name of a GCE instance. This is the value provided by `host.name`, the - // visible name of the instance in the Cloud Console UI, and the prefix for - // the default hostname of the instance as defined by the [default internal - // DNS - // name](https://cloud.google.com/compute/docs/internal-dns#instance-fully-qualified-domain-names). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'instance-1', 'my-vm-name' - GCPGceInstanceNameKey = attribute.Key("gcp.gce.instance.name") -) - -// GCPGceInstanceHostname returns an attribute KeyValue conforming to the -// "gcp.gce.instance.hostname" semantic conventions. It represents the hostname -// of a GCE instance. This is the full value of the default or [custom -// hostname](https://cloud.google.com/compute/docs/instances/custom-hostname-vm). -func GCPGceInstanceHostname(val string) attribute.KeyValue { - return GCPGceInstanceHostnameKey.String(val) -} - -// GCPGceInstanceName returns an attribute KeyValue conforming to the -// "gcp.gce.instance.name" semantic conventions. It represents the instance -// name of a GCE instance. This is the value provided by `host.name`, the -// visible name of the instance in the Cloud Console UI, and the prefix for the -// default hostname of the instance as defined by the [default internal DNS -// name](https://cloud.google.com/compute/docs/internal-dns#instance-fully-qualified-domain-names). -func GCPGceInstanceName(val string) attribute.KeyValue { - return GCPGceInstanceNameKey.String(val) -} - -// Heroku dyno metadata -const ( - // HerokuAppIDKey is the attribute Key conforming to the "heroku.app.id" - // semantic conventions. It represents the unique identifier for the - // application - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2daa2797-e42b-4624-9322-ec3f968df4da' - HerokuAppIDKey = attribute.Key("heroku.app.id") - - // HerokuReleaseCommitKey is the attribute Key conforming to the - // "heroku.release.commit" semantic conventions. It represents the commit - // hash for the current release - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'e6134959463efd8966b20e75b913cafe3f5ec' - HerokuReleaseCommitKey = attribute.Key("heroku.release.commit") - - // HerokuReleaseCreationTimestampKey is the attribute Key conforming to the - // "heroku.release.creation_timestamp" semantic conventions. It represents - // the time and date the release was created - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2022-10-23T18:00:42Z' - HerokuReleaseCreationTimestampKey = attribute.Key("heroku.release.creation_timestamp") -) - -// HerokuAppID returns an attribute KeyValue conforming to the -// "heroku.app.id" semantic conventions. It represents the unique identifier -// for the application -func HerokuAppID(val string) attribute.KeyValue { - return HerokuAppIDKey.String(val) -} - -// HerokuReleaseCommit returns an attribute KeyValue conforming to the -// "heroku.release.commit" semantic conventions. It represents the commit hash -// for the current release -func HerokuReleaseCommit(val string) attribute.KeyValue { - return HerokuReleaseCommitKey.String(val) -} - -// HerokuReleaseCreationTimestamp returns an attribute KeyValue conforming -// to the "heroku.release.creation_timestamp" semantic conventions. It -// represents the time and date the release was created -func HerokuReleaseCreationTimestamp(val string) attribute.KeyValue { - return HerokuReleaseCreationTimestampKey.String(val) -} - -// The software deployment. -const ( - // DeploymentEnvironmentKey is the attribute Key conforming to the - // "deployment.environment" semantic conventions. It represents the name of - // the [deployment - // environment](https://wikipedia.org/wiki/Deployment_environment) (aka - // deployment tier). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'staging', 'production' - // Note: `deployment.environment` does not affect the uniqueness - // constraints defined through - // the `service.namespace`, `service.name` and `service.instance.id` - // resource attributes. - // This implies that resources carrying the following attribute - // combinations MUST be - // considered to be identifying the same service: - // - // * `service.name=frontend`, `deployment.environment=production` - // * `service.name=frontend`, `deployment.environment=staging`. - DeploymentEnvironmentKey = attribute.Key("deployment.environment") -) - -// DeploymentEnvironment returns an attribute KeyValue conforming to the -// "deployment.environment" semantic conventions. It represents the name of the -// [deployment environment](https://wikipedia.org/wiki/Deployment_environment) -// (aka deployment tier). -func DeploymentEnvironment(val string) attribute.KeyValue { - return DeploymentEnvironmentKey.String(val) -} - -// A serverless instance. -const ( - // FaaSInstanceKey is the attribute Key conforming to the "faas.instance" - // semantic conventions. It represents the execution environment ID as a - // string, that will be potentially reused for other invocations to the - // same function/function version. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2021/06/28/[$LATEST]2f399eb14537447da05ab2a2e39309de' - // Note: * **AWS Lambda:** Use the (full) log stream name. - FaaSInstanceKey = attribute.Key("faas.instance") - - // FaaSMaxMemoryKey is the attribute Key conforming to the - // "faas.max_memory" semantic conventions. It represents the amount of - // memory available to the serverless function converted to Bytes. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 134217728 - // Note: It's recommended to set this attribute since e.g. too little - // memory can easily stop a Java AWS Lambda function from working - // correctly. On AWS Lambda, the environment variable - // `AWS_LAMBDA_FUNCTION_MEMORY_SIZE` provides this information (which must - // be multiplied by 1,048,576). - FaaSMaxMemoryKey = attribute.Key("faas.max_memory") - - // FaaSNameKey is the attribute Key conforming to the "faas.name" semantic - // conventions. It represents the name of the single function that this - // runtime instance executes. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'my-function', 'myazurefunctionapp/some-function-name' - // Note: This is the name of the function as configured/deployed on the - // FaaS - // platform and is usually different from the name of the callback - // function (which may be stored in the - // [`code.namespace`/`code.function`](/docs/general/attributes.md#source-code-attributes) - // span attributes). - // - // For some cloud providers, the above definition is ambiguous. The - // following - // definition of function name MUST be used for this attribute - // (and consequently the span name) for the listed cloud - // providers/products: - // - // * **Azure:** The full name `/`, i.e., function app name - // followed by a forward slash followed by the function name (this form - // can also be seen in the resource JSON for the function). - // This means that a span attribute MUST be used, as an Azure function - // app can host multiple functions that would usually share - // a TracerProvider (see also the `cloud.resource_id` attribute). - FaaSNameKey = attribute.Key("faas.name") - - // FaaSVersionKey is the attribute Key conforming to the "faas.version" - // semantic conventions. It represents the immutable version of the - // function being executed. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '26', 'pinkfroid-00002' - // Note: Depending on the cloud provider and platform, use: - // - // * **AWS Lambda:** The [function - // version](https://docs.aws.amazon.com/lambda/latest/dg/configuration-versions.html) - // (an integer represented as a decimal string). - // * **Google Cloud Run (Services):** The - // [revision](https://cloud.google.com/run/docs/managing/revisions) - // (i.e., the function name plus the revision suffix). - // * **Google Cloud Functions:** The value of the - // [`K_REVISION` environment - // variable](https://cloud.google.com/functions/docs/env-var#runtime_environment_variables_set_automatically). - // * **Azure Functions:** Not applicable. Do not set this attribute. - FaaSVersionKey = attribute.Key("faas.version") -) - -// FaaSInstance returns an attribute KeyValue conforming to the -// "faas.instance" semantic conventions. It represents the execution -// environment ID as a string, that will be potentially reused for other -// invocations to the same function/function version. -func FaaSInstance(val string) attribute.KeyValue { - return FaaSInstanceKey.String(val) -} - -// FaaSMaxMemory returns an attribute KeyValue conforming to the -// "faas.max_memory" semantic conventions. It represents the amount of memory -// available to the serverless function converted to Bytes. -func FaaSMaxMemory(val int) attribute.KeyValue { - return FaaSMaxMemoryKey.Int(val) -} - -// FaaSName returns an attribute KeyValue conforming to the "faas.name" -// semantic conventions. It represents the name of the single function that -// this runtime instance executes. -func FaaSName(val string) attribute.KeyValue { - return FaaSNameKey.String(val) -} - -// FaaSVersion returns an attribute KeyValue conforming to the -// "faas.version" semantic conventions. It represents the immutable version of -// the function being executed. -func FaaSVersion(val string) attribute.KeyValue { - return FaaSVersionKey.String(val) -} - -// A service instance. -const ( - // ServiceNameKey is the attribute Key conforming to the "service.name" - // semantic conventions. It represents the logical name of the service. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'shoppingcart' - // Note: MUST be the same for all instances of horizontally scaled - // services. If the value was not specified, SDKs MUST fallback to - // `unknown_service:` concatenated with - // [`process.executable.name`](process.md#process), e.g. - // `unknown_service:bash`. If `process.executable.name` is not available, - // the value MUST be set to `unknown_service`. - ServiceNameKey = attribute.Key("service.name") - - // ServiceVersionKey is the attribute Key conforming to the - // "service.version" semantic conventions. It represents the version string - // of the service API or implementation. The format is not defined by these - // conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2.0.0', 'a01dbef8a' - ServiceVersionKey = attribute.Key("service.version") -) - -// ServiceName returns an attribute KeyValue conforming to the -// "service.name" semantic conventions. It represents the logical name of the -// service. -func ServiceName(val string) attribute.KeyValue { - return ServiceNameKey.String(val) -} - -// ServiceVersion returns an attribute KeyValue conforming to the -// "service.version" semantic conventions. It represents the version string of -// the service API or implementation. The format is not defined by these -// conventions. -func ServiceVersion(val string) attribute.KeyValue { - return ServiceVersionKey.String(val) -} - -// A service instance. -const ( - // ServiceInstanceIDKey is the attribute Key conforming to the - // "service.instance.id" semantic conventions. It represents the string ID - // of the service instance. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'my-k8s-pod-deployment-1', - // '627cc493-f310-47de-96bd-71410b7dec09' - // Note: MUST be unique for each instance of the same - // `service.namespace,service.name` pair (in other words - // `service.namespace,service.name,service.instance.id` triplet MUST be - // globally unique). The ID helps to distinguish instances of the same - // service that exist at the same time (e.g. instances of a horizontally - // scaled service). It is preferable for the ID to be persistent and stay - // the same for the lifetime of the service instance, however it is - // acceptable that the ID is ephemeral and changes during important - // lifetime events for the service (e.g. service restarts). If the service - // has no inherent unique ID that can be used as the value of this - // attribute it is recommended to generate a random Version 1 or Version 4 - // RFC 4122 UUID (services aiming for reproducible UUIDs may also use - // Version 5, see RFC 4122 for more recommendations). - ServiceInstanceIDKey = attribute.Key("service.instance.id") - - // ServiceNamespaceKey is the attribute Key conforming to the - // "service.namespace" semantic conventions. It represents a namespace for - // `service.name`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Shop' - // Note: A string value having a meaning that helps to distinguish a group - // of services, for example the team name that owns a group of services. - // `service.name` is expected to be unique within the same namespace. If - // `service.namespace` is not specified in the Resource then `service.name` - // is expected to be unique for all services that have no explicit - // namespace defined (so the empty/unspecified namespace is simply one more - // valid namespace). Zero-length namespace string is assumed equal to - // unspecified namespace. - ServiceNamespaceKey = attribute.Key("service.namespace") -) - -// ServiceInstanceID returns an attribute KeyValue conforming to the -// "service.instance.id" semantic conventions. It represents the string ID of -// the service instance. -func ServiceInstanceID(val string) attribute.KeyValue { - return ServiceInstanceIDKey.String(val) -} - -// ServiceNamespace returns an attribute KeyValue conforming to the -// "service.namespace" semantic conventions. It represents a namespace for -// `service.name`. -func ServiceNamespace(val string) attribute.KeyValue { - return ServiceNamespaceKey.String(val) -} - -// The telemetry SDK used to capture data recorded by the instrumentation -// libraries. -const ( - // TelemetrySDKLanguageKey is the attribute Key conforming to the - // "telemetry.sdk.language" semantic conventions. It represents the - // language of the telemetry SDK. - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - TelemetrySDKLanguageKey = attribute.Key("telemetry.sdk.language") - - // TelemetrySDKNameKey is the attribute Key conforming to the - // "telemetry.sdk.name" semantic conventions. It represents the name of the - // telemetry SDK as defined above. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'opentelemetry' - // Note: The OpenTelemetry SDK MUST set the `telemetry.sdk.name` attribute - // to `opentelemetry`. - // If another SDK, like a fork or a vendor-provided implementation, is - // used, this SDK MUST set the - // `telemetry.sdk.name` attribute to the fully-qualified class or module - // name of this SDK's main entry point - // or another suitable identifier depending on the language. - // The identifier `opentelemetry` is reserved and MUST NOT be used in this - // case. - // All custom identifiers SHOULD be stable across different versions of an - // implementation. - TelemetrySDKNameKey = attribute.Key("telemetry.sdk.name") - - // TelemetrySDKVersionKey is the attribute Key conforming to the - // "telemetry.sdk.version" semantic conventions. It represents the version - // string of the telemetry SDK. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: '1.2.3' - TelemetrySDKVersionKey = attribute.Key("telemetry.sdk.version") -) - -var ( - // cpp - TelemetrySDKLanguageCPP = TelemetrySDKLanguageKey.String("cpp") - // dotnet - TelemetrySDKLanguageDotnet = TelemetrySDKLanguageKey.String("dotnet") - // erlang - TelemetrySDKLanguageErlang = TelemetrySDKLanguageKey.String("erlang") - // go - TelemetrySDKLanguageGo = TelemetrySDKLanguageKey.String("go") - // java - TelemetrySDKLanguageJava = TelemetrySDKLanguageKey.String("java") - // nodejs - TelemetrySDKLanguageNodejs = TelemetrySDKLanguageKey.String("nodejs") - // php - TelemetrySDKLanguagePHP = TelemetrySDKLanguageKey.String("php") - // python - TelemetrySDKLanguagePython = TelemetrySDKLanguageKey.String("python") - // ruby - TelemetrySDKLanguageRuby = TelemetrySDKLanguageKey.String("ruby") - // rust - TelemetrySDKLanguageRust = TelemetrySDKLanguageKey.String("rust") - // swift - TelemetrySDKLanguageSwift = TelemetrySDKLanguageKey.String("swift") - // webjs - TelemetrySDKLanguageWebjs = TelemetrySDKLanguageKey.String("webjs") -) - -// TelemetrySDKName returns an attribute KeyValue conforming to the -// "telemetry.sdk.name" semantic conventions. It represents the name of the -// telemetry SDK as defined above. -func TelemetrySDKName(val string) attribute.KeyValue { - return TelemetrySDKNameKey.String(val) -} - -// TelemetrySDKVersion returns an attribute KeyValue conforming to the -// "telemetry.sdk.version" semantic conventions. It represents the version -// string of the telemetry SDK. -func TelemetrySDKVersion(val string) attribute.KeyValue { - return TelemetrySDKVersionKey.String(val) -} - -// The telemetry SDK used to capture data recorded by the instrumentation -// libraries. -const ( - // TelemetryDistroNameKey is the attribute Key conforming to the - // "telemetry.distro.name" semantic conventions. It represents the name of - // the auto instrumentation agent or distribution, if used. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'parts-unlimited-java' - // Note: Official auto instrumentation agents and distributions SHOULD set - // the `telemetry.distro.name` attribute to - // a string starting with `opentelemetry-`, e.g. - // `opentelemetry-java-instrumentation`. - TelemetryDistroNameKey = attribute.Key("telemetry.distro.name") - - // TelemetryDistroVersionKey is the attribute Key conforming to the - // "telemetry.distro.version" semantic conventions. It represents the - // version string of the auto instrumentation agent or distribution, if - // used. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1.2.3' - TelemetryDistroVersionKey = attribute.Key("telemetry.distro.version") -) - -// TelemetryDistroName returns an attribute KeyValue conforming to the -// "telemetry.distro.name" semantic conventions. It represents the name of the -// auto instrumentation agent or distribution, if used. -func TelemetryDistroName(val string) attribute.KeyValue { - return TelemetryDistroNameKey.String(val) -} - -// TelemetryDistroVersion returns an attribute KeyValue conforming to the -// "telemetry.distro.version" semantic conventions. It represents the version -// string of the auto instrumentation agent or distribution, if used. -func TelemetryDistroVersion(val string) attribute.KeyValue { - return TelemetryDistroVersionKey.String(val) -} - -// Resource describing the packaged software running the application code. Web -// engines are typically executed using process.runtime. -const ( - // WebEngineDescriptionKey is the attribute Key conforming to the - // "webengine.description" semantic conventions. It represents the - // additional description of the web engine (e.g. detailed version and - // edition information). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'WildFly Full 21.0.0.Final (WildFly Core 13.0.1.Final) - - // 2.2.2.Final' - WebEngineDescriptionKey = attribute.Key("webengine.description") - - // WebEngineNameKey is the attribute Key conforming to the "webengine.name" - // semantic conventions. It represents the name of the web engine. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'WildFly' - WebEngineNameKey = attribute.Key("webengine.name") - - // WebEngineVersionKey is the attribute Key conforming to the - // "webengine.version" semantic conventions. It represents the version of - // the web engine. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '21.0.0' - WebEngineVersionKey = attribute.Key("webengine.version") -) - -// WebEngineDescription returns an attribute KeyValue conforming to the -// "webengine.description" semantic conventions. It represents the additional -// description of the web engine (e.g. detailed version and edition -// information). -func WebEngineDescription(val string) attribute.KeyValue { - return WebEngineDescriptionKey.String(val) -} - -// WebEngineName returns an attribute KeyValue conforming to the -// "webengine.name" semantic conventions. It represents the name of the web -// engine. -func WebEngineName(val string) attribute.KeyValue { - return WebEngineNameKey.String(val) -} - -// WebEngineVersion returns an attribute KeyValue conforming to the -// "webengine.version" semantic conventions. It represents the version of the -// web engine. -func WebEngineVersion(val string) attribute.KeyValue { - return WebEngineVersionKey.String(val) -} - -// Attributes used by non-OTLP exporters to represent OpenTelemetry Scope's -// concepts. -const ( - // OTelScopeNameKey is the attribute Key conforming to the - // "otel.scope.name" semantic conventions. It represents the name of the - // instrumentation scope - (`InstrumentationScope.Name` in OTLP). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'io.opentelemetry.contrib.mongodb' - OTelScopeNameKey = attribute.Key("otel.scope.name") - - // OTelScopeVersionKey is the attribute Key conforming to the - // "otel.scope.version" semantic conventions. It represents the version of - // the instrumentation scope - (`InstrumentationScope.Version` in OTLP). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1.0.0' - OTelScopeVersionKey = attribute.Key("otel.scope.version") -) - -// OTelScopeName returns an attribute KeyValue conforming to the -// "otel.scope.name" semantic conventions. It represents the name of the -// instrumentation scope - (`InstrumentationScope.Name` in OTLP). -func OTelScopeName(val string) attribute.KeyValue { - return OTelScopeNameKey.String(val) -} - -// OTelScopeVersion returns an attribute KeyValue conforming to the -// "otel.scope.version" semantic conventions. It represents the version of the -// instrumentation scope - (`InstrumentationScope.Version` in OTLP). -func OTelScopeVersion(val string) attribute.KeyValue { - return OTelScopeVersionKey.String(val) -} - -// Span attributes used by non-OTLP exporters to represent OpenTelemetry -// Scope's concepts. -const ( - // OTelLibraryNameKey is the attribute Key conforming to the - // "otel.library.name" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: 'io.opentelemetry.contrib.mongodb' - // Deprecated: use the `otel.scope.name` attribute. - OTelLibraryNameKey = attribute.Key("otel.library.name") - - // OTelLibraryVersionKey is the attribute Key conforming to the - // "otel.library.version" semantic conventions. - // - // Type: string - // RequirementLevel: Optional - // Stability: deprecated - // Examples: '1.0.0' - // Deprecated: use the `otel.scope.version` attribute. - OTelLibraryVersionKey = attribute.Key("otel.library.version") -) - -// OTelLibraryName returns an attribute KeyValue conforming to the -// "otel.library.name" semantic conventions. -// -// Deprecated: use the `otel.scope.name` attribute. -func OTelLibraryName(val string) attribute.KeyValue { - return OTelLibraryNameKey.String(val) -} - -// OTelLibraryVersion returns an attribute KeyValue conforming to the -// "otel.library.version" semantic conventions. -// -// Deprecated: use the `otel.scope.version` attribute. -func OTelLibraryVersion(val string) attribute.KeyValue { - return OTelLibraryVersionKey.String(val) -} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/schema.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/schema.go deleted file mode 100644 index fe80b1731d0..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/schema.go +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -// SchemaURL is the schema URL that matches the version of the semantic conventions -// that this package defines. Semconv packages starting from v1.4.0 must declare -// non-empty schema URL in the form https://opentelemetry.io/schemas/ -const SchemaURL = "https://opentelemetry.io/schemas/1.24.0" diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/trace.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/trace.go deleted file mode 100644 index c1718234e52..00000000000 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/semconv/v1.24.0/trace.go +++ /dev/null @@ -1,1323 +0,0 @@ -// Copyright The OpenTelemetry Authors -// SPDX-License-Identifier: Apache-2.0 - -// Code generated from semantic convention specification. DO NOT EDIT. - -package semconv // import "go.opentelemetry.io/otel/semconv/v1.24.0" - -import "go.opentelemetry.io/otel/attribute" - -// Operations that access some remote service. -const ( - // PeerServiceKey is the attribute Key conforming to the "peer.service" - // semantic conventions. It represents the - // [`service.name`](/docs/resource/README.md#service) of the remote - // service. SHOULD be equal to the actual `service.name` resource attribute - // of the remote service if any. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'AuthTokenCache' - PeerServiceKey = attribute.Key("peer.service") -) - -// PeerService returns an attribute KeyValue conforming to the -// "peer.service" semantic conventions. It represents the -// [`service.name`](/docs/resource/README.md#service) of the remote service. -// SHOULD be equal to the actual `service.name` resource attribute of the -// remote service if any. -func PeerService(val string) attribute.KeyValue { - return PeerServiceKey.String(val) -} - -// These attributes may be used for any operation with an authenticated and/or -// authorized enduser. -const ( - // EnduserIDKey is the attribute Key conforming to the "enduser.id" - // semantic conventions. It represents the username or client_id extracted - // from the access token or - // [Authorization](https://tools.ietf.org/html/rfc7235#section-4.2) header - // in the inbound request from outside the system. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'username' - EnduserIDKey = attribute.Key("enduser.id") - - // EnduserRoleKey is the attribute Key conforming to the "enduser.role" - // semantic conventions. It represents the actual/assumed role the client - // is making the request under extracted from token or application security - // context. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'admin' - EnduserRoleKey = attribute.Key("enduser.role") - - // EnduserScopeKey is the attribute Key conforming to the "enduser.scope" - // semantic conventions. It represents the scopes or granted authorities - // the client currently possesses extracted from token or application - // security context. The value would come from the scope associated with an - // [OAuth 2.0 Access - // Token](https://tools.ietf.org/html/rfc6749#section-3.3) or an attribute - // value in a [SAML 2.0 - // Assertion](http://docs.oasis-open.org/security/saml/Post2.0/sstc-saml-tech-overview-2.0.html). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'read:message, write:files' - EnduserScopeKey = attribute.Key("enduser.scope") -) - -// EnduserID returns an attribute KeyValue conforming to the "enduser.id" -// semantic conventions. It represents the username or client_id extracted from -// the access token or -// [Authorization](https://tools.ietf.org/html/rfc7235#section-4.2) header in -// the inbound request from outside the system. -func EnduserID(val string) attribute.KeyValue { - return EnduserIDKey.String(val) -} - -// EnduserRole returns an attribute KeyValue conforming to the -// "enduser.role" semantic conventions. It represents the actual/assumed role -// the client is making the request under extracted from token or application -// security context. -func EnduserRole(val string) attribute.KeyValue { - return EnduserRoleKey.String(val) -} - -// EnduserScope returns an attribute KeyValue conforming to the -// "enduser.scope" semantic conventions. It represents the scopes or granted -// authorities the client currently possesses extracted from token or -// application security context. The value would come from the scope associated -// with an [OAuth 2.0 Access -// Token](https://tools.ietf.org/html/rfc6749#section-3.3) or an attribute -// value in a [SAML 2.0 -// Assertion](http://docs.oasis-open.org/security/saml/Post2.0/sstc-saml-tech-overview-2.0.html). -func EnduserScope(val string) attribute.KeyValue { - return EnduserScopeKey.String(val) -} - -// These attributes allow to report this unit of code and therefore to provide -// more context about the span. -const ( - // CodeColumnKey is the attribute Key conforming to the "code.column" - // semantic conventions. It represents the column number in `code.filepath` - // best representing the operation. It SHOULD point within the code unit - // named in `code.function`. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 16 - CodeColumnKey = attribute.Key("code.column") - - // CodeFilepathKey is the attribute Key conforming to the "code.filepath" - // semantic conventions. It represents the source code file name that - // identifies the code unit as uniquely as possible (preferably an absolute - // file path). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '/usr/local/MyApplication/content_root/app/index.php' - CodeFilepathKey = attribute.Key("code.filepath") - - // CodeFunctionKey is the attribute Key conforming to the "code.function" - // semantic conventions. It represents the method or function name, or - // equivalent (usually rightmost part of the code unit's name). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'serveRequest' - CodeFunctionKey = attribute.Key("code.function") - - // CodeLineNumberKey is the attribute Key conforming to the "code.lineno" - // semantic conventions. It represents the line number in `code.filepath` - // best representing the operation. It SHOULD point within the code unit - // named in `code.function`. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 42 - CodeLineNumberKey = attribute.Key("code.lineno") - - // CodeNamespaceKey is the attribute Key conforming to the "code.namespace" - // semantic conventions. It represents the "namespace" within which - // `code.function` is defined. Usually the qualified class or module name, - // such that `code.namespace` + some separator + `code.function` form a - // unique identifier for the code unit. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'com.example.MyHTTPService' - CodeNamespaceKey = attribute.Key("code.namespace") - - // CodeStacktraceKey is the attribute Key conforming to the - // "code.stacktrace" semantic conventions. It represents a stacktrace as a - // string in the natural representation for the language runtime. The - // representation is to be determined and documented by each language SIG. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'at - // com.example.GenerateTrace.methodB(GenerateTrace.java:13)\\n at ' - // 'com.example.GenerateTrace.methodA(GenerateTrace.java:9)\\n at ' - // 'com.example.GenerateTrace.main(GenerateTrace.java:5)' - CodeStacktraceKey = attribute.Key("code.stacktrace") -) - -// CodeColumn returns an attribute KeyValue conforming to the "code.column" -// semantic conventions. It represents the column number in `code.filepath` -// best representing the operation. It SHOULD point within the code unit named -// in `code.function`. -func CodeColumn(val int) attribute.KeyValue { - return CodeColumnKey.Int(val) -} - -// CodeFilepath returns an attribute KeyValue conforming to the -// "code.filepath" semantic conventions. It represents the source code file -// name that identifies the code unit as uniquely as possible (preferably an -// absolute file path). -func CodeFilepath(val string) attribute.KeyValue { - return CodeFilepathKey.String(val) -} - -// CodeFunction returns an attribute KeyValue conforming to the -// "code.function" semantic conventions. It represents the method or function -// name, or equivalent (usually rightmost part of the code unit's name). -func CodeFunction(val string) attribute.KeyValue { - return CodeFunctionKey.String(val) -} - -// CodeLineNumber returns an attribute KeyValue conforming to the "code.lineno" -// semantic conventions. It represents the line number in `code.filepath` best -// representing the operation. It SHOULD point within the code unit named in -// `code.function`. -func CodeLineNumber(val int) attribute.KeyValue { - return CodeLineNumberKey.Int(val) -} - -// CodeNamespace returns an attribute KeyValue conforming to the -// "code.namespace" semantic conventions. It represents the "namespace" within -// which `code.function` is defined. Usually the qualified class or module -// name, such that `code.namespace` + some separator + `code.function` form a -// unique identifier for the code unit. -func CodeNamespace(val string) attribute.KeyValue { - return CodeNamespaceKey.String(val) -} - -// CodeStacktrace returns an attribute KeyValue conforming to the -// "code.stacktrace" semantic conventions. It represents a stacktrace as a -// string in the natural representation for the language runtime. The -// representation is to be determined and documented by each language SIG. -func CodeStacktrace(val string) attribute.KeyValue { - return CodeStacktraceKey.String(val) -} - -// These attributes may be used for any operation to store information about a -// thread that started a span. -const ( - // ThreadIDKey is the attribute Key conforming to the "thread.id" semantic - // conventions. It represents the current "managed" thread ID (as opposed - // to OS thread ID). - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 42 - ThreadIDKey = attribute.Key("thread.id") - - // ThreadNameKey is the attribute Key conforming to the "thread.name" - // semantic conventions. It represents the current thread name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'main' - ThreadNameKey = attribute.Key("thread.name") -) - -// ThreadID returns an attribute KeyValue conforming to the "thread.id" -// semantic conventions. It represents the current "managed" thread ID (as -// opposed to OS thread ID). -func ThreadID(val int) attribute.KeyValue { - return ThreadIDKey.Int(val) -} - -// ThreadName returns an attribute KeyValue conforming to the "thread.name" -// semantic conventions. It represents the current thread name. -func ThreadName(val string) attribute.KeyValue { - return ThreadNameKey.String(val) -} - -// Span attributes used by AWS Lambda (in addition to general `faas` -// attributes). -const ( - // AWSLambdaInvokedARNKey is the attribute Key conforming to the - // "aws.lambda.invoked_arn" semantic conventions. It represents the full - // invoked ARN as provided on the `Context` passed to the function - // (`Lambda-Runtime-Invoked-Function-ARN` header on the - // `/runtime/invocation/next` applicable). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'arn:aws:lambda:us-east-1:123456:function:myfunction:myalias' - // Note: This may be different from `cloud.resource_id` if an alias is - // involved. - AWSLambdaInvokedARNKey = attribute.Key("aws.lambda.invoked_arn") -) - -// AWSLambdaInvokedARN returns an attribute KeyValue conforming to the -// "aws.lambda.invoked_arn" semantic conventions. It represents the full -// invoked ARN as provided on the `Context` passed to the function -// (`Lambda-Runtime-Invoked-Function-ARN` header on the -// `/runtime/invocation/next` applicable). -func AWSLambdaInvokedARN(val string) attribute.KeyValue { - return AWSLambdaInvokedARNKey.String(val) -} - -// Attributes for CloudEvents. CloudEvents is a specification on how to define -// event data in a standard way. These attributes can be attached to spans when -// performing operations with CloudEvents, regardless of the protocol being -// used. -const ( - // CloudeventsEventIDKey is the attribute Key conforming to the - // "cloudevents.event_id" semantic conventions. It represents the - // [event_id](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#id) - // uniquely identifies the event. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: '123e4567-e89b-12d3-a456-426614174000', '0001' - CloudeventsEventIDKey = attribute.Key("cloudevents.event_id") - - // CloudeventsEventSourceKey is the attribute Key conforming to the - // "cloudevents.event_source" semantic conventions. It represents the - // [source](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#source-1) - // identifies the context in which an event happened. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'https://github.com/cloudevents', - // '/cloudevents/spec/pull/123', 'my-service' - CloudeventsEventSourceKey = attribute.Key("cloudevents.event_source") - - // CloudeventsEventSpecVersionKey is the attribute Key conforming to the - // "cloudevents.event_spec_version" semantic conventions. It represents the - // [version of the CloudEvents - // specification](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#specversion) - // which the event uses. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '1.0' - CloudeventsEventSpecVersionKey = attribute.Key("cloudevents.event_spec_version") - - // CloudeventsEventSubjectKey is the attribute Key conforming to the - // "cloudevents.event_subject" semantic conventions. It represents the - // [subject](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#subject) - // of the event in the context of the event producer (identified by - // source). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'mynewfile.jpg' - CloudeventsEventSubjectKey = attribute.Key("cloudevents.event_subject") - - // CloudeventsEventTypeKey is the attribute Key conforming to the - // "cloudevents.event_type" semantic conventions. It represents the - // [event_type](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#type) - // contains a value describing the type of event related to the originating - // occurrence. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'com.github.pull_request.opened', - // 'com.example.object.deleted.v2' - CloudeventsEventTypeKey = attribute.Key("cloudevents.event_type") -) - -// CloudeventsEventID returns an attribute KeyValue conforming to the -// "cloudevents.event_id" semantic conventions. It represents the -// [event_id](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#id) -// uniquely identifies the event. -func CloudeventsEventID(val string) attribute.KeyValue { - return CloudeventsEventIDKey.String(val) -} - -// CloudeventsEventSource returns an attribute KeyValue conforming to the -// "cloudevents.event_source" semantic conventions. It represents the -// [source](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#source-1) -// identifies the context in which an event happened. -func CloudeventsEventSource(val string) attribute.KeyValue { - return CloudeventsEventSourceKey.String(val) -} - -// CloudeventsEventSpecVersion returns an attribute KeyValue conforming to -// the "cloudevents.event_spec_version" semantic conventions. It represents the -// [version of the CloudEvents -// specification](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#specversion) -// which the event uses. -func CloudeventsEventSpecVersion(val string) attribute.KeyValue { - return CloudeventsEventSpecVersionKey.String(val) -} - -// CloudeventsEventSubject returns an attribute KeyValue conforming to the -// "cloudevents.event_subject" semantic conventions. It represents the -// [subject](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#subject) -// of the event in the context of the event producer (identified by source). -func CloudeventsEventSubject(val string) attribute.KeyValue { - return CloudeventsEventSubjectKey.String(val) -} - -// CloudeventsEventType returns an attribute KeyValue conforming to the -// "cloudevents.event_type" semantic conventions. It represents the -// [event_type](https://github.com/cloudevents/spec/blob/v1.0.2/cloudevents/spec.md#type) -// contains a value describing the type of event related to the originating -// occurrence. -func CloudeventsEventType(val string) attribute.KeyValue { - return CloudeventsEventTypeKey.String(val) -} - -// Semantic conventions for the OpenTracing Shim -const ( - // OpentracingRefTypeKey is the attribute Key conforming to the - // "opentracing.ref_type" semantic conventions. It represents the - // parent-child Reference type - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Note: The causal relationship between a child Span and a parent Span. - OpentracingRefTypeKey = attribute.Key("opentracing.ref_type") -) - -var ( - // The parent Span depends on the child Span in some capacity - OpentracingRefTypeChildOf = OpentracingRefTypeKey.String("child_of") - // The parent Span doesn't depend in any way on the result of the child Span - OpentracingRefTypeFollowsFrom = OpentracingRefTypeKey.String("follows_from") -) - -// Span attributes used by non-OTLP exporters to represent OpenTelemetry Span's -// concepts. -const ( - // OTelStatusCodeKey is the attribute Key conforming to the - // "otel.status_code" semantic conventions. It represents the name of the - // code, either "OK" or "ERROR". MUST NOT be set if the status code is - // UNSET. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - OTelStatusCodeKey = attribute.Key("otel.status_code") - - // OTelStatusDescriptionKey is the attribute Key conforming to the - // "otel.status_description" semantic conventions. It represents the - // description of the Status if it has a value, otherwise not set. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'resource not found' - OTelStatusDescriptionKey = attribute.Key("otel.status_description") -) - -var ( - // The operation has been validated by an Application developer or Operator to have completed successfully - OTelStatusCodeOk = OTelStatusCodeKey.String("OK") - // The operation contains an error - OTelStatusCodeError = OTelStatusCodeKey.String("ERROR") -) - -// OTelStatusDescription returns an attribute KeyValue conforming to the -// "otel.status_description" semantic conventions. It represents the -// description of the Status if it has a value, otherwise not set. -func OTelStatusDescription(val string) attribute.KeyValue { - return OTelStatusDescriptionKey.String(val) -} - -// This semantic convention describes an instance of a function that runs -// without provisioning or managing of servers (also known as serverless -// functions or Function as a Service (FaaS)) with spans. -const ( - // FaaSInvocationIDKey is the attribute Key conforming to the - // "faas.invocation_id" semantic conventions. It represents the invocation - // ID of the current function invocation. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'af9d5aa4-a685-4c5f-a22b-444f80b3cc28' - FaaSInvocationIDKey = attribute.Key("faas.invocation_id") -) - -// FaaSInvocationID returns an attribute KeyValue conforming to the -// "faas.invocation_id" semantic conventions. It represents the invocation ID -// of the current function invocation. -func FaaSInvocationID(val string) attribute.KeyValue { - return FaaSInvocationIDKey.String(val) -} - -// Semantic Convention for FaaS triggered as a response to some data source -// operation such as a database or filesystem read/write. -const ( - // FaaSDocumentCollectionKey is the attribute Key conforming to the - // "faas.document.collection" semantic conventions. It represents the name - // of the source on which the triggering operation was performed. For - // example, in Cloud Storage or S3 corresponds to the bucket name, and in - // Cosmos DB to the database name. - // - // Type: string - // RequirementLevel: Required - // Stability: experimental - // Examples: 'myBucketName', 'myDBName' - FaaSDocumentCollectionKey = attribute.Key("faas.document.collection") - - // FaaSDocumentNameKey is the attribute Key conforming to the - // "faas.document.name" semantic conventions. It represents the document - // name/table subjected to the operation. For example, in Cloud Storage or - // S3 is the name of the file, and in Cosmos DB the table name. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'myFile.txt', 'myTableName' - FaaSDocumentNameKey = attribute.Key("faas.document.name") - - // FaaSDocumentOperationKey is the attribute Key conforming to the - // "faas.document.operation" semantic conventions. It represents the - // describes the type of the operation that was performed on the data. - // - // Type: Enum - // RequirementLevel: Required - // Stability: experimental - FaaSDocumentOperationKey = attribute.Key("faas.document.operation") - - // FaaSDocumentTimeKey is the attribute Key conforming to the - // "faas.document.time" semantic conventions. It represents a string - // containing the time when the data was accessed in the [ISO - // 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format - // expressed in [UTC](https://www.w3.org/TR/NOTE-datetime). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2020-01-23T13:47:06Z' - FaaSDocumentTimeKey = attribute.Key("faas.document.time") -) - -var ( - // When a new object is created - FaaSDocumentOperationInsert = FaaSDocumentOperationKey.String("insert") - // When an object is modified - FaaSDocumentOperationEdit = FaaSDocumentOperationKey.String("edit") - // When an object is deleted - FaaSDocumentOperationDelete = FaaSDocumentOperationKey.String("delete") -) - -// FaaSDocumentCollection returns an attribute KeyValue conforming to the -// "faas.document.collection" semantic conventions. It represents the name of -// the source on which the triggering operation was performed. For example, in -// Cloud Storage or S3 corresponds to the bucket name, and in Cosmos DB to the -// database name. -func FaaSDocumentCollection(val string) attribute.KeyValue { - return FaaSDocumentCollectionKey.String(val) -} - -// FaaSDocumentName returns an attribute KeyValue conforming to the -// "faas.document.name" semantic conventions. It represents the document -// name/table subjected to the operation. For example, in Cloud Storage or S3 -// is the name of the file, and in Cosmos DB the table name. -func FaaSDocumentName(val string) attribute.KeyValue { - return FaaSDocumentNameKey.String(val) -} - -// FaaSDocumentTime returns an attribute KeyValue conforming to the -// "faas.document.time" semantic conventions. It represents a string containing -// the time when the data was accessed in the [ISO -// 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format -// expressed in [UTC](https://www.w3.org/TR/NOTE-datetime). -func FaaSDocumentTime(val string) attribute.KeyValue { - return FaaSDocumentTimeKey.String(val) -} - -// Semantic Convention for FaaS scheduled to be executed regularly. -const ( - // FaaSCronKey is the attribute Key conforming to the "faas.cron" semantic - // conventions. It represents a string containing the schedule period as - // [Cron - // Expression](https://docs.oracle.com/cd/E12058_01/doc/doc.1014/e12030/cron_expressions.htm). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '0/5 * * * ? *' - FaaSCronKey = attribute.Key("faas.cron") - - // FaaSTimeKey is the attribute Key conforming to the "faas.time" semantic - // conventions. It represents a string containing the function invocation - // time in the [ISO - // 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format - // expressed in [UTC](https://www.w3.org/TR/NOTE-datetime). - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '2020-01-23T13:47:06Z' - FaaSTimeKey = attribute.Key("faas.time") -) - -// FaaSCron returns an attribute KeyValue conforming to the "faas.cron" -// semantic conventions. It represents a string containing the schedule period -// as [Cron -// Expression](https://docs.oracle.com/cd/E12058_01/doc/doc.1014/e12030/cron_expressions.htm). -func FaaSCron(val string) attribute.KeyValue { - return FaaSCronKey.String(val) -} - -// FaaSTime returns an attribute KeyValue conforming to the "faas.time" -// semantic conventions. It represents a string containing the function -// invocation time in the [ISO -// 8601](https://www.iso.org/iso-8601-date-and-time-format.html) format -// expressed in [UTC](https://www.w3.org/TR/NOTE-datetime). -func FaaSTime(val string) attribute.KeyValue { - return FaaSTimeKey.String(val) -} - -// Contains additional attributes for incoming FaaS spans. -const ( - // FaaSColdstartKey is the attribute Key conforming to the "faas.coldstart" - // semantic conventions. It represents a boolean that is true if the - // serverless function is executed for the first time (aka cold-start). - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - FaaSColdstartKey = attribute.Key("faas.coldstart") -) - -// FaaSColdstart returns an attribute KeyValue conforming to the -// "faas.coldstart" semantic conventions. It represents a boolean that is true -// if the serverless function is executed for the first time (aka cold-start). -func FaaSColdstart(val bool) attribute.KeyValue { - return FaaSColdstartKey.Bool(val) -} - -// The `aws` conventions apply to operations using the AWS SDK. They map -// request or response parameters in AWS SDK API calls to attributes on a Span. -// The conventions have been collected over time based on feedback from AWS -// users of tracing and will continue to evolve as new interesting conventions -// are found. -// Some descriptions are also provided for populating general OpenTelemetry -// semantic conventions based on these APIs. -const ( - // AWSRequestIDKey is the attribute Key conforming to the "aws.request_id" - // semantic conventions. It represents the AWS request ID as returned in - // the response headers `x-amz-request-id` or `x-amz-requestid`. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '79b9da39-b7ae-508a-a6bc-864b2829c622', 'C9ER4AJX75574TDJ' - AWSRequestIDKey = attribute.Key("aws.request_id") -) - -// AWSRequestID returns an attribute KeyValue conforming to the -// "aws.request_id" semantic conventions. It represents the AWS request ID as -// returned in the response headers `x-amz-request-id` or `x-amz-requestid`. -func AWSRequestID(val string) attribute.KeyValue { - return AWSRequestIDKey.String(val) -} - -// Attributes that exist for multiple DynamoDB request types. -const ( - // AWSDynamoDBAttributesToGetKey is the attribute Key conforming to the - // "aws.dynamodb.attributes_to_get" semantic conventions. It represents the - // value of the `AttributesToGet` request parameter. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'lives', 'id' - AWSDynamoDBAttributesToGetKey = attribute.Key("aws.dynamodb.attributes_to_get") - - // AWSDynamoDBConsistentReadKey is the attribute Key conforming to the - // "aws.dynamodb.consistent_read" semantic conventions. It represents the - // value of the `ConsistentRead` request parameter. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - AWSDynamoDBConsistentReadKey = attribute.Key("aws.dynamodb.consistent_read") - - // AWSDynamoDBConsumedCapacityKey is the attribute Key conforming to the - // "aws.dynamodb.consumed_capacity" semantic conventions. It represents the - // JSON-serialized value of each item in the `ConsumedCapacity` response - // field. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '{ "CapacityUnits": number, "GlobalSecondaryIndexes": { - // "string" : { "CapacityUnits": number, "ReadCapacityUnits": number, - // "WriteCapacityUnits": number } }, "LocalSecondaryIndexes": { "string" : - // { "CapacityUnits": number, "ReadCapacityUnits": number, - // "WriteCapacityUnits": number } }, "ReadCapacityUnits": number, "Table": - // { "CapacityUnits": number, "ReadCapacityUnits": number, - // "WriteCapacityUnits": number }, "TableName": "string", - // "WriteCapacityUnits": number }' - AWSDynamoDBConsumedCapacityKey = attribute.Key("aws.dynamodb.consumed_capacity") - - // AWSDynamoDBIndexNameKey is the attribute Key conforming to the - // "aws.dynamodb.index_name" semantic conventions. It represents the value - // of the `IndexName` request parameter. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'name_to_group' - AWSDynamoDBIndexNameKey = attribute.Key("aws.dynamodb.index_name") - - // AWSDynamoDBItemCollectionMetricsKey is the attribute Key conforming to - // the "aws.dynamodb.item_collection_metrics" semantic conventions. It - // represents the JSON-serialized value of the `ItemCollectionMetrics` - // response field. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: '{ "string" : [ { "ItemCollectionKey": { "string" : { "B": - // blob, "BOOL": boolean, "BS": [ blob ], "L": [ "AttributeValue" ], "M": { - // "string" : "AttributeValue" }, "N": "string", "NS": [ "string" ], - // "NULL": boolean, "S": "string", "SS": [ "string" ] } }, - // "SizeEstimateRangeGB": [ number ] } ] }' - AWSDynamoDBItemCollectionMetricsKey = attribute.Key("aws.dynamodb.item_collection_metrics") - - // AWSDynamoDBLimitKey is the attribute Key conforming to the - // "aws.dynamodb.limit" semantic conventions. It represents the value of - // the `Limit` request parameter. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 10 - AWSDynamoDBLimitKey = attribute.Key("aws.dynamodb.limit") - - // AWSDynamoDBProjectionKey is the attribute Key conforming to the - // "aws.dynamodb.projection" semantic conventions. It represents the value - // of the `ProjectionExpression` request parameter. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Title', 'Title, Price, Color', 'Title, Description, - // RelatedItems, ProductReviews' - AWSDynamoDBProjectionKey = attribute.Key("aws.dynamodb.projection") - - // AWSDynamoDBProvisionedReadCapacityKey is the attribute Key conforming to - // the "aws.dynamodb.provisioned_read_capacity" semantic conventions. It - // represents the value of the `ProvisionedThroughput.ReadCapacityUnits` - // request parameter. - // - // Type: double - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1.0, 2.0 - AWSDynamoDBProvisionedReadCapacityKey = attribute.Key("aws.dynamodb.provisioned_read_capacity") - - // AWSDynamoDBProvisionedWriteCapacityKey is the attribute Key conforming - // to the "aws.dynamodb.provisioned_write_capacity" semantic conventions. - // It represents the value of the - // `ProvisionedThroughput.WriteCapacityUnits` request parameter. - // - // Type: double - // RequirementLevel: Optional - // Stability: experimental - // Examples: 1.0, 2.0 - AWSDynamoDBProvisionedWriteCapacityKey = attribute.Key("aws.dynamodb.provisioned_write_capacity") - - // AWSDynamoDBSelectKey is the attribute Key conforming to the - // "aws.dynamodb.select" semantic conventions. It represents the value of - // the `Select` request parameter. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'ALL_ATTRIBUTES', 'COUNT' - AWSDynamoDBSelectKey = attribute.Key("aws.dynamodb.select") - - // AWSDynamoDBTableNamesKey is the attribute Key conforming to the - // "aws.dynamodb.table_names" semantic conventions. It represents the keys - // in the `RequestItems` object field. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Users', 'Cats' - AWSDynamoDBTableNamesKey = attribute.Key("aws.dynamodb.table_names") -) - -// AWSDynamoDBAttributesToGet returns an attribute KeyValue conforming to -// the "aws.dynamodb.attributes_to_get" semantic conventions. It represents the -// value of the `AttributesToGet` request parameter. -func AWSDynamoDBAttributesToGet(val ...string) attribute.KeyValue { - return AWSDynamoDBAttributesToGetKey.StringSlice(val) -} - -// AWSDynamoDBConsistentRead returns an attribute KeyValue conforming to the -// "aws.dynamodb.consistent_read" semantic conventions. It represents the value -// of the `ConsistentRead` request parameter. -func AWSDynamoDBConsistentRead(val bool) attribute.KeyValue { - return AWSDynamoDBConsistentReadKey.Bool(val) -} - -// AWSDynamoDBConsumedCapacity returns an attribute KeyValue conforming to -// the "aws.dynamodb.consumed_capacity" semantic conventions. It represents the -// JSON-serialized value of each item in the `ConsumedCapacity` response field. -func AWSDynamoDBConsumedCapacity(val ...string) attribute.KeyValue { - return AWSDynamoDBConsumedCapacityKey.StringSlice(val) -} - -// AWSDynamoDBIndexName returns an attribute KeyValue conforming to the -// "aws.dynamodb.index_name" semantic conventions. It represents the value of -// the `IndexName` request parameter. -func AWSDynamoDBIndexName(val string) attribute.KeyValue { - return AWSDynamoDBIndexNameKey.String(val) -} - -// AWSDynamoDBItemCollectionMetrics returns an attribute KeyValue conforming -// to the "aws.dynamodb.item_collection_metrics" semantic conventions. It -// represents the JSON-serialized value of the `ItemCollectionMetrics` response -// field. -func AWSDynamoDBItemCollectionMetrics(val string) attribute.KeyValue { - return AWSDynamoDBItemCollectionMetricsKey.String(val) -} - -// AWSDynamoDBLimit returns an attribute KeyValue conforming to the -// "aws.dynamodb.limit" semantic conventions. It represents the value of the -// `Limit` request parameter. -func AWSDynamoDBLimit(val int) attribute.KeyValue { - return AWSDynamoDBLimitKey.Int(val) -} - -// AWSDynamoDBProjection returns an attribute KeyValue conforming to the -// "aws.dynamodb.projection" semantic conventions. It represents the value of -// the `ProjectionExpression` request parameter. -func AWSDynamoDBProjection(val string) attribute.KeyValue { - return AWSDynamoDBProjectionKey.String(val) -} - -// AWSDynamoDBProvisionedReadCapacity returns an attribute KeyValue -// conforming to the "aws.dynamodb.provisioned_read_capacity" semantic -// conventions. It represents the value of the -// `ProvisionedThroughput.ReadCapacityUnits` request parameter. -func AWSDynamoDBProvisionedReadCapacity(val float64) attribute.KeyValue { - return AWSDynamoDBProvisionedReadCapacityKey.Float64(val) -} - -// AWSDynamoDBProvisionedWriteCapacity returns an attribute KeyValue -// conforming to the "aws.dynamodb.provisioned_write_capacity" semantic -// conventions. It represents the value of the -// `ProvisionedThroughput.WriteCapacityUnits` request parameter. -func AWSDynamoDBProvisionedWriteCapacity(val float64) attribute.KeyValue { - return AWSDynamoDBProvisionedWriteCapacityKey.Float64(val) -} - -// AWSDynamoDBSelect returns an attribute KeyValue conforming to the -// "aws.dynamodb.select" semantic conventions. It represents the value of the -// `Select` request parameter. -func AWSDynamoDBSelect(val string) attribute.KeyValue { - return AWSDynamoDBSelectKey.String(val) -} - -// AWSDynamoDBTableNames returns an attribute KeyValue conforming to the -// "aws.dynamodb.table_names" semantic conventions. It represents the keys in -// the `RequestItems` object field. -func AWSDynamoDBTableNames(val ...string) attribute.KeyValue { - return AWSDynamoDBTableNamesKey.StringSlice(val) -} - -// DynamoDB.CreateTable -const ( - // AWSDynamoDBGlobalSecondaryIndexesKey is the attribute Key conforming to - // the "aws.dynamodb.global_secondary_indexes" semantic conventions. It - // represents the JSON-serialized value of each item of the - // `GlobalSecondaryIndexes` request field - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '{ "IndexName": "string", "KeySchema": [ { "AttributeName": - // "string", "KeyType": "string" } ], "Projection": { "NonKeyAttributes": [ - // "string" ], "ProjectionType": "string" }, "ProvisionedThroughput": { - // "ReadCapacityUnits": number, "WriteCapacityUnits": number } }' - AWSDynamoDBGlobalSecondaryIndexesKey = attribute.Key("aws.dynamodb.global_secondary_indexes") - - // AWSDynamoDBLocalSecondaryIndexesKey is the attribute Key conforming to - // the "aws.dynamodb.local_secondary_indexes" semantic conventions. It - // represents the JSON-serialized value of each item of the - // `LocalSecondaryIndexes` request field. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '{ "IndexARN": "string", "IndexName": "string", - // "IndexSizeBytes": number, "ItemCount": number, "KeySchema": [ { - // "AttributeName": "string", "KeyType": "string" } ], "Projection": { - // "NonKeyAttributes": [ "string" ], "ProjectionType": "string" } }' - AWSDynamoDBLocalSecondaryIndexesKey = attribute.Key("aws.dynamodb.local_secondary_indexes") -) - -// AWSDynamoDBGlobalSecondaryIndexes returns an attribute KeyValue -// conforming to the "aws.dynamodb.global_secondary_indexes" semantic -// conventions. It represents the JSON-serialized value of each item of the -// `GlobalSecondaryIndexes` request field -func AWSDynamoDBGlobalSecondaryIndexes(val ...string) attribute.KeyValue { - return AWSDynamoDBGlobalSecondaryIndexesKey.StringSlice(val) -} - -// AWSDynamoDBLocalSecondaryIndexes returns an attribute KeyValue conforming -// to the "aws.dynamodb.local_secondary_indexes" semantic conventions. It -// represents the JSON-serialized value of each item of the -// `LocalSecondaryIndexes` request field. -func AWSDynamoDBLocalSecondaryIndexes(val ...string) attribute.KeyValue { - return AWSDynamoDBLocalSecondaryIndexesKey.StringSlice(val) -} - -// DynamoDB.ListTables -const ( - // AWSDynamoDBExclusiveStartTableKey is the attribute Key conforming to the - // "aws.dynamodb.exclusive_start_table" semantic conventions. It represents - // the value of the `ExclusiveStartTableName` request parameter. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'Users', 'CatsTable' - AWSDynamoDBExclusiveStartTableKey = attribute.Key("aws.dynamodb.exclusive_start_table") - - // AWSDynamoDBTableCountKey is the attribute Key conforming to the - // "aws.dynamodb.table_count" semantic conventions. It represents the the - // number of items in the `TableNames` response parameter. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 20 - AWSDynamoDBTableCountKey = attribute.Key("aws.dynamodb.table_count") -) - -// AWSDynamoDBExclusiveStartTable returns an attribute KeyValue conforming -// to the "aws.dynamodb.exclusive_start_table" semantic conventions. It -// represents the value of the `ExclusiveStartTableName` request parameter. -func AWSDynamoDBExclusiveStartTable(val string) attribute.KeyValue { - return AWSDynamoDBExclusiveStartTableKey.String(val) -} - -// AWSDynamoDBTableCount returns an attribute KeyValue conforming to the -// "aws.dynamodb.table_count" semantic conventions. It represents the the -// number of items in the `TableNames` response parameter. -func AWSDynamoDBTableCount(val int) attribute.KeyValue { - return AWSDynamoDBTableCountKey.Int(val) -} - -// DynamoDB.Query -const ( - // AWSDynamoDBScanForwardKey is the attribute Key conforming to the - // "aws.dynamodb.scan_forward" semantic conventions. It represents the - // value of the `ScanIndexForward` request parameter. - // - // Type: boolean - // RequirementLevel: Optional - // Stability: experimental - AWSDynamoDBScanForwardKey = attribute.Key("aws.dynamodb.scan_forward") -) - -// AWSDynamoDBScanForward returns an attribute KeyValue conforming to the -// "aws.dynamodb.scan_forward" semantic conventions. It represents the value of -// the `ScanIndexForward` request parameter. -func AWSDynamoDBScanForward(val bool) attribute.KeyValue { - return AWSDynamoDBScanForwardKey.Bool(val) -} - -// DynamoDB.Scan -const ( - // AWSDynamoDBCountKey is the attribute Key conforming to the - // "aws.dynamodb.count" semantic conventions. It represents the value of - // the `Count` response parameter. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 10 - AWSDynamoDBCountKey = attribute.Key("aws.dynamodb.count") - - // AWSDynamoDBScannedCountKey is the attribute Key conforming to the - // "aws.dynamodb.scanned_count" semantic conventions. It represents the - // value of the `ScannedCount` response parameter. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 50 - AWSDynamoDBScannedCountKey = attribute.Key("aws.dynamodb.scanned_count") - - // AWSDynamoDBSegmentKey is the attribute Key conforming to the - // "aws.dynamodb.segment" semantic conventions. It represents the value of - // the `Segment` request parameter. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 10 - AWSDynamoDBSegmentKey = attribute.Key("aws.dynamodb.segment") - - // AWSDynamoDBTotalSegmentsKey is the attribute Key conforming to the - // "aws.dynamodb.total_segments" semantic conventions. It represents the - // value of the `TotalSegments` request parameter. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 100 - AWSDynamoDBTotalSegmentsKey = attribute.Key("aws.dynamodb.total_segments") -) - -// AWSDynamoDBCount returns an attribute KeyValue conforming to the -// "aws.dynamodb.count" semantic conventions. It represents the value of the -// `Count` response parameter. -func AWSDynamoDBCount(val int) attribute.KeyValue { - return AWSDynamoDBCountKey.Int(val) -} - -// AWSDynamoDBScannedCount returns an attribute KeyValue conforming to the -// "aws.dynamodb.scanned_count" semantic conventions. It represents the value -// of the `ScannedCount` response parameter. -func AWSDynamoDBScannedCount(val int) attribute.KeyValue { - return AWSDynamoDBScannedCountKey.Int(val) -} - -// AWSDynamoDBSegment returns an attribute KeyValue conforming to the -// "aws.dynamodb.segment" semantic conventions. It represents the value of the -// `Segment` request parameter. -func AWSDynamoDBSegment(val int) attribute.KeyValue { - return AWSDynamoDBSegmentKey.Int(val) -} - -// AWSDynamoDBTotalSegments returns an attribute KeyValue conforming to the -// "aws.dynamodb.total_segments" semantic conventions. It represents the value -// of the `TotalSegments` request parameter. -func AWSDynamoDBTotalSegments(val int) attribute.KeyValue { - return AWSDynamoDBTotalSegmentsKey.Int(val) -} - -// DynamoDB.UpdateTable -const ( - // AWSDynamoDBAttributeDefinitionsKey is the attribute Key conforming to - // the "aws.dynamodb.attribute_definitions" semantic conventions. It - // represents the JSON-serialized value of each item in the - // `AttributeDefinitions` request field. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '{ "AttributeName": "string", "AttributeType": "string" }' - AWSDynamoDBAttributeDefinitionsKey = attribute.Key("aws.dynamodb.attribute_definitions") - - // AWSDynamoDBGlobalSecondaryIndexUpdatesKey is the attribute Key - // conforming to the "aws.dynamodb.global_secondary_index_updates" semantic - // conventions. It represents the JSON-serialized value of each item in the - // the `GlobalSecondaryIndexUpdates` request field. - // - // Type: string[] - // RequirementLevel: Optional - // Stability: experimental - // Examples: '{ "Create": { "IndexName": "string", "KeySchema": [ { - // "AttributeName": "string", "KeyType": "string" } ], "Projection": { - // "NonKeyAttributes": [ "string" ], "ProjectionType": "string" }, - // "ProvisionedThroughput": { "ReadCapacityUnits": number, - // "WriteCapacityUnits": number } }' - AWSDynamoDBGlobalSecondaryIndexUpdatesKey = attribute.Key("aws.dynamodb.global_secondary_index_updates") -) - -// AWSDynamoDBAttributeDefinitions returns an attribute KeyValue conforming -// to the "aws.dynamodb.attribute_definitions" semantic conventions. It -// represents the JSON-serialized value of each item in the -// `AttributeDefinitions` request field. -func AWSDynamoDBAttributeDefinitions(val ...string) attribute.KeyValue { - return AWSDynamoDBAttributeDefinitionsKey.StringSlice(val) -} - -// AWSDynamoDBGlobalSecondaryIndexUpdates returns an attribute KeyValue -// conforming to the "aws.dynamodb.global_secondary_index_updates" semantic -// conventions. It represents the JSON-serialized value of each item in the the -// `GlobalSecondaryIndexUpdates` request field. -func AWSDynamoDBGlobalSecondaryIndexUpdates(val ...string) attribute.KeyValue { - return AWSDynamoDBGlobalSecondaryIndexUpdatesKey.StringSlice(val) -} - -// Attributes that exist for S3 request types. -const ( - // AWSS3BucketKey is the attribute Key conforming to the "aws.s3.bucket" - // semantic conventions. It represents the S3 bucket name the request - // refers to. Corresponds to the `--bucket` parameter of the [S3 - // API](https://docs.aws.amazon.com/cli/latest/reference/s3api/index.html) - // operations. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'some-bucket-name' - // Note: The `bucket` attribute is applicable to all S3 operations that - // reference a bucket, i.e. that require the bucket name as a mandatory - // parameter. - // This applies to almost all S3 operations except `list-buckets`. - AWSS3BucketKey = attribute.Key("aws.s3.bucket") - - // AWSS3CopySourceKey is the attribute Key conforming to the - // "aws.s3.copy_source" semantic conventions. It represents the source - // object (in the form `bucket`/`key`) for the copy operation. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'someFile.yml' - // Note: The `copy_source` attribute applies to S3 copy operations and - // corresponds to the `--copy-source` parameter - // of the [copy-object operation within the S3 - // API](https://docs.aws.amazon.com/cli/latest/reference/s3api/copy-object.html). - // This applies in particular to the following operations: - // - // - - // [copy-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/copy-object.html) - // - - // [upload-part-copy](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part-copy.html) - AWSS3CopySourceKey = attribute.Key("aws.s3.copy_source") - - // AWSS3DeleteKey is the attribute Key conforming to the "aws.s3.delete" - // semantic conventions. It represents the delete request container that - // specifies the objects to be deleted. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: - // 'Objects=[{Key=string,VersionID=string},{Key=string,VersionID=string}],Quiet=boolean' - // Note: The `delete` attribute is only applicable to the - // [delete-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/delete-object.html) - // operation. - // The `delete` attribute corresponds to the `--delete` parameter of the - // [delete-objects operation within the S3 - // API](https://docs.aws.amazon.com/cli/latest/reference/s3api/delete-objects.html). - AWSS3DeleteKey = attribute.Key("aws.s3.delete") - - // AWSS3KeyKey is the attribute Key conforming to the "aws.s3.key" semantic - // conventions. It represents the S3 object key the request refers to. - // Corresponds to the `--key` parameter of the [S3 - // API](https://docs.aws.amazon.com/cli/latest/reference/s3api/index.html) - // operations. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'someFile.yml' - // Note: The `key` attribute is applicable to all object-related S3 - // operations, i.e. that require the object key as a mandatory parameter. - // This applies in particular to the following operations: - // - // - - // [copy-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/copy-object.html) - // - - // [delete-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/delete-object.html) - // - - // [get-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/get-object.html) - // - - // [head-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/head-object.html) - // - - // [put-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/put-object.html) - // - - // [restore-object](https://docs.aws.amazon.com/cli/latest/reference/s3api/restore-object.html) - // - - // [select-object-content](https://docs.aws.amazon.com/cli/latest/reference/s3api/select-object-content.html) - // - - // [abort-multipart-upload](https://docs.aws.amazon.com/cli/latest/reference/s3api/abort-multipart-upload.html) - // - - // [complete-multipart-upload](https://docs.aws.amazon.com/cli/latest/reference/s3api/complete-multipart-upload.html) - // - - // [create-multipart-upload](https://docs.aws.amazon.com/cli/latest/reference/s3api/create-multipart-upload.html) - // - - // [list-parts](https://docs.aws.amazon.com/cli/latest/reference/s3api/list-parts.html) - // - - // [upload-part](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part.html) - // - - // [upload-part-copy](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part-copy.html) - AWSS3KeyKey = attribute.Key("aws.s3.key") - - // AWSS3PartNumberKey is the attribute Key conforming to the - // "aws.s3.part_number" semantic conventions. It represents the part number - // of the part being uploaded in a multipart-upload operation. This is a - // positive integer between 1 and 10,000. - // - // Type: int - // RequirementLevel: Optional - // Stability: experimental - // Examples: 3456 - // Note: The `part_number` attribute is only applicable to the - // [upload-part](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part.html) - // and - // [upload-part-copy](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part-copy.html) - // operations. - // The `part_number` attribute corresponds to the `--part-number` parameter - // of the - // [upload-part operation within the S3 - // API](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part.html). - AWSS3PartNumberKey = attribute.Key("aws.s3.part_number") - - // AWSS3UploadIDKey is the attribute Key conforming to the - // "aws.s3.upload_id" semantic conventions. It represents the upload ID - // that identifies the multipart upload. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'dfRtDYWFbkRONycy.Yxwh66Yjlx.cph0gtNBtJ' - // Note: The `upload_id` attribute applies to S3 multipart-upload - // operations and corresponds to the `--upload-id` parameter - // of the [S3 - // API](https://docs.aws.amazon.com/cli/latest/reference/s3api/index.html) - // multipart operations. - // This applies in particular to the following operations: - // - // - - // [abort-multipart-upload](https://docs.aws.amazon.com/cli/latest/reference/s3api/abort-multipart-upload.html) - // - - // [complete-multipart-upload](https://docs.aws.amazon.com/cli/latest/reference/s3api/complete-multipart-upload.html) - // - - // [list-parts](https://docs.aws.amazon.com/cli/latest/reference/s3api/list-parts.html) - // - - // [upload-part](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part.html) - // - - // [upload-part-copy](https://docs.aws.amazon.com/cli/latest/reference/s3api/upload-part-copy.html) - AWSS3UploadIDKey = attribute.Key("aws.s3.upload_id") -) - -// AWSS3Bucket returns an attribute KeyValue conforming to the -// "aws.s3.bucket" semantic conventions. It represents the S3 bucket name the -// request refers to. Corresponds to the `--bucket` parameter of the [S3 -// API](https://docs.aws.amazon.com/cli/latest/reference/s3api/index.html) -// operations. -func AWSS3Bucket(val string) attribute.KeyValue { - return AWSS3BucketKey.String(val) -} - -// AWSS3CopySource returns an attribute KeyValue conforming to the -// "aws.s3.copy_source" semantic conventions. It represents the source object -// (in the form `bucket`/`key`) for the copy operation. -func AWSS3CopySource(val string) attribute.KeyValue { - return AWSS3CopySourceKey.String(val) -} - -// AWSS3Delete returns an attribute KeyValue conforming to the -// "aws.s3.delete" semantic conventions. It represents the delete request -// container that specifies the objects to be deleted. -func AWSS3Delete(val string) attribute.KeyValue { - return AWSS3DeleteKey.String(val) -} - -// AWSS3Key returns an attribute KeyValue conforming to the "aws.s3.key" -// semantic conventions. It represents the S3 object key the request refers to. -// Corresponds to the `--key` parameter of the [S3 -// API](https://docs.aws.amazon.com/cli/latest/reference/s3api/index.html) -// operations. -func AWSS3Key(val string) attribute.KeyValue { - return AWSS3KeyKey.String(val) -} - -// AWSS3PartNumber returns an attribute KeyValue conforming to the -// "aws.s3.part_number" semantic conventions. It represents the part number of -// the part being uploaded in a multipart-upload operation. This is a positive -// integer between 1 and 10,000. -func AWSS3PartNumber(val int) attribute.KeyValue { - return AWSS3PartNumberKey.Int(val) -} - -// AWSS3UploadID returns an attribute KeyValue conforming to the -// "aws.s3.upload_id" semantic conventions. It represents the upload ID that -// identifies the multipart upload. -func AWSS3UploadID(val string) attribute.KeyValue { - return AWSS3UploadIDKey.String(val) -} - -// Semantic conventions to apply when instrumenting the GraphQL implementation. -// They map GraphQL operations to attributes on a Span. -const ( - // GraphqlDocumentKey is the attribute Key conforming to the - // "graphql.document" semantic conventions. It represents the GraphQL - // document being executed. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'query findBookByID { bookByID(id: ?) { name } }' - // Note: The value may be sanitized to exclude sensitive information. - GraphqlDocumentKey = attribute.Key("graphql.document") - - // GraphqlOperationNameKey is the attribute Key conforming to the - // "graphql.operation.name" semantic conventions. It represents the name of - // the operation being executed. - // - // Type: string - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'findBookByID' - GraphqlOperationNameKey = attribute.Key("graphql.operation.name") - - // GraphqlOperationTypeKey is the attribute Key conforming to the - // "graphql.operation.type" semantic conventions. It represents the type of - // the operation being executed. - // - // Type: Enum - // RequirementLevel: Optional - // Stability: experimental - // Examples: 'query', 'mutation', 'subscription' - GraphqlOperationTypeKey = attribute.Key("graphql.operation.type") -) - -var ( - // GraphQL query - GraphqlOperationTypeQuery = GraphqlOperationTypeKey.String("query") - // GraphQL mutation - GraphqlOperationTypeMutation = GraphqlOperationTypeKey.String("mutation") - // GraphQL subscription - GraphqlOperationTypeSubscription = GraphqlOperationTypeKey.String("subscription") -) - -// GraphqlDocument returns an attribute KeyValue conforming to the -// "graphql.document" semantic conventions. It represents the GraphQL document -// being executed. -func GraphqlDocument(val string) attribute.KeyValue { - return GraphqlDocumentKey.String(val) -} - -// GraphqlOperationName returns an attribute KeyValue conforming to the -// "graphql.operation.name" semantic conventions. It represents the name of the -// operation being executed. -func GraphqlOperationName(val string) attribute.KeyValue { - return GraphqlOperationNameKey.String(val) -} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/provider.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/provider.go new file mode 100644 index 00000000000..ef85cb70c6d --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/provider.go @@ -0,0 +1,59 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package trace // import "go.opentelemetry.io/otel/trace" + +import "go.opentelemetry.io/otel/trace/embedded" + +// TracerProvider provides Tracers that are used by instrumentation code to +// trace computational workflows. +// +// A TracerProvider is the collection destination of all Spans from Tracers it +// provides, it represents a unique telemetry collection pipeline. How that +// pipeline is defined, meaning how those Spans are collected, processed, and +// where they are exported, depends on its implementation. Instrumentation +// authors do not need to define this implementation, rather just use the +// provided Tracers to instrument code. +// +// Commonly, instrumentation code will accept a TracerProvider implementation +// at runtime from its users or it can simply use the globally registered one +// (see https://pkg.go.dev/go.opentelemetry.io/otel#GetTracerProvider). +// +// Warning: Methods may be added to this interface in minor releases. See +// package documentation on API implementation for information on how to set +// default behavior for unimplemented methods. +type TracerProvider interface { + // Users of the interface can ignore this. This embedded type is only used + // by implementations of this interface. See the "API Implementations" + // section of the package documentation for more information. + embedded.TracerProvider + + // Tracer returns a unique Tracer scoped to be used by instrumentation code + // to trace computational workflows. The scope and identity of that + // instrumentation code is uniquely defined by the name and options passed. + // + // The passed name needs to uniquely identify instrumentation code. + // Therefore, it is recommended that name is the Go package name of the + // library providing instrumentation (note: not the code being + // instrumented). Instrumentation libraries can have multiple versions, + // therefore, the WithInstrumentationVersion option should be used to + // distinguish these different codebases. Additionally, instrumentation + // libraries may sometimes use traces to communicate different domains of + // workflow data (i.e. using spans to communicate workflow events only). If + // this is the case, the WithScopeAttributes option should be used to + // uniquely identify Tracers that handle the different domains of workflow + // data. + // + // If the same name and options are passed multiple times, the same Tracer + // will be returned (it is up to the implementation if this will be the + // same underlying instance of that Tracer or not). It is not necessary to + // call this multiple times with the same name and options to get an + // up-to-date Tracer. All implementations will ensure any TracerProvider + // configuration changes are propagated to all provided Tracers. + // + // If name is empty, then an implementation defined default name will be + // used instead. + // + // This method is safe to call concurrently. + Tracer(name string, options ...TracerOption) Tracer +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/span.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/span.go new file mode 100644 index 00000000000..d3aa476ee12 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/span.go @@ -0,0 +1,177 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package trace // import "go.opentelemetry.io/otel/trace" + +import ( + "context" + + "go.opentelemetry.io/otel/attribute" + "go.opentelemetry.io/otel/codes" + "go.opentelemetry.io/otel/trace/embedded" +) + +// Span is the individual component of a trace. It represents a single named +// and timed operation of a workflow that is traced. A Tracer is used to +// create a Span and it is then up to the operation the Span represents to +// properly end the Span when the operation itself ends. +// +// Warning: Methods may be added to this interface in minor releases. See +// package documentation on API implementation for information on how to set +// default behavior for unimplemented methods. +type Span interface { + // Users of the interface can ignore this. This embedded type is only used + // by implementations of this interface. See the "API Implementations" + // section of the package documentation for more information. + embedded.Span + + // End completes the Span. The Span is considered complete and ready to be + // delivered through the rest of the telemetry pipeline after this method + // is called. Therefore, updates to the Span are not allowed after this + // method has been called. + End(options ...SpanEndOption) + + // AddEvent adds an event with the provided name and options. + AddEvent(name string, options ...EventOption) + + // AddLink adds a link. + // Adding links at span creation using WithLinks is preferred to calling AddLink + // later, for contexts that are available during span creation, because head + // sampling decisions can only consider information present during span creation. + AddLink(link Link) + + // IsRecording returns the recording state of the Span. It will return + // true if the Span is active and events can be recorded. + IsRecording() bool + + // RecordError will record err as an exception span event for this span. An + // additional call to SetStatus is required if the Status of the Span should + // be set to Error, as this method does not change the Span status. If this + // span is not being recorded or err is nil then this method does nothing. + RecordError(err error, options ...EventOption) + + // SpanContext returns the SpanContext of the Span. The returned SpanContext + // is usable even after the End method has been called for the Span. + SpanContext() SpanContext + + // SetStatus sets the status of the Span in the form of a code and a + // description, provided the status hasn't already been set to a higher + // value before (OK > Error > Unset). The description is only included in a + // status when the code is for an error. + SetStatus(code codes.Code, description string) + + // SetName sets the Span name. + SetName(name string) + + // SetAttributes sets kv as attributes of the Span. If a key from kv + // already exists for an attribute of the Span it will be overwritten with + // the value contained in kv. + SetAttributes(kv ...attribute.KeyValue) + + // TracerProvider returns a TracerProvider that can be used to generate + // additional Spans on the same telemetry pipeline as the current Span. + TracerProvider() TracerProvider +} + +// Link is the relationship between two Spans. The relationship can be within +// the same Trace or across different Traces. +// +// For example, a Link is used in the following situations: +// +// 1. Batch Processing: A batch of operations may contain operations +// associated with one or more traces/spans. Since there can only be one +// parent SpanContext, a Link is used to keep reference to the +// SpanContext of all operations in the batch. +// 2. Public Endpoint: A SpanContext for an in incoming client request on a +// public endpoint should be considered untrusted. In such a case, a new +// trace with its own identity and sampling decision needs to be created, +// but this new trace needs to be related to the original trace in some +// form. A Link is used to keep reference to the original SpanContext and +// track the relationship. +type Link struct { + // SpanContext of the linked Span. + SpanContext SpanContext + + // Attributes describe the aspects of the link. + Attributes []attribute.KeyValue +} + +// LinkFromContext returns a link encapsulating the SpanContext in the provided +// ctx. +func LinkFromContext(ctx context.Context, attrs ...attribute.KeyValue) Link { + return Link{ + SpanContext: SpanContextFromContext(ctx), + Attributes: attrs, + } +} + +// SpanKind is the role a Span plays in a Trace. +type SpanKind int + +// As a convenience, these match the proto definition, see +// https://github.com/open-telemetry/opentelemetry-proto/blob/30d237e1ff3ab7aa50e0922b5bebdd93505090af/opentelemetry/proto/trace/v1/trace.proto#L101-L129 +// +// The unspecified value is not a valid `SpanKind`. Use `ValidateSpanKind()` +// to coerce a span kind to a valid value. +const ( + // SpanKindUnspecified is an unspecified SpanKind and is not a valid + // SpanKind. SpanKindUnspecified should be replaced with SpanKindInternal + // if it is received. + SpanKindUnspecified SpanKind = 0 + // SpanKindInternal is a SpanKind for a Span that represents an internal + // operation within an application. + SpanKindInternal SpanKind = 1 + // SpanKindServer is a SpanKind for a Span that represents the operation + // of handling a request from a client. + SpanKindServer SpanKind = 2 + // SpanKindClient is a SpanKind for a Span that represents the operation + // of client making a request to a server. + SpanKindClient SpanKind = 3 + // SpanKindProducer is a SpanKind for a Span that represents the operation + // of a producer sending a message to a message broker. Unlike + // SpanKindClient and SpanKindServer, there is often no direct + // relationship between this kind of Span and a SpanKindConsumer kind. A + // SpanKindProducer Span will end once the message is accepted by the + // message broker which might not overlap with the processing of that + // message. + SpanKindProducer SpanKind = 4 + // SpanKindConsumer is a SpanKind for a Span that represents the operation + // of a consumer receiving a message from a message broker. Like + // SpanKindProducer Spans, there is often no direct relationship between + // this Span and the Span that produced the message. + SpanKindConsumer SpanKind = 5 +) + +// ValidateSpanKind returns a valid span kind value. This will coerce +// invalid values into the default value, SpanKindInternal. +func ValidateSpanKind(spanKind SpanKind) SpanKind { + switch spanKind { + case SpanKindInternal, + SpanKindServer, + SpanKindClient, + SpanKindProducer, + SpanKindConsumer: + // valid + return spanKind + default: + return SpanKindInternal + } +} + +// String returns the specified name of the SpanKind in lower-case. +func (sk SpanKind) String() string { + switch sk { + case SpanKindInternal: + return "internal" + case SpanKindServer: + return "server" + case SpanKindClient: + return "client" + case SpanKindProducer: + return "producer" + case SpanKindConsumer: + return "consumer" + default: + return "unspecified" + } +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/trace.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/trace.go index 28877d4ab4d..d49adf671b9 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/trace.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/trace.go @@ -5,13 +5,8 @@ package trace // import "go.opentelemetry.io/otel/trace" import ( "bytes" - "context" "encoding/hex" "encoding/json" - - "go.opentelemetry.io/otel/attribute" - "go.opentelemetry.io/otel/codes" - "go.opentelemetry.io/otel/trace/embedded" ) const ( @@ -326,247 +321,3 @@ func (sc SpanContext) MarshalJSON() ([]byte, error) { Remote: sc.remote, }) } - -// Span is the individual component of a trace. It represents a single named -// and timed operation of a workflow that is traced. A Tracer is used to -// create a Span and it is then up to the operation the Span represents to -// properly end the Span when the operation itself ends. -// -// Warning: Methods may be added to this interface in minor releases. See -// package documentation on API implementation for information on how to set -// default behavior for unimplemented methods. -type Span interface { - // Users of the interface can ignore this. This embedded type is only used - // by implementations of this interface. See the "API Implementations" - // section of the package documentation for more information. - embedded.Span - - // End completes the Span. The Span is considered complete and ready to be - // delivered through the rest of the telemetry pipeline after this method - // is called. Therefore, updates to the Span are not allowed after this - // method has been called. - End(options ...SpanEndOption) - - // AddEvent adds an event with the provided name and options. - AddEvent(name string, options ...EventOption) - - // AddLink adds a link. - // Adding links at span creation using WithLinks is preferred to calling AddLink - // later, for contexts that are available during span creation, because head - // sampling decisions can only consider information present during span creation. - AddLink(link Link) - - // IsRecording returns the recording state of the Span. It will return - // true if the Span is active and events can be recorded. - IsRecording() bool - - // RecordError will record err as an exception span event for this span. An - // additional call to SetStatus is required if the Status of the Span should - // be set to Error, as this method does not change the Span status. If this - // span is not being recorded or err is nil then this method does nothing. - RecordError(err error, options ...EventOption) - - // SpanContext returns the SpanContext of the Span. The returned SpanContext - // is usable even after the End method has been called for the Span. - SpanContext() SpanContext - - // SetStatus sets the status of the Span in the form of a code and a - // description, provided the status hasn't already been set to a higher - // value before (OK > Error > Unset). The description is only included in a - // status when the code is for an error. - SetStatus(code codes.Code, description string) - - // SetName sets the Span name. - SetName(name string) - - // SetAttributes sets kv as attributes of the Span. If a key from kv - // already exists for an attribute of the Span it will be overwritten with - // the value contained in kv. - SetAttributes(kv ...attribute.KeyValue) - - // TracerProvider returns a TracerProvider that can be used to generate - // additional Spans on the same telemetry pipeline as the current Span. - TracerProvider() TracerProvider -} - -// Link is the relationship between two Spans. The relationship can be within -// the same Trace or across different Traces. -// -// For example, a Link is used in the following situations: -// -// 1. Batch Processing: A batch of operations may contain operations -// associated with one or more traces/spans. Since there can only be one -// parent SpanContext, a Link is used to keep reference to the -// SpanContext of all operations in the batch. -// 2. Public Endpoint: A SpanContext for an in incoming client request on a -// public endpoint should be considered untrusted. In such a case, a new -// trace with its own identity and sampling decision needs to be created, -// but this new trace needs to be related to the original trace in some -// form. A Link is used to keep reference to the original SpanContext and -// track the relationship. -type Link struct { - // SpanContext of the linked Span. - SpanContext SpanContext - - // Attributes describe the aspects of the link. - Attributes []attribute.KeyValue -} - -// LinkFromContext returns a link encapsulating the SpanContext in the provided ctx. -func LinkFromContext(ctx context.Context, attrs ...attribute.KeyValue) Link { - return Link{ - SpanContext: SpanContextFromContext(ctx), - Attributes: attrs, - } -} - -// SpanKind is the role a Span plays in a Trace. -type SpanKind int - -// As a convenience, these match the proto definition, see -// https://github.com/open-telemetry/opentelemetry-proto/blob/30d237e1ff3ab7aa50e0922b5bebdd93505090af/opentelemetry/proto/trace/v1/trace.proto#L101-L129 -// -// The unspecified value is not a valid `SpanKind`. Use `ValidateSpanKind()` -// to coerce a span kind to a valid value. -const ( - // SpanKindUnspecified is an unspecified SpanKind and is not a valid - // SpanKind. SpanKindUnspecified should be replaced with SpanKindInternal - // if it is received. - SpanKindUnspecified SpanKind = 0 - // SpanKindInternal is a SpanKind for a Span that represents an internal - // operation within an application. - SpanKindInternal SpanKind = 1 - // SpanKindServer is a SpanKind for a Span that represents the operation - // of handling a request from a client. - SpanKindServer SpanKind = 2 - // SpanKindClient is a SpanKind for a Span that represents the operation - // of client making a request to a server. - SpanKindClient SpanKind = 3 - // SpanKindProducer is a SpanKind for a Span that represents the operation - // of a producer sending a message to a message broker. Unlike - // SpanKindClient and SpanKindServer, there is often no direct - // relationship between this kind of Span and a SpanKindConsumer kind. A - // SpanKindProducer Span will end once the message is accepted by the - // message broker which might not overlap with the processing of that - // message. - SpanKindProducer SpanKind = 4 - // SpanKindConsumer is a SpanKind for a Span that represents the operation - // of a consumer receiving a message from a message broker. Like - // SpanKindProducer Spans, there is often no direct relationship between - // this Span and the Span that produced the message. - SpanKindConsumer SpanKind = 5 -) - -// ValidateSpanKind returns a valid span kind value. This will coerce -// invalid values into the default value, SpanKindInternal. -func ValidateSpanKind(spanKind SpanKind) SpanKind { - switch spanKind { - case SpanKindInternal, - SpanKindServer, - SpanKindClient, - SpanKindProducer, - SpanKindConsumer: - // valid - return spanKind - default: - return SpanKindInternal - } -} - -// String returns the specified name of the SpanKind in lower-case. -func (sk SpanKind) String() string { - switch sk { - case SpanKindInternal: - return "internal" - case SpanKindServer: - return "server" - case SpanKindClient: - return "client" - case SpanKindProducer: - return "producer" - case SpanKindConsumer: - return "consumer" - default: - return "unspecified" - } -} - -// Tracer is the creator of Spans. -// -// Warning: Methods may be added to this interface in minor releases. See -// package documentation on API implementation for information on how to set -// default behavior for unimplemented methods. -type Tracer interface { - // Users of the interface can ignore this. This embedded type is only used - // by implementations of this interface. See the "API Implementations" - // section of the package documentation for more information. - embedded.Tracer - - // Start creates a span and a context.Context containing the newly-created span. - // - // If the context.Context provided in `ctx` contains a Span then the newly-created - // Span will be a child of that span, otherwise it will be a root span. This behavior - // can be overridden by providing `WithNewRoot()` as a SpanOption, causing the - // newly-created Span to be a root span even if `ctx` contains a Span. - // - // When creating a Span it is recommended to provide all known span attributes using - // the `WithAttributes()` SpanOption as samplers will only have access to the - // attributes provided when a Span is created. - // - // Any Span that is created MUST also be ended. This is the responsibility of the user. - // Implementations of this API may leak memory or other resources if Spans are not ended. - Start(ctx context.Context, spanName string, opts ...SpanStartOption) (context.Context, Span) -} - -// TracerProvider provides Tracers that are used by instrumentation code to -// trace computational workflows. -// -// A TracerProvider is the collection destination of all Spans from Tracers it -// provides, it represents a unique telemetry collection pipeline. How that -// pipeline is defined, meaning how those Spans are collected, processed, and -// where they are exported, depends on its implementation. Instrumentation -// authors do not need to define this implementation, rather just use the -// provided Tracers to instrument code. -// -// Commonly, instrumentation code will accept a TracerProvider implementation -// at runtime from its users or it can simply use the globally registered one -// (see https://pkg.go.dev/go.opentelemetry.io/otel#GetTracerProvider). -// -// Warning: Methods may be added to this interface in minor releases. See -// package documentation on API implementation for information on how to set -// default behavior for unimplemented methods. -type TracerProvider interface { - // Users of the interface can ignore this. This embedded type is only used - // by implementations of this interface. See the "API Implementations" - // section of the package documentation for more information. - embedded.TracerProvider - - // Tracer returns a unique Tracer scoped to be used by instrumentation code - // to trace computational workflows. The scope and identity of that - // instrumentation code is uniquely defined by the name and options passed. - // - // The passed name needs to uniquely identify instrumentation code. - // Therefore, it is recommended that name is the Go package name of the - // library providing instrumentation (note: not the code being - // instrumented). Instrumentation libraries can have multiple versions, - // therefore, the WithInstrumentationVersion option should be used to - // distinguish these different codebases. Additionally, instrumentation - // libraries may sometimes use traces to communicate different domains of - // workflow data (i.e. using spans to communicate workflow events only). If - // this is the case, the WithScopeAttributes option should be used to - // uniquely identify Tracers that handle the different domains of workflow - // data. - // - // If the same name and options are passed multiple times, the same Tracer - // will be returned (it is up to the implementation if this will be the - // same underlying instance of that Tracer or not). It is not necessary to - // call this multiple times with the same name and options to get an - // up-to-date Tracer. All implementations will ensure any TracerProvider - // configuration changes are propagated to all provided Tracers. - // - // If name is empty, then an implementation defined default name will be - // used instead. - // - // This method is safe to call concurrently. - Tracer(name string, options ...TracerOption) Tracer -} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracer.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracer.go new file mode 100644 index 00000000000..77952d2a0b3 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracer.go @@ -0,0 +1,37 @@ +// Copyright The OpenTelemetry Authors +// SPDX-License-Identifier: Apache-2.0 + +package trace // import "go.opentelemetry.io/otel/trace" + +import ( + "context" + + "go.opentelemetry.io/otel/trace/embedded" +) + +// Tracer is the creator of Spans. +// +// Warning: Methods may be added to this interface in minor releases. See +// package documentation on API implementation for information on how to set +// default behavior for unimplemented methods. +type Tracer interface { + // Users of the interface can ignore this. This embedded type is only used + // by implementations of this interface. See the "API Implementations" + // section of the package documentation for more information. + embedded.Tracer + + // Start creates a span and a context.Context containing the newly-created span. + // + // If the context.Context provided in `ctx` contains a Span then the newly-created + // Span will be a child of that span, otherwise it will be a root span. This behavior + // can be overridden by providing `WithNewRoot()` as a SpanOption, causing the + // newly-created Span to be a root span even if `ctx` contains a Span. + // + // When creating a Span it is recommended to provide all known span attributes using + // the `WithAttributes()` SpanOption as samplers will only have access to the + // attributes provided when a Span is created. + // + // Any Span that is created MUST also be ended. This is the responsibility of the user. + // Implementations of this API may leak memory or other resources if Spans are not ended. + Start(ctx context.Context, spanName string, opts ...SpanStartOption) (context.Context, Span) +} diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracestate.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracestate.go index 20b5cf24332..dc5e34cad0d 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracestate.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/trace/tracestate.go @@ -260,6 +260,16 @@ func (ts TraceState) Get(key string) string { return "" } +// Walk walks all key value pairs in the TraceState by calling f +// Iteration stops if f returns false. +func (ts TraceState) Walk(f func(key, value string) bool) { + for _, m := range ts.list { + if !f(m.Key, m.Value) { + break + } + } +} + // Insert adds a new list-member defined by the key/value pair to the // TraceState. If a list-member already exists for the given key, that // list-member's value is updated. The new or updated list-member is always diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/verify_released_changelog.sh b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/verify_released_changelog.sh new file mode 100644 index 00000000000..c9b7cdbbfef --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/verify_released_changelog.sh @@ -0,0 +1,42 @@ +#!/bin/bash + +# Copyright The OpenTelemetry Authors +# SPDX-License-Identifier: Apache-2.0 + +set -euo pipefail + +TARGET="${1:?Must provide target ref}" + +FILE="CHANGELOG.md" +TEMP_DIR=$(mktemp -d) +echo "Temp folder: $TEMP_DIR" + +# Only the latest commit of the feature branch is available +# automatically. To diff with the base branch, we need to +# fetch that too (and we only need its latest commit). +git fetch origin "${TARGET}" --depth=1 + +# Checkout the previous version on the base branch of the changelog to tmpfolder +git --work-tree="$TEMP_DIR" checkout FETCH_HEAD $FILE + +PREVIOUS_FILE="$TEMP_DIR/$FILE" +CURRENT_FILE="$FILE" +PREVIOUS_LOCKED_FILE="$TEMP_DIR/previous_locked_section.md" +CURRENT_LOCKED_FILE="$TEMP_DIR/current_locked_section.md" + +# Extract released sections from the previous version +awk '/^/ {flag=1} /^/ {flag=0} flag' "$PREVIOUS_FILE" > "$PREVIOUS_LOCKED_FILE" + +# Extract released sections from the current version +awk '/^/ {flag=1} /^/ {flag=0} flag' "$CURRENT_FILE" > "$CURRENT_LOCKED_FILE" + +# Compare the released sections +if ! diff -q "$PREVIOUS_LOCKED_FILE" "$CURRENT_LOCKED_FILE"; then + echo "Error: The released sections of the changelog file have been modified." + diff "$PREVIOUS_LOCKED_FILE" "$CURRENT_LOCKED_FILE" + rm -rf "$TEMP_DIR" + false +fi + +rm -rf "$TEMP_DIR" +echo "The released sections remain unchanged." diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/version.go b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/version.go index ab28960524b..f67039ed1f9 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/version.go +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/version.go @@ -5,5 +5,5 @@ package otel // import "go.opentelemetry.io/otel" // Version is the current release version of OpenTelemetry in use. func Version() string { - return "1.28.0" + return "1.29.0" } diff --git a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/versions.yaml b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/versions.yaml index 241cfc82a8d..3ba611d7136 100644 --- a/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/versions.yaml +++ b/cluster-api/providers/vsphere/vendor/go.opentelemetry.io/otel/versions.yaml @@ -3,7 +3,7 @@ module-sets: stable-v1: - version: v1.28.0 + version: v1.29.0 modules: - go.opentelemetry.io/otel - go.opentelemetry.io/otel/bridge/opencensus @@ -29,15 +29,16 @@ module-sets: - go.opentelemetry.io/otel/sdk/metric - go.opentelemetry.io/otel/trace experimental-metrics: - version: v0.50.0 + version: v0.51.0 modules: - go.opentelemetry.io/otel/example/prometheus - go.opentelemetry.io/otel/exporters/prometheus experimental-logs: - version: v0.4.0 + version: v0.5.0 modules: - go.opentelemetry.io/otel/log - go.opentelemetry.io/otel/sdk/log + - go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc - go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploghttp - go.opentelemetry.io/otel/exporters/stdout/stdoutlog experimental-schema: @@ -46,4 +47,3 @@ module-sets: - go.opentelemetry.io/otel/schema excluded-modules: - go.opentelemetry.io/otel/internal/tools - - go.opentelemetry.io/otel/exporters/otlp/otlplog/otlploggrpc diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/atom/table.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/atom/table.go index 2a938864cb9..b460e6f722b 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/atom/table.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/atom/table.go @@ -11,23 +11,23 @@ const ( AcceptCharset Atom = 0x1a0e Accesskey Atom = 0x2c09 Acronym Atom = 0xaa07 - Action Atom = 0x27206 - Address Atom = 0x6f307 + Action Atom = 0x26506 + Address Atom = 0x6f107 Align Atom = 0xb105 - Allowfullscreen Atom = 0x2080f + Allowfullscreen Atom = 0x3280f Allowpaymentrequest Atom = 0xc113 Allowusermedia Atom = 0xdd0e Alt Atom = 0xf303 Annotation Atom = 0x1c90a AnnotationXml Atom = 0x1c90e - Applet Atom = 0x31906 - Area Atom = 0x35604 - Article Atom = 0x3fc07 + Applet Atom = 0x30806 + Area Atom = 0x35004 + Article Atom = 0x3f607 As Atom = 0x3c02 Aside Atom = 0x10705 Async Atom = 0xff05 Audio Atom = 0x11505 - Autocomplete Atom = 0x2780c + Autocomplete Atom = 0x26b0c Autofocus Atom = 0x12109 Autoplay Atom = 0x13c08 B Atom = 0x101 @@ -43,34 +43,34 @@ const ( Br Atom = 0x202 Button Atom = 0x19106 Canvas Atom = 0x10306 - Caption Atom = 0x23107 - Center Atom = 0x22006 - Challenge Atom = 0x29b09 + Caption Atom = 0x22407 + Center Atom = 0x21306 + Challenge Atom = 0x28e09 Charset Atom = 0x2107 - Checked Atom = 0x47907 + Checked Atom = 0x5b507 Cite Atom = 0x19c04 - Class Atom = 0x56405 - Code Atom = 0x5c504 + Class Atom = 0x55805 + Code Atom = 0x5ee04 Col Atom = 0x1ab03 Colgroup Atom = 0x1ab08 Color Atom = 0x1bf05 Cols Atom = 0x1c404 Colspan Atom = 0x1c407 Command Atom = 0x1d707 - Content Atom = 0x58b07 - Contenteditable Atom = 0x58b0f - Contextmenu Atom = 0x3800b + Content Atom = 0x57b07 + Contenteditable Atom = 0x57b0f + Contextmenu Atom = 0x37a0b Controls Atom = 0x1de08 - Coords Atom = 0x1ea06 - Crossorigin Atom = 0x1fb0b - Data Atom = 0x4a504 - Datalist Atom = 0x4a508 - Datetime Atom = 0x2b808 - Dd Atom = 0x2d702 + Coords Atom = 0x1f006 + Crossorigin Atom = 0x1fa0b + Data Atom = 0x49904 + Datalist Atom = 0x49908 + Datetime Atom = 0x2ab08 + Dd Atom = 0x2bf02 Default Atom = 0x10a07 - Defer Atom = 0x5c705 - Del Atom = 0x45203 - Desc Atom = 0x56104 + Defer Atom = 0x5f005 + Del Atom = 0x44c03 + Desc Atom = 0x55504 Details Atom = 0x7207 Dfn Atom = 0x8703 Dialog Atom = 0xbb06 @@ -78,106 +78,106 @@ const ( Dirname Atom = 0x9307 Disabled Atom = 0x16408 Div Atom = 0x16b03 - Dl Atom = 0x5e602 - Download Atom = 0x46308 + Dl Atom = 0x5d602 + Download Atom = 0x45d08 Draggable Atom = 0x17a09 - Dropzone Atom = 0x40508 - Dt Atom = 0x64b02 + Dropzone Atom = 0x3ff08 + Dt Atom = 0x64002 Em Atom = 0x6e02 Embed Atom = 0x6e05 - Enctype Atom = 0x28d07 - Face Atom = 0x21e04 - Fieldset Atom = 0x22608 - Figcaption Atom = 0x22e0a - Figure Atom = 0x24806 + Enctype Atom = 0x28007 + Face Atom = 0x21104 + Fieldset Atom = 0x21908 + Figcaption Atom = 0x2210a + Figure Atom = 0x23b06 Font Atom = 0x3f04 Footer Atom = 0xf606 - For Atom = 0x25403 - ForeignObject Atom = 0x2540d - Foreignobject Atom = 0x2610d - Form Atom = 0x26e04 - Formaction Atom = 0x26e0a - Formenctype Atom = 0x2890b - Formmethod Atom = 0x2a40a - Formnovalidate Atom = 0x2ae0e - Formtarget Atom = 0x2c00a + For Atom = 0x24703 + ForeignObject Atom = 0x2470d + Foreignobject Atom = 0x2540d + Form Atom = 0x26104 + Formaction Atom = 0x2610a + Formenctype Atom = 0x27c0b + Formmethod Atom = 0x2970a + Formnovalidate Atom = 0x2a10e + Formtarget Atom = 0x2b30a Frame Atom = 0x8b05 Frameset Atom = 0x8b08 H1 Atom = 0x15c02 - H2 Atom = 0x2de02 - H3 Atom = 0x30d02 - H4 Atom = 0x34502 - H5 Atom = 0x34f02 - H6 Atom = 0x64d02 - Head Atom = 0x33104 - Header Atom = 0x33106 - Headers Atom = 0x33107 + H2 Atom = 0x56102 + H3 Atom = 0x2cd02 + H4 Atom = 0x2fc02 + H5 Atom = 0x33f02 + H6 Atom = 0x34902 + Head Atom = 0x32004 + Header Atom = 0x32006 + Headers Atom = 0x32007 Height Atom = 0x5206 - Hgroup Atom = 0x2ca06 - Hidden Atom = 0x2d506 - High Atom = 0x2db04 + Hgroup Atom = 0x64206 + Hidden Atom = 0x2bd06 + High Atom = 0x2ca04 Hr Atom = 0x15702 - Href Atom = 0x2e004 - Hreflang Atom = 0x2e008 + Href Atom = 0x2cf04 + Hreflang Atom = 0x2cf08 Html Atom = 0x5604 - HttpEquiv Atom = 0x2e80a + HttpEquiv Atom = 0x2d70a I Atom = 0x601 - Icon Atom = 0x58a04 + Icon Atom = 0x57a04 Id Atom = 0x10902 - Iframe Atom = 0x2fc06 - Image Atom = 0x30205 - Img Atom = 0x30703 - Input Atom = 0x44b05 - Inputmode Atom = 0x44b09 - Ins Atom = 0x20403 - Integrity Atom = 0x23f09 + Iframe Atom = 0x2eb06 + Image Atom = 0x2f105 + Img Atom = 0x2f603 + Input Atom = 0x44505 + Inputmode Atom = 0x44509 + Ins Atom = 0x20303 + Integrity Atom = 0x23209 Is Atom = 0x16502 - Isindex Atom = 0x30f07 - Ismap Atom = 0x31605 - Itemid Atom = 0x38b06 + Isindex Atom = 0x2fe07 + Ismap Atom = 0x30505 + Itemid Atom = 0x38506 Itemprop Atom = 0x19d08 - Itemref Atom = 0x3cd07 - Itemscope Atom = 0x67109 - Itemtype Atom = 0x31f08 + Itemref Atom = 0x3c707 + Itemscope Atom = 0x66f09 + Itemtype Atom = 0x30e08 Kbd Atom = 0xb903 Keygen Atom = 0x3206 Keytype Atom = 0xd607 Kind Atom = 0x17704 Label Atom = 0x5905 - Lang Atom = 0x2e404 + Lang Atom = 0x2d304 Legend Atom = 0x18106 Li Atom = 0xb202 Link Atom = 0x17404 - List Atom = 0x4a904 - Listing Atom = 0x4a907 + List Atom = 0x49d04 + Listing Atom = 0x49d07 Loop Atom = 0x5d04 Low Atom = 0xc303 Main Atom = 0x1004 Malignmark Atom = 0xb00a - Manifest Atom = 0x6d708 - Map Atom = 0x31803 + Manifest Atom = 0x6d508 + Map Atom = 0x30703 Mark Atom = 0xb604 - Marquee Atom = 0x32707 - Math Atom = 0x32e04 - Max Atom = 0x33d03 - Maxlength Atom = 0x33d09 + Marquee Atom = 0x31607 + Math Atom = 0x31d04 + Max Atom = 0x33703 + Maxlength Atom = 0x33709 Media Atom = 0xe605 Mediagroup Atom = 0xe60a - Menu Atom = 0x38704 - Menuitem Atom = 0x38708 - Meta Atom = 0x4b804 + Menu Atom = 0x38104 + Menuitem Atom = 0x38108 + Meta Atom = 0x4ac04 Meter Atom = 0x9805 - Method Atom = 0x2a806 - Mglyph Atom = 0x30806 - Mi Atom = 0x34702 - Min Atom = 0x34703 - Minlength Atom = 0x34709 - Mn Atom = 0x2b102 + Method Atom = 0x29b06 + Mglyph Atom = 0x2f706 + Mi Atom = 0x34102 + Min Atom = 0x34103 + Minlength Atom = 0x34109 + Mn Atom = 0x2a402 Mo Atom = 0xa402 - Ms Atom = 0x67402 - Mtext Atom = 0x35105 - Multiple Atom = 0x35f08 - Muted Atom = 0x36705 + Ms Atom = 0x67202 + Mtext Atom = 0x34b05 + Multiple Atom = 0x35908 + Muted Atom = 0x36105 Name Atom = 0x9604 Nav Atom = 0x1303 Nobr Atom = 0x3704 @@ -185,101 +185,101 @@ const ( Noframes Atom = 0x8908 Nomodule Atom = 0xa208 Nonce Atom = 0x1a605 - Noscript Atom = 0x21608 - Novalidate Atom = 0x2b20a - Object Atom = 0x26806 + Noscript Atom = 0x2c208 + Novalidate Atom = 0x2a50a + Object Atom = 0x25b06 Ol Atom = 0x13702 Onabort Atom = 0x19507 - Onafterprint Atom = 0x2360c - Onautocomplete Atom = 0x2760e - Onautocompleteerror Atom = 0x27613 - Onauxclick Atom = 0x61f0a - Onbeforeprint Atom = 0x69e0d - Onbeforeunload Atom = 0x6e70e - Onblur Atom = 0x56d06 + Onafterprint Atom = 0x2290c + Onautocomplete Atom = 0x2690e + Onautocompleteerror Atom = 0x26913 + Onauxclick Atom = 0x6140a + Onbeforeprint Atom = 0x69c0d + Onbeforeunload Atom = 0x6e50e + Onblur Atom = 0x1ea06 Oncancel Atom = 0x11908 Oncanplay Atom = 0x14d09 Oncanplaythrough Atom = 0x14d10 - Onchange Atom = 0x41b08 - Onclick Atom = 0x2f507 - Onclose Atom = 0x36c07 - Oncontextmenu Atom = 0x37e0d - Oncopy Atom = 0x39106 - Oncuechange Atom = 0x3970b - Oncut Atom = 0x3a205 - Ondblclick Atom = 0x3a70a - Ondrag Atom = 0x3b106 - Ondragend Atom = 0x3b109 - Ondragenter Atom = 0x3ba0b - Ondragexit Atom = 0x3c50a - Ondragleave Atom = 0x3df0b - Ondragover Atom = 0x3ea0a - Ondragstart Atom = 0x3f40b - Ondrop Atom = 0x40306 - Ondurationchange Atom = 0x41310 - Onemptied Atom = 0x40a09 - Onended Atom = 0x42307 - Onerror Atom = 0x42a07 - Onfocus Atom = 0x43107 - Onhashchange Atom = 0x43d0c - Oninput Atom = 0x44907 - Oninvalid Atom = 0x45509 - Onkeydown Atom = 0x45e09 - Onkeypress Atom = 0x46b0a - Onkeyup Atom = 0x48007 - Onlanguagechange Atom = 0x48d10 - Onload Atom = 0x49d06 - Onloadeddata Atom = 0x49d0c - Onloadedmetadata Atom = 0x4b010 - Onloadend Atom = 0x4c609 - Onloadstart Atom = 0x4cf0b - Onmessage Atom = 0x4da09 - Onmessageerror Atom = 0x4da0e - Onmousedown Atom = 0x4e80b - Onmouseenter Atom = 0x4f30c - Onmouseleave Atom = 0x4ff0c - Onmousemove Atom = 0x50b0b - Onmouseout Atom = 0x5160a - Onmouseover Atom = 0x5230b - Onmouseup Atom = 0x52e09 - Onmousewheel Atom = 0x53c0c - Onoffline Atom = 0x54809 - Ononline Atom = 0x55108 - Onpagehide Atom = 0x5590a - Onpageshow Atom = 0x5730a - Onpaste Atom = 0x57f07 - Onpause Atom = 0x59a07 - Onplay Atom = 0x5a406 - Onplaying Atom = 0x5a409 - Onpopstate Atom = 0x5ad0a - Onprogress Atom = 0x5b70a - Onratechange Atom = 0x5cc0c - Onrejectionhandled Atom = 0x5d812 - Onreset Atom = 0x5ea07 - Onresize Atom = 0x5f108 - Onscroll Atom = 0x60008 - Onsecuritypolicyviolation Atom = 0x60819 - Onseeked Atom = 0x62908 - Onseeking Atom = 0x63109 - Onselect Atom = 0x63a08 - Onshow Atom = 0x64406 - Onsort Atom = 0x64f06 - Onstalled Atom = 0x65909 - Onstorage Atom = 0x66209 - Onsubmit Atom = 0x66b08 - Onsuspend Atom = 0x67b09 + Onchange Atom = 0x41508 + Onclick Atom = 0x2e407 + Onclose Atom = 0x36607 + Oncontextmenu Atom = 0x3780d + Oncopy Atom = 0x38b06 + Oncuechange Atom = 0x3910b + Oncut Atom = 0x39c05 + Ondblclick Atom = 0x3a10a + Ondrag Atom = 0x3ab06 + Ondragend Atom = 0x3ab09 + Ondragenter Atom = 0x3b40b + Ondragexit Atom = 0x3bf0a + Ondragleave Atom = 0x3d90b + Ondragover Atom = 0x3e40a + Ondragstart Atom = 0x3ee0b + Ondrop Atom = 0x3fd06 + Ondurationchange Atom = 0x40d10 + Onemptied Atom = 0x40409 + Onended Atom = 0x41d07 + Onerror Atom = 0x42407 + Onfocus Atom = 0x42b07 + Onhashchange Atom = 0x4370c + Oninput Atom = 0x44307 + Oninvalid Atom = 0x44f09 + Onkeydown Atom = 0x45809 + Onkeypress Atom = 0x4650a + Onkeyup Atom = 0x47407 + Onlanguagechange Atom = 0x48110 + Onload Atom = 0x49106 + Onloadeddata Atom = 0x4910c + Onloadedmetadata Atom = 0x4a410 + Onloadend Atom = 0x4ba09 + Onloadstart Atom = 0x4c30b + Onmessage Atom = 0x4ce09 + Onmessageerror Atom = 0x4ce0e + Onmousedown Atom = 0x4dc0b + Onmouseenter Atom = 0x4e70c + Onmouseleave Atom = 0x4f30c + Onmousemove Atom = 0x4ff0b + Onmouseout Atom = 0x50a0a + Onmouseover Atom = 0x5170b + Onmouseup Atom = 0x52209 + Onmousewheel Atom = 0x5300c + Onoffline Atom = 0x53c09 + Ononline Atom = 0x54508 + Onpagehide Atom = 0x54d0a + Onpageshow Atom = 0x5630a + Onpaste Atom = 0x56f07 + Onpause Atom = 0x58a07 + Onplay Atom = 0x59406 + Onplaying Atom = 0x59409 + Onpopstate Atom = 0x59d0a + Onprogress Atom = 0x5a70a + Onratechange Atom = 0x5bc0c + Onrejectionhandled Atom = 0x5c812 + Onreset Atom = 0x5da07 + Onresize Atom = 0x5e108 + Onscroll Atom = 0x5f508 + Onsecuritypolicyviolation Atom = 0x5fd19 + Onseeked Atom = 0x61e08 + Onseeking Atom = 0x62609 + Onselect Atom = 0x62f08 + Onshow Atom = 0x63906 + Onsort Atom = 0x64d06 + Onstalled Atom = 0x65709 + Onstorage Atom = 0x66009 + Onsubmit Atom = 0x66908 + Onsuspend Atom = 0x67909 Ontimeupdate Atom = 0x400c - Ontoggle Atom = 0x68408 - Onunhandledrejection Atom = 0x68c14 - Onunload Atom = 0x6ab08 - Onvolumechange Atom = 0x6b30e - Onwaiting Atom = 0x6c109 - Onwheel Atom = 0x6ca07 + Ontoggle Atom = 0x68208 + Onunhandledrejection Atom = 0x68a14 + Onunload Atom = 0x6a908 + Onvolumechange Atom = 0x6b10e + Onwaiting Atom = 0x6bf09 + Onwheel Atom = 0x6c807 Open Atom = 0x1a304 Optgroup Atom = 0x5f08 - Optimum Atom = 0x6d107 - Option Atom = 0x6e306 - Output Atom = 0x51d06 + Optimum Atom = 0x6cf07 + Option Atom = 0x6e106 + Output Atom = 0x51106 P Atom = 0xc01 Param Atom = 0xc05 Pattern Atom = 0x6607 @@ -288,466 +288,468 @@ const ( Placeholder Atom = 0x1310b Plaintext Atom = 0x1b209 Playsinline Atom = 0x1400b - Poster Atom = 0x2cf06 - Pre Atom = 0x47003 - Preload Atom = 0x48607 - Progress Atom = 0x5b908 - Prompt Atom = 0x53606 - Public Atom = 0x58606 + Poster Atom = 0x64706 + Pre Atom = 0x46a03 + Preload Atom = 0x47a07 + Progress Atom = 0x5a908 + Prompt Atom = 0x52a06 + Public Atom = 0x57606 Q Atom = 0xcf01 Radiogroup Atom = 0x30a Rb Atom = 0x3a02 - Readonly Atom = 0x35708 - Referrerpolicy Atom = 0x3d10e - Rel Atom = 0x48703 - Required Atom = 0x24c08 + Readonly Atom = 0x35108 + Referrerpolicy Atom = 0x3cb0e + Rel Atom = 0x47b03 + Required Atom = 0x23f08 Reversed Atom = 0x8008 Rows Atom = 0x9c04 Rowspan Atom = 0x9c07 - Rp Atom = 0x23c02 + Rp Atom = 0x22f02 Rt Atom = 0x19a02 Rtc Atom = 0x19a03 Ruby Atom = 0xfb04 S Atom = 0x2501 Samp Atom = 0x7804 Sandbox Atom = 0x12907 - Scope Atom = 0x67505 - Scoped Atom = 0x67506 - Script Atom = 0x21806 - Seamless Atom = 0x37108 - Section Atom = 0x56807 - Select Atom = 0x63c06 - Selected Atom = 0x63c08 - Shape Atom = 0x1e505 - Size Atom = 0x5f504 - Sizes Atom = 0x5f505 - Slot Atom = 0x1ef04 - Small Atom = 0x20605 - Sortable Atom = 0x65108 - Sorted Atom = 0x33706 - Source Atom = 0x37806 - Spacer Atom = 0x43706 + Scope Atom = 0x67305 + Scoped Atom = 0x67306 + Script Atom = 0x2c406 + Seamless Atom = 0x36b08 + Search Atom = 0x55c06 + Section Atom = 0x1e507 + Select Atom = 0x63106 + Selected Atom = 0x63108 + Shape Atom = 0x1f505 + Size Atom = 0x5e504 + Sizes Atom = 0x5e505 + Slot Atom = 0x20504 + Small Atom = 0x32605 + Sortable Atom = 0x64f08 + Sorted Atom = 0x37206 + Source Atom = 0x43106 + Spacer Atom = 0x46e06 Span Atom = 0x9f04 - Spellcheck Atom = 0x4740a - Src Atom = 0x5c003 - Srcdoc Atom = 0x5c006 - Srclang Atom = 0x5f907 - Srcset Atom = 0x6f906 - Start Atom = 0x3fa05 - Step Atom = 0x58304 + Spellcheck Atom = 0x5b00a + Src Atom = 0x5e903 + Srcdoc Atom = 0x5e906 + Srclang Atom = 0x6f707 + Srcset Atom = 0x6fe06 + Start Atom = 0x3f405 + Step Atom = 0x57304 Strike Atom = 0xd206 - Strong Atom = 0x6dd06 - Style Atom = 0x6ff05 - Sub Atom = 0x66d03 - Summary Atom = 0x70407 - Sup Atom = 0x70b03 - Svg Atom = 0x70e03 - System Atom = 0x71106 - Tabindex Atom = 0x4be08 - Table Atom = 0x59505 - Target Atom = 0x2c406 + Strong Atom = 0x6db06 + Style Atom = 0x70405 + Sub Atom = 0x66b03 + Summary Atom = 0x70907 + Sup Atom = 0x71003 + Svg Atom = 0x71303 + System Atom = 0x71606 + Tabindex Atom = 0x4b208 + Table Atom = 0x58505 + Target Atom = 0x2b706 Tbody Atom = 0x2705 Td Atom = 0x9202 - Template Atom = 0x71408 - Textarea Atom = 0x35208 + Template Atom = 0x71908 + Textarea Atom = 0x34c08 Tfoot Atom = 0xf505 Th Atom = 0x15602 - Thead Atom = 0x33005 + Thead Atom = 0x31f05 Time Atom = 0x4204 Title Atom = 0x11005 Tr Atom = 0xcc02 Track Atom = 0x1ba05 - Translate Atom = 0x1f209 + Translate Atom = 0x20809 Tt Atom = 0x6802 Type Atom = 0xd904 - Typemustmatch Atom = 0x2900d + Typemustmatch Atom = 0x2830d U Atom = 0xb01 Ul Atom = 0xa702 Updateviacache Atom = 0x460e - Usemap Atom = 0x59e06 + Usemap Atom = 0x58e06 Value Atom = 0x1505 Var Atom = 0x16d03 - Video Atom = 0x2f105 - Wbr Atom = 0x57c03 - Width Atom = 0x64905 - Workertype Atom = 0x71c0a - Wrap Atom = 0x72604 + Video Atom = 0x2e005 + Wbr Atom = 0x56c03 + Width Atom = 0x63e05 + Workertype Atom = 0x7210a + Wrap Atom = 0x72b04 Xmp Atom = 0x12f03 ) -const hash0 = 0x81cdf10e +const hash0 = 0x84f70e16 const maxAtomLen = 25 var table = [1 << 9]Atom{ - 0x1: 0xe60a, // mediagroup - 0x2: 0x2e404, // lang - 0x4: 0x2c09, // accesskey - 0x5: 0x8b08, // frameset - 0x7: 0x63a08, // onselect - 0x8: 0x71106, // system - 0xa: 0x64905, // width - 0xc: 0x2890b, // formenctype - 0xd: 0x13702, // ol - 0xe: 0x3970b, // oncuechange - 0x10: 0x14b03, // bdo - 0x11: 0x11505, // audio - 0x12: 0x17a09, // draggable - 0x14: 0x2f105, // video - 0x15: 0x2b102, // mn - 0x16: 0x38704, // menu - 0x17: 0x2cf06, // poster - 0x19: 0xf606, // footer - 0x1a: 0x2a806, // method - 0x1b: 0x2b808, // datetime - 0x1c: 0x19507, // onabort - 0x1d: 0x460e, // updateviacache - 0x1e: 0xff05, // async - 0x1f: 0x49d06, // onload - 0x21: 0x11908, // oncancel - 0x22: 0x62908, // onseeked - 0x23: 0x30205, // image - 0x24: 0x5d812, // onrejectionhandled - 0x26: 0x17404, // link - 0x27: 0x51d06, // output - 0x28: 0x33104, // head - 0x29: 0x4ff0c, // onmouseleave - 0x2a: 0x57f07, // onpaste - 0x2b: 0x5a409, // onplaying - 0x2c: 0x1c407, // colspan - 0x2f: 0x1bf05, // color - 0x30: 0x5f504, // size - 0x31: 0x2e80a, // http-equiv - 0x33: 0x601, // i - 0x34: 0x5590a, // onpagehide - 0x35: 0x68c14, // onunhandledrejection - 0x37: 0x42a07, // onerror - 0x3a: 0x3b08, // basefont - 0x3f: 0x1303, // nav - 0x40: 0x17704, // kind - 0x41: 0x35708, // readonly - 0x42: 0x30806, // mglyph - 0x44: 0xb202, // li - 0x46: 0x2d506, // hidden - 0x47: 0x70e03, // svg - 0x48: 0x58304, // step - 0x49: 0x23f09, // integrity - 0x4a: 0x58606, // public - 0x4c: 0x1ab03, // col - 0x4d: 0x1870a, // blockquote - 0x4e: 0x34f02, // h5 - 0x50: 0x5b908, // progress - 0x51: 0x5f505, // sizes - 0x52: 0x34502, // h4 - 0x56: 0x33005, // thead - 0x57: 0xd607, // keytype - 0x58: 0x5b70a, // onprogress - 0x59: 0x44b09, // inputmode - 0x5a: 0x3b109, // ondragend - 0x5d: 0x3a205, // oncut - 0x5e: 0x43706, // spacer - 0x5f: 0x1ab08, // colgroup - 0x62: 0x16502, // is - 0x65: 0x3c02, // as - 0x66: 0x54809, // onoffline - 0x67: 0x33706, // sorted - 0x69: 0x48d10, // onlanguagechange - 0x6c: 0x43d0c, // onhashchange - 0x6d: 0x9604, // name - 0x6e: 0xf505, // tfoot - 0x6f: 0x56104, // desc - 0x70: 0x33d03, // max - 0x72: 0x1ea06, // coords - 0x73: 0x30d02, // h3 - 0x74: 0x6e70e, // onbeforeunload - 0x75: 0x9c04, // rows - 0x76: 0x63c06, // select - 0x77: 0x9805, // meter - 0x78: 0x38b06, // itemid - 0x79: 0x53c0c, // onmousewheel - 0x7a: 0x5c006, // srcdoc - 0x7d: 0x1ba05, // track - 0x7f: 0x31f08, // itemtype - 0x82: 0xa402, // mo - 0x83: 0x41b08, // onchange - 0x84: 0x33107, // headers - 0x85: 0x5cc0c, // onratechange - 0x86: 0x60819, // onsecuritypolicyviolation - 0x88: 0x4a508, // datalist - 0x89: 0x4e80b, // onmousedown - 0x8a: 0x1ef04, // slot - 0x8b: 0x4b010, // onloadedmetadata - 0x8c: 0x1a06, // accept - 0x8d: 0x26806, // object - 0x91: 0x6b30e, // onvolumechange - 0x92: 0x2107, // charset - 0x93: 0x27613, // onautocompleteerror - 0x94: 0xc113, // allowpaymentrequest - 0x95: 0x2804, // body - 0x96: 0x10a07, // default - 0x97: 0x63c08, // selected - 0x98: 0x21e04, // face - 0x99: 0x1e505, // shape - 0x9b: 0x68408, // ontoggle - 0x9e: 0x64b02, // dt - 0x9f: 0xb604, // mark - 0xa1: 0xb01, // u - 0xa4: 0x6ab08, // onunload - 0xa5: 0x5d04, // loop - 0xa6: 0x16408, // disabled - 0xaa: 0x42307, // onended - 0xab: 0xb00a, // malignmark - 0xad: 0x67b09, // onsuspend - 0xae: 0x35105, // mtext - 0xaf: 0x64f06, // onsort - 0xb0: 0x19d08, // itemprop - 0xb3: 0x67109, // itemscope - 0xb4: 0x17305, // blink - 0xb6: 0x3b106, // ondrag - 0xb7: 0xa702, // ul - 0xb8: 0x26e04, // form - 0xb9: 0x12907, // sandbox - 0xba: 0x8b05, // frame - 0xbb: 0x1505, // value - 0xbc: 0x66209, // onstorage - 0xbf: 0xaa07, // acronym - 0xc0: 0x19a02, // rt - 0xc2: 0x202, // br - 0xc3: 0x22608, // fieldset - 0xc4: 0x2900d, // typemustmatch - 0xc5: 0xa208, // nomodule - 0xc6: 0x6c07, // noembed - 0xc7: 0x69e0d, // onbeforeprint - 0xc8: 0x19106, // button - 0xc9: 0x2f507, // onclick - 0xca: 0x70407, // summary - 0xcd: 0xfb04, // ruby - 0xce: 0x56405, // class - 0xcf: 0x3f40b, // ondragstart - 0xd0: 0x23107, // caption - 0xd4: 0xdd0e, // allowusermedia - 0xd5: 0x4cf0b, // onloadstart - 0xd9: 0x16b03, // div - 0xda: 0x4a904, // list - 0xdb: 0x32e04, // math - 0xdc: 0x44b05, // input - 0xdf: 0x3ea0a, // ondragover - 0xe0: 0x2de02, // h2 - 0xe2: 0x1b209, // plaintext - 0xe4: 0x4f30c, // onmouseenter - 0xe7: 0x47907, // checked - 0xe8: 0x47003, // pre - 0xea: 0x35f08, // multiple - 0xeb: 0xba03, // bdi - 0xec: 0x33d09, // maxlength - 0xed: 0xcf01, // q - 0xee: 0x61f0a, // onauxclick - 0xf0: 0x57c03, // wbr - 0xf2: 0x3b04, // base - 0xf3: 0x6e306, // option - 0xf5: 0x41310, // ondurationchange - 0xf7: 0x8908, // noframes - 0xf9: 0x40508, // dropzone - 0xfb: 0x67505, // scope - 0xfc: 0x8008, // reversed - 0xfd: 0x3ba0b, // ondragenter - 0xfe: 0x3fa05, // start - 0xff: 0x12f03, // xmp - 0x100: 0x5f907, // srclang - 0x101: 0x30703, // img - 0x104: 0x101, // b - 0x105: 0x25403, // for - 0x106: 0x10705, // aside - 0x107: 0x44907, // oninput - 0x108: 0x35604, // area - 0x109: 0x2a40a, // formmethod - 0x10a: 0x72604, // wrap - 0x10c: 0x23c02, // rp - 0x10d: 0x46b0a, // onkeypress - 0x10e: 0x6802, // tt - 0x110: 0x34702, // mi - 0x111: 0x36705, // muted - 0x112: 0xf303, // alt - 0x113: 0x5c504, // code - 0x114: 0x6e02, // em - 0x115: 0x3c50a, // ondragexit - 0x117: 0x9f04, // span - 0x119: 0x6d708, // manifest - 0x11a: 0x38708, // menuitem - 0x11b: 0x58b07, // content - 0x11d: 0x6c109, // onwaiting - 0x11f: 0x4c609, // onloadend - 0x121: 0x37e0d, // oncontextmenu - 0x123: 0x56d06, // onblur - 0x124: 0x3fc07, // article - 0x125: 0x9303, // dir - 0x126: 0xef04, // ping - 0x127: 0x24c08, // required - 0x128: 0x45509, // oninvalid - 0x129: 0xb105, // align - 0x12b: 0x58a04, // icon - 0x12c: 0x64d02, // h6 - 0x12d: 0x1c404, // cols - 0x12e: 0x22e0a, // figcaption - 0x12f: 0x45e09, // onkeydown - 0x130: 0x66b08, // onsubmit - 0x131: 0x14d09, // oncanplay - 0x132: 0x70b03, // sup - 0x133: 0xc01, // p - 0x135: 0x40a09, // onemptied - 0x136: 0x39106, // oncopy - 0x137: 0x19c04, // cite - 0x138: 0x3a70a, // ondblclick - 0x13a: 0x50b0b, // onmousemove - 0x13c: 0x66d03, // sub - 0x13d: 0x48703, // rel - 0x13e: 0x5f08, // optgroup - 0x142: 0x9c07, // rowspan - 0x143: 0x37806, // source - 0x144: 0x21608, // noscript - 0x145: 0x1a304, // open - 0x146: 0x20403, // ins - 0x147: 0x2540d, // foreignObject - 0x148: 0x5ad0a, // onpopstate - 0x14a: 0x28d07, // enctype - 0x14b: 0x2760e, // onautocomplete - 0x14c: 0x35208, // textarea - 0x14e: 0x2780c, // autocomplete - 0x14f: 0x15702, // hr - 0x150: 0x1de08, // controls - 0x151: 0x10902, // id - 0x153: 0x2360c, // onafterprint - 0x155: 0x2610d, // foreignobject - 0x156: 0x32707, // marquee - 0x157: 0x59a07, // onpause - 0x158: 0x5e602, // dl - 0x159: 0x5206, // height - 0x15a: 0x34703, // min - 0x15b: 0x9307, // dirname - 0x15c: 0x1f209, // translate - 0x15d: 0x5604, // html - 0x15e: 0x34709, // minlength - 0x15f: 0x48607, // preload - 0x160: 0x71408, // template - 0x161: 0x3df0b, // ondragleave - 0x162: 0x3a02, // rb - 0x164: 0x5c003, // src - 0x165: 0x6dd06, // strong - 0x167: 0x7804, // samp - 0x168: 0x6f307, // address - 0x169: 0x55108, // ononline - 0x16b: 0x1310b, // placeholder - 0x16c: 0x2c406, // target - 0x16d: 0x20605, // small - 0x16e: 0x6ca07, // onwheel - 0x16f: 0x1c90a, // annotation - 0x170: 0x4740a, // spellcheck - 0x171: 0x7207, // details - 0x172: 0x10306, // canvas - 0x173: 0x12109, // autofocus - 0x174: 0xc05, // param - 0x176: 0x46308, // download - 0x177: 0x45203, // del - 0x178: 0x36c07, // onclose - 0x179: 0xb903, // kbd - 0x17a: 0x31906, // applet - 0x17b: 0x2e004, // href - 0x17c: 0x5f108, // onresize - 0x17e: 0x49d0c, // onloadeddata - 0x180: 0xcc02, // tr - 0x181: 0x2c00a, // formtarget - 0x182: 0x11005, // title - 0x183: 0x6ff05, // style - 0x184: 0xd206, // strike - 0x185: 0x59e06, // usemap - 0x186: 0x2fc06, // iframe - 0x187: 0x1004, // main - 0x189: 0x7b07, // picture - 0x18c: 0x31605, // ismap - 0x18e: 0x4a504, // data - 0x18f: 0x5905, // label - 0x191: 0x3d10e, // referrerpolicy - 0x192: 0x15602, // th - 0x194: 0x53606, // prompt - 0x195: 0x56807, // section - 0x197: 0x6d107, // optimum - 0x198: 0x2db04, // high - 0x199: 0x15c02, // h1 - 0x19a: 0x65909, // onstalled - 0x19b: 0x16d03, // var - 0x19c: 0x4204, // time - 0x19e: 0x67402, // ms - 0x19f: 0x33106, // header - 0x1a0: 0x4da09, // onmessage - 0x1a1: 0x1a605, // nonce - 0x1a2: 0x26e0a, // formaction - 0x1a3: 0x22006, // center - 0x1a4: 0x3704, // nobr - 0x1a5: 0x59505, // table - 0x1a6: 0x4a907, // listing - 0x1a7: 0x18106, // legend - 0x1a9: 0x29b09, // challenge - 0x1aa: 0x24806, // figure - 0x1ab: 0xe605, // media - 0x1ae: 0xd904, // type - 0x1af: 0x3f04, // font - 0x1b0: 0x4da0e, // onmessageerror - 0x1b1: 0x37108, // seamless - 0x1b2: 0x8703, // dfn - 0x1b3: 0x5c705, // defer - 0x1b4: 0xc303, // low - 0x1b5: 0x19a03, // rtc - 0x1b6: 0x5230b, // onmouseover - 0x1b7: 0x2b20a, // novalidate - 0x1b8: 0x71c0a, // workertype - 0x1ba: 0x3cd07, // itemref - 0x1bd: 0x1, // a - 0x1be: 0x31803, // map - 0x1bf: 0x400c, // ontimeupdate - 0x1c0: 0x15e07, // bgsound - 0x1c1: 0x3206, // keygen - 0x1c2: 0x2705, // tbody - 0x1c5: 0x64406, // onshow - 0x1c7: 0x2501, // s - 0x1c8: 0x6607, // pattern - 0x1cc: 0x14d10, // oncanplaythrough - 0x1ce: 0x2d702, // dd - 0x1cf: 0x6f906, // srcset - 0x1d0: 0x17003, // big - 0x1d2: 0x65108, // sortable - 0x1d3: 0x48007, // onkeyup - 0x1d5: 0x5a406, // onplay - 0x1d7: 0x4b804, // meta - 0x1d8: 0x40306, // ondrop - 0x1da: 0x60008, // onscroll - 0x1db: 0x1fb0b, // crossorigin - 0x1dc: 0x5730a, // onpageshow - 0x1dd: 0x4, // abbr - 0x1de: 0x9202, // td - 0x1df: 0x58b0f, // contenteditable - 0x1e0: 0x27206, // action - 0x1e1: 0x1400b, // playsinline - 0x1e2: 0x43107, // onfocus - 0x1e3: 0x2e008, // hreflang - 0x1e5: 0x5160a, // onmouseout - 0x1e6: 0x5ea07, // onreset - 0x1e7: 0x13c08, // autoplay - 0x1e8: 0x63109, // onseeking - 0x1ea: 0x67506, // scoped - 0x1ec: 0x30a, // radiogroup - 0x1ee: 0x3800b, // contextmenu - 0x1ef: 0x52e09, // onmouseup - 0x1f1: 0x2ca06, // hgroup - 0x1f2: 0x2080f, // allowfullscreen - 0x1f3: 0x4be08, // tabindex - 0x1f6: 0x30f07, // isindex - 0x1f7: 0x1a0e, // accept-charset - 0x1f8: 0x2ae0e, // formnovalidate - 0x1fb: 0x1c90e, // annotation-xml - 0x1fc: 0x6e05, // embed - 0x1fd: 0x21806, // script - 0x1fe: 0xbb06, // dialog - 0x1ff: 0x1d707, // command + 0x1: 0x3ff08, // dropzone + 0x2: 0x3b08, // basefont + 0x3: 0x23209, // integrity + 0x4: 0x43106, // source + 0x5: 0x2c09, // accesskey + 0x6: 0x1a06, // accept + 0x7: 0x6c807, // onwheel + 0xb: 0x47407, // onkeyup + 0xc: 0x32007, // headers + 0xd: 0x67306, // scoped + 0xe: 0x67909, // onsuspend + 0xf: 0x8908, // noframes + 0x10: 0x1fa0b, // crossorigin + 0x11: 0x2e407, // onclick + 0x12: 0x3f405, // start + 0x13: 0x37a0b, // contextmenu + 0x14: 0x5e903, // src + 0x15: 0x1c404, // cols + 0x16: 0xbb06, // dialog + 0x17: 0x47a07, // preload + 0x18: 0x3c707, // itemref + 0x1b: 0x2f105, // image + 0x1d: 0x4ba09, // onloadend + 0x1e: 0x45d08, // download + 0x1f: 0x46a03, // pre + 0x23: 0x2970a, // formmethod + 0x24: 0x71303, // svg + 0x25: 0xcf01, // q + 0x26: 0x64002, // dt + 0x27: 0x1de08, // controls + 0x2a: 0x2804, // body + 0x2b: 0xd206, // strike + 0x2c: 0x3910b, // oncuechange + 0x2d: 0x4c30b, // onloadstart + 0x2e: 0x2fe07, // isindex + 0x2f: 0xb202, // li + 0x30: 0x1400b, // playsinline + 0x31: 0x34102, // mi + 0x32: 0x30806, // applet + 0x33: 0x4ce09, // onmessage + 0x35: 0x13702, // ol + 0x36: 0x1a304, // open + 0x39: 0x14d09, // oncanplay + 0x3a: 0x6bf09, // onwaiting + 0x3b: 0x11908, // oncancel + 0x3c: 0x6a908, // onunload + 0x3e: 0x53c09, // onoffline + 0x3f: 0x1a0e, // accept-charset + 0x40: 0x32004, // head + 0x42: 0x3ab09, // ondragend + 0x43: 0x1310b, // placeholder + 0x44: 0x2b30a, // formtarget + 0x45: 0x2540d, // foreignobject + 0x47: 0x400c, // ontimeupdate + 0x48: 0xdd0e, // allowusermedia + 0x4a: 0x69c0d, // onbeforeprint + 0x4b: 0x5604, // html + 0x4c: 0x9f04, // span + 0x4d: 0x64206, // hgroup + 0x4e: 0x16408, // disabled + 0x4f: 0x4204, // time + 0x51: 0x42b07, // onfocus + 0x53: 0xb00a, // malignmark + 0x55: 0x4650a, // onkeypress + 0x56: 0x55805, // class + 0x57: 0x1ab08, // colgroup + 0x58: 0x33709, // maxlength + 0x59: 0x5a908, // progress + 0x5b: 0x70405, // style + 0x5c: 0x2a10e, // formnovalidate + 0x5e: 0x38b06, // oncopy + 0x60: 0x26104, // form + 0x61: 0xf606, // footer + 0x64: 0x30a, // radiogroup + 0x66: 0xfb04, // ruby + 0x67: 0x4ff0b, // onmousemove + 0x68: 0x19d08, // itemprop + 0x69: 0x2d70a, // http-equiv + 0x6a: 0x15602, // th + 0x6c: 0x6e02, // em + 0x6d: 0x38108, // menuitem + 0x6e: 0x63106, // select + 0x6f: 0x48110, // onlanguagechange + 0x70: 0x31f05, // thead + 0x71: 0x15c02, // h1 + 0x72: 0x5e906, // srcdoc + 0x75: 0x9604, // name + 0x76: 0x19106, // button + 0x77: 0x55504, // desc + 0x78: 0x17704, // kind + 0x79: 0x1bf05, // color + 0x7c: 0x58e06, // usemap + 0x7d: 0x30e08, // itemtype + 0x7f: 0x6d508, // manifest + 0x81: 0x5300c, // onmousewheel + 0x82: 0x4dc0b, // onmousedown + 0x84: 0xc05, // param + 0x85: 0x2e005, // video + 0x86: 0x4910c, // onloadeddata + 0x87: 0x6f107, // address + 0x8c: 0xef04, // ping + 0x8d: 0x24703, // for + 0x8f: 0x62f08, // onselect + 0x90: 0x30703, // map + 0x92: 0xc01, // p + 0x93: 0x8008, // reversed + 0x94: 0x54d0a, // onpagehide + 0x95: 0x3206, // keygen + 0x96: 0x34109, // minlength + 0x97: 0x3e40a, // ondragover + 0x98: 0x42407, // onerror + 0x9a: 0x2107, // charset + 0x9b: 0x29b06, // method + 0x9c: 0x101, // b + 0x9d: 0x68208, // ontoggle + 0x9e: 0x2bd06, // hidden + 0xa0: 0x3f607, // article + 0xa2: 0x63906, // onshow + 0xa3: 0x64d06, // onsort + 0xa5: 0x57b0f, // contenteditable + 0xa6: 0x66908, // onsubmit + 0xa8: 0x44f09, // oninvalid + 0xaa: 0x202, // br + 0xab: 0x10902, // id + 0xac: 0x5d04, // loop + 0xad: 0x5630a, // onpageshow + 0xb0: 0x2cf04, // href + 0xb2: 0x2210a, // figcaption + 0xb3: 0x2690e, // onautocomplete + 0xb4: 0x49106, // onload + 0xb6: 0x9c04, // rows + 0xb7: 0x1a605, // nonce + 0xb8: 0x68a14, // onunhandledrejection + 0xbb: 0x21306, // center + 0xbc: 0x59406, // onplay + 0xbd: 0x33f02, // h5 + 0xbe: 0x49d07, // listing + 0xbf: 0x57606, // public + 0xc2: 0x23b06, // figure + 0xc3: 0x57a04, // icon + 0xc4: 0x1ab03, // col + 0xc5: 0x47b03, // rel + 0xc6: 0xe605, // media + 0xc7: 0x12109, // autofocus + 0xc8: 0x19a02, // rt + 0xca: 0x2d304, // lang + 0xcc: 0x49908, // datalist + 0xce: 0x2eb06, // iframe + 0xcf: 0x36105, // muted + 0xd0: 0x6140a, // onauxclick + 0xd2: 0x3c02, // as + 0xd6: 0x3fd06, // ondrop + 0xd7: 0x1c90a, // annotation + 0xd8: 0x21908, // fieldset + 0xdb: 0x2cf08, // hreflang + 0xdc: 0x4e70c, // onmouseenter + 0xdd: 0x2a402, // mn + 0xde: 0xe60a, // mediagroup + 0xdf: 0x9805, // meter + 0xe0: 0x56c03, // wbr + 0xe2: 0x63e05, // width + 0xe3: 0x2290c, // onafterprint + 0xe4: 0x30505, // ismap + 0xe5: 0x1505, // value + 0xe7: 0x1303, // nav + 0xe8: 0x54508, // ononline + 0xe9: 0xb604, // mark + 0xea: 0xc303, // low + 0xeb: 0x3ee0b, // ondragstart + 0xef: 0x12f03, // xmp + 0xf0: 0x22407, // caption + 0xf1: 0xd904, // type + 0xf2: 0x70907, // summary + 0xf3: 0x6802, // tt + 0xf4: 0x20809, // translate + 0xf5: 0x1870a, // blockquote + 0xf8: 0x15702, // hr + 0xfa: 0x2705, // tbody + 0xfc: 0x7b07, // picture + 0xfd: 0x5206, // height + 0xfe: 0x19c04, // cite + 0xff: 0x2501, // s + 0x101: 0xff05, // async + 0x102: 0x56f07, // onpaste + 0x103: 0x19507, // onabort + 0x104: 0x2b706, // target + 0x105: 0x14b03, // bdo + 0x106: 0x1f006, // coords + 0x107: 0x5e108, // onresize + 0x108: 0x71908, // template + 0x10a: 0x3a02, // rb + 0x10b: 0x2a50a, // novalidate + 0x10c: 0x460e, // updateviacache + 0x10d: 0x71003, // sup + 0x10e: 0x6c07, // noembed + 0x10f: 0x16b03, // div + 0x110: 0x6f707, // srclang + 0x111: 0x17a09, // draggable + 0x112: 0x67305, // scope + 0x113: 0x5905, // label + 0x114: 0x22f02, // rp + 0x115: 0x23f08, // required + 0x116: 0x3780d, // oncontextmenu + 0x117: 0x5e504, // size + 0x118: 0x5b00a, // spellcheck + 0x119: 0x3f04, // font + 0x11a: 0x9c07, // rowspan + 0x11b: 0x10a07, // default + 0x11d: 0x44307, // oninput + 0x11e: 0x38506, // itemid + 0x11f: 0x5ee04, // code + 0x120: 0xaa07, // acronym + 0x121: 0x3b04, // base + 0x125: 0x2470d, // foreignObject + 0x126: 0x2ca04, // high + 0x127: 0x3cb0e, // referrerpolicy + 0x128: 0x33703, // max + 0x129: 0x59d0a, // onpopstate + 0x12a: 0x2fc02, // h4 + 0x12b: 0x4ac04, // meta + 0x12c: 0x17305, // blink + 0x12e: 0x5f508, // onscroll + 0x12f: 0x59409, // onplaying + 0x130: 0xc113, // allowpaymentrequest + 0x131: 0x19a03, // rtc + 0x132: 0x72b04, // wrap + 0x134: 0x8b08, // frameset + 0x135: 0x32605, // small + 0x137: 0x32006, // header + 0x138: 0x40409, // onemptied + 0x139: 0x34902, // h6 + 0x13a: 0x35908, // multiple + 0x13c: 0x52a06, // prompt + 0x13f: 0x28e09, // challenge + 0x141: 0x4370c, // onhashchange + 0x142: 0x57b07, // content + 0x143: 0x1c90e, // annotation-xml + 0x144: 0x36607, // onclose + 0x145: 0x14d10, // oncanplaythrough + 0x148: 0x5170b, // onmouseover + 0x149: 0x64f08, // sortable + 0x14a: 0xa402, // mo + 0x14b: 0x2cd02, // h3 + 0x14c: 0x2c406, // script + 0x14d: 0x41d07, // onended + 0x14f: 0x64706, // poster + 0x150: 0x7210a, // workertype + 0x153: 0x1f505, // shape + 0x154: 0x4, // abbr + 0x155: 0x1, // a + 0x156: 0x2bf02, // dd + 0x157: 0x71606, // system + 0x158: 0x4ce0e, // onmessageerror + 0x159: 0x36b08, // seamless + 0x15a: 0x2610a, // formaction + 0x15b: 0x6e106, // option + 0x15c: 0x31d04, // math + 0x15d: 0x62609, // onseeking + 0x15e: 0x39c05, // oncut + 0x15f: 0x44c03, // del + 0x160: 0x11005, // title + 0x161: 0x11505, // audio + 0x162: 0x63108, // selected + 0x165: 0x3b40b, // ondragenter + 0x166: 0x46e06, // spacer + 0x167: 0x4a410, // onloadedmetadata + 0x168: 0x44505, // input + 0x16a: 0x58505, // table + 0x16b: 0x41508, // onchange + 0x16e: 0x5f005, // defer + 0x171: 0x50a0a, // onmouseout + 0x172: 0x20504, // slot + 0x175: 0x3704, // nobr + 0x177: 0x1d707, // command + 0x17a: 0x7207, // details + 0x17b: 0x38104, // menu + 0x17c: 0xb903, // kbd + 0x17d: 0x57304, // step + 0x17e: 0x20303, // ins + 0x17f: 0x13c08, // autoplay + 0x182: 0x34103, // min + 0x183: 0x17404, // link + 0x185: 0x40d10, // ondurationchange + 0x186: 0x9202, // td + 0x187: 0x8b05, // frame + 0x18a: 0x2ab08, // datetime + 0x18b: 0x44509, // inputmode + 0x18c: 0x35108, // readonly + 0x18d: 0x21104, // face + 0x18f: 0x5e505, // sizes + 0x191: 0x4b208, // tabindex + 0x192: 0x6db06, // strong + 0x193: 0xba03, // bdi + 0x194: 0x6fe06, // srcset + 0x196: 0x67202, // ms + 0x197: 0x5b507, // checked + 0x198: 0xb105, // align + 0x199: 0x1e507, // section + 0x19b: 0x6e05, // embed + 0x19d: 0x15e07, // bgsound + 0x1a2: 0x49d04, // list + 0x1a3: 0x61e08, // onseeked + 0x1a4: 0x66009, // onstorage + 0x1a5: 0x2f603, // img + 0x1a6: 0xf505, // tfoot + 0x1a9: 0x26913, // onautocompleteerror + 0x1aa: 0x5fd19, // onsecuritypolicyviolation + 0x1ad: 0x9303, // dir + 0x1ae: 0x9307, // dirname + 0x1b0: 0x5a70a, // onprogress + 0x1b2: 0x65709, // onstalled + 0x1b5: 0x66f09, // itemscope + 0x1b6: 0x49904, // data + 0x1b7: 0x3d90b, // ondragleave + 0x1b8: 0x56102, // h2 + 0x1b9: 0x2f706, // mglyph + 0x1ba: 0x16502, // is + 0x1bb: 0x6e50e, // onbeforeunload + 0x1bc: 0x2830d, // typemustmatch + 0x1bd: 0x3ab06, // ondrag + 0x1be: 0x5da07, // onreset + 0x1c0: 0x51106, // output + 0x1c1: 0x12907, // sandbox + 0x1c2: 0x1b209, // plaintext + 0x1c4: 0x34c08, // textarea + 0x1c7: 0xd607, // keytype + 0x1c8: 0x34b05, // mtext + 0x1c9: 0x6b10e, // onvolumechange + 0x1ca: 0x1ea06, // onblur + 0x1cb: 0x58a07, // onpause + 0x1cd: 0x5bc0c, // onratechange + 0x1ce: 0x10705, // aside + 0x1cf: 0x6cf07, // optimum + 0x1d1: 0x45809, // onkeydown + 0x1d2: 0x1c407, // colspan + 0x1d3: 0x1004, // main + 0x1d4: 0x66b03, // sub + 0x1d5: 0x25b06, // object + 0x1d6: 0x55c06, // search + 0x1d7: 0x37206, // sorted + 0x1d8: 0x17003, // big + 0x1d9: 0xb01, // u + 0x1db: 0x26b0c, // autocomplete + 0x1dc: 0xcc02, // tr + 0x1dd: 0xf303, // alt + 0x1df: 0x7804, // samp + 0x1e0: 0x5c812, // onrejectionhandled + 0x1e1: 0x4f30c, // onmouseleave + 0x1e2: 0x28007, // enctype + 0x1e3: 0xa208, // nomodule + 0x1e5: 0x3280f, // allowfullscreen + 0x1e6: 0x5f08, // optgroup + 0x1e8: 0x27c0b, // formenctype + 0x1e9: 0x18106, // legend + 0x1ea: 0x10306, // canvas + 0x1eb: 0x6607, // pattern + 0x1ec: 0x2c208, // noscript + 0x1ed: 0x601, // i + 0x1ee: 0x5d602, // dl + 0x1ef: 0xa702, // ul + 0x1f2: 0x52209, // onmouseup + 0x1f4: 0x1ba05, // track + 0x1f7: 0x3a10a, // ondblclick + 0x1f8: 0x3bf0a, // ondragexit + 0x1fa: 0x8703, // dfn + 0x1fc: 0x26506, // action + 0x1fd: 0x35004, // area + 0x1fe: 0x31607, // marquee + 0x1ff: 0x16d03, // var } const atomText = "abbradiogrouparamainavalueaccept-charsetbodyaccesskeygenobrb" + @@ -758,26 +760,26 @@ const atomText = "abbradiogrouparamainavalueaccept-charsetbodyaccesskeygenobrb" "dboxmplaceholderautoplaysinlinebdoncanplaythrough1bgsoundisa" + "bledivarbigblinkindraggablegendblockquotebuttonabortcitempro" + "penoncecolgrouplaintextrackcolorcolspannotation-xmlcommandco" + - "ntrolshapecoordslotranslatecrossoriginsmallowfullscreenoscri" + - "ptfacenterfieldsetfigcaptionafterprintegrityfigurequiredfore" + - "ignObjectforeignobjectformactionautocompleteerrorformenctype" + - "mustmatchallengeformmethodformnovalidatetimeformtargethgroup" + - "osterhiddenhigh2hreflanghttp-equivideonclickiframeimageimgly" + - "ph3isindexismappletitemtypemarqueematheadersortedmaxlength4m" + - "inlength5mtextareadonlymultiplemutedoncloseamlessourceoncont" + - "extmenuitemidoncopyoncuechangeoncutondblclickondragendondrag" + - "enterondragexitemreferrerpolicyondragleaveondragoverondragst" + - "articleondropzonemptiedondurationchangeonendedonerroronfocus" + - "paceronhashchangeoninputmodeloninvalidonkeydownloadonkeypres" + - "spellcheckedonkeyupreloadonlanguagechangeonloadeddatalisting" + - "onloadedmetadatabindexonloadendonloadstartonmessageerroronmo" + - "usedownonmouseenteronmouseleaveonmousemoveonmouseoutputonmou" + - "seoveronmouseupromptonmousewheelonofflineononlineonpagehides" + - "classectionbluronpageshowbronpastepublicontenteditableonpaus" + - "emaponplayingonpopstateonprogressrcdocodeferonratechangeonre" + - "jectionhandledonresetonresizesrclangonscrollonsecuritypolicy" + - "violationauxclickonseekedonseekingonselectedonshowidth6onsor" + - "tableonstalledonstorageonsubmitemscopedonsuspendontoggleonun" + - "handledrejectionbeforeprintonunloadonvolumechangeonwaitingon" + - "wheeloptimumanifestrongoptionbeforeunloaddressrcsetstylesumm" + - "arysupsvgsystemplateworkertypewrap" + "ntrolsectionblurcoordshapecrossoriginslotranslatefacenterfie" + + "ldsetfigcaptionafterprintegrityfigurequiredforeignObjectfore" + + "ignobjectformactionautocompleteerrorformenctypemustmatchalle" + + "ngeformmethodformnovalidatetimeformtargethiddenoscripthigh3h" + + "reflanghttp-equivideonclickiframeimageimglyph4isindexismappl" + + "etitemtypemarqueematheadersmallowfullscreenmaxlength5minleng" + + "th6mtextareadonlymultiplemutedoncloseamlessortedoncontextmen" + + "uitemidoncopyoncuechangeoncutondblclickondragendondragentero" + + "ndragexitemreferrerpolicyondragleaveondragoverondragstarticl" + + "eondropzonemptiedondurationchangeonendedonerroronfocusourceo" + + "nhashchangeoninputmodeloninvalidonkeydownloadonkeypresspacer" + + "onkeyupreloadonlanguagechangeonloadeddatalistingonloadedmeta" + + "databindexonloadendonloadstartonmessageerroronmousedownonmou" + + "seenteronmouseleaveonmousemoveonmouseoutputonmouseoveronmous" + + "eupromptonmousewheelonofflineononlineonpagehidesclassearch2o" + + "npageshowbronpastepublicontenteditableonpausemaponplayingonp" + + "opstateonprogresspellcheckedonratechangeonrejectionhandledon" + + "resetonresizesrcdocodeferonscrollonsecuritypolicyviolationau" + + "xclickonseekedonseekingonselectedonshowidthgrouposteronsorta" + + "bleonstalledonstorageonsubmitemscopedonsuspendontoggleonunha" + + "ndledrejectionbeforeprintonunloadonvolumechangeonwaitingonwh" + + "eeloptimumanifestrongoptionbeforeunloaddressrclangsrcsetstyl" + + "esummarysupsvgsystemplateworkertypewrap" diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/parse.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/parse.go index 643c674e378..518ee4c94e7 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/parse.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/parse.go @@ -924,7 +924,7 @@ func inBodyIM(p *parser) bool { p.addElement() p.im = inFramesetIM return true - case a.Address, a.Article, a.Aside, a.Blockquote, a.Center, a.Details, a.Dialog, a.Dir, a.Div, a.Dl, a.Fieldset, a.Figcaption, a.Figure, a.Footer, a.Header, a.Hgroup, a.Main, a.Menu, a.Nav, a.Ol, a.P, a.Section, a.Summary, a.Ul: + case a.Address, a.Article, a.Aside, a.Blockquote, a.Center, a.Details, a.Dialog, a.Dir, a.Div, a.Dl, a.Fieldset, a.Figcaption, a.Figure, a.Footer, a.Header, a.Hgroup, a.Main, a.Menu, a.Nav, a.Ol, a.P, a.Search, a.Section, a.Summary, a.Ul: p.popUntil(buttonScope, a.P) p.addElement() case a.H1, a.H2, a.H3, a.H4, a.H5, a.H6: @@ -1136,7 +1136,7 @@ func inBodyIM(p *parser) bool { return false } return true - case a.Address, a.Article, a.Aside, a.Blockquote, a.Button, a.Center, a.Details, a.Dialog, a.Dir, a.Div, a.Dl, a.Fieldset, a.Figcaption, a.Figure, a.Footer, a.Header, a.Hgroup, a.Listing, a.Main, a.Menu, a.Nav, a.Ol, a.Pre, a.Section, a.Summary, a.Ul: + case a.Address, a.Article, a.Aside, a.Blockquote, a.Button, a.Center, a.Details, a.Dialog, a.Dir, a.Div, a.Dl, a.Fieldset, a.Figcaption, a.Figure, a.Footer, a.Header, a.Hgroup, a.Listing, a.Main, a.Menu, a.Nav, a.Ol, a.Pre, a.Search, a.Section, a.Summary, a.Ul: p.popUntil(defaultScope, p.tok.DataAtom) case a.Form: if p.oe.contains(a.Template) { diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/token.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/token.go index 3c57880d697..6598c1f7b32 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/token.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/html/token.go @@ -839,8 +839,22 @@ func (z *Tokenizer) readStartTag() TokenType { if raw { z.rawTag = strings.ToLower(string(z.buf[z.data.start:z.data.end])) } - // Look for a self-closing token like "
". - if z.err == nil && z.buf[z.raw.end-2] == '/' { + // Look for a self-closing token (e.g.
). + // + // Originally, we did this by just checking that the last character of the + // tag (ignoring the closing bracket) was a solidus (/) character, but this + // is not always accurate. + // + // We need to be careful that we don't misinterpret a non-self-closing tag + // as self-closing, as can happen if the tag contains unquoted attribute + // values (i.e.

). + // + // To avoid this, we check that the last non-bracket character of the tag + // (z.raw.end-2) isn't the same character as the last non-quote character of + // the last attribute of the tag (z.pendingAttr[1].end-1), if the tag has + // attributes. + nAttrs := len(z.attr) + if z.err == nil && z.buf[z.raw.end-2] == '/' && (nAttrs == 0 || z.raw.end-2 != z.attr[nAttrs-1][1].end-1) { return SelfClosingTagToken } return StartTagToken diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/frame.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/frame.go index 81faec7e75d..97bd8b06f7a 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/frame.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/frame.go @@ -225,6 +225,11 @@ var fhBytes = sync.Pool{ }, } +func invalidHTTP1LookingFrameHeader() FrameHeader { + fh, _ := readFrameHeader(make([]byte, frameHeaderLen), strings.NewReader("HTTP/1.1 ")) + return fh +} + // ReadFrameHeader reads 9 bytes from r and returns a FrameHeader. // Most users should use Framer.ReadFrame instead. func ReadFrameHeader(r io.Reader) (FrameHeader, error) { @@ -503,10 +508,16 @@ func (fr *Framer) ReadFrame() (Frame, error) { return nil, err } if fh.Length > fr.maxReadSize { + if fh == invalidHTTP1LookingFrameHeader() { + return nil, fmt.Errorf("http2: failed reading the frame payload: %w, note that the frame header looked like an HTTP/1.1 header", err) + } return nil, ErrFrameTooLarge } payload := fr.getReadBuf(fh.Length) if _, err := io.ReadFull(fr.r, payload); err != nil { + if fh == invalidHTTP1LookingFrameHeader() { + return nil, fmt.Errorf("http2: failed reading the frame payload: %w, note that the frame header looked like an HTTP/1.1 header", err) + } return nil, err } f, err := typeFrameParser(fh.Type)(fr.frameCache, fh, fr.countError, payload) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/http2.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/http2.go index c7601c909ff..6c18ea230be 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/http2.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/http2.go @@ -34,11 +34,19 @@ import ( ) var ( - VerboseLogs bool - logFrameWrites bool - logFrameReads bool - inTests bool - disableExtendedConnectProtocol bool + VerboseLogs bool + logFrameWrites bool + logFrameReads bool + inTests bool + + // Enabling extended CONNECT by causes browsers to attempt to use + // WebSockets-over-HTTP/2. This results in problems when the server's websocket + // package doesn't support extended CONNECT. + // + // Disable extended CONNECT by default for now. + // + // Issue #71128. + disableExtendedConnectProtocol = true ) func init() { @@ -51,8 +59,8 @@ func init() { logFrameWrites = true logFrameReads = true } - if strings.Contains(e, "http2xconnect=0") { - disableExtendedConnectProtocol = true + if strings.Contains(e, "http2xconnect=1") { + disableExtendedConnectProtocol = false } } @@ -407,23 +415,6 @@ func (s *sorter) SortStrings(ss []string) { s.v = save } -// validPseudoPath reports whether v is a valid :path pseudo-header -// value. It must be either: -// -// - a non-empty string starting with '/' -// - the string '*', for OPTIONS requests. -// -// For now this is only used a quick check for deciding when to clean -// up Opaque URLs before sending requests from the Transport. -// See golang.org/issue/16847 -// -// We used to enforce that the path also didn't start with "//", but -// Google's GFE accepts such paths and Chrome sends them, so ignore -// that part of the spec. See golang.org/issue/19103. -func validPseudoPath(v string) bool { - return (len(v) > 0 && v[0] == '/') || v == "*" -} - // incomparable is a zero-width, non-comparable type. Adding it to a struct // makes that struct also non-comparable, and generally doesn't add // any size (as long as it's first). diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/server.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/server.go index b55547aec64..51fca38f61d 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/server.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/server.go @@ -50,6 +50,7 @@ import ( "golang.org/x/net/http/httpguts" "golang.org/x/net/http2/hpack" + "golang.org/x/net/internal/httpcommon" ) const ( @@ -812,8 +813,7 @@ const maxCachedCanonicalHeadersKeysSize = 2048 func (sc *serverConn) canonicalHeader(v string) string { sc.serveG.check() - buildCommonHeaderMapsOnce() - cv, ok := commonCanonHeader[v] + cv, ok := httpcommon.CachedCanonicalHeader(v) if ok { return cv } @@ -1068,7 +1068,10 @@ func (sc *serverConn) serve(conf http2Config) { func (sc *serverConn) handlePingTimer(lastFrameReadTime time.Time) { if sc.pingSent { - sc.vlogf("timeout waiting for PING response") + sc.logf("timeout waiting for PING response") + if f := sc.countErrorFunc; f != nil { + f("conn_close_lost_ping") + } sc.conn.Close() return } @@ -2233,25 +2236,25 @@ func (sc *serverConn) newStream(id, pusherID uint32, state streamState) *stream func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*responseWriter, *http.Request, error) { sc.serveG.check() - rp := requestParam{ - method: f.PseudoValue("method"), - scheme: f.PseudoValue("scheme"), - authority: f.PseudoValue("authority"), - path: f.PseudoValue("path"), - protocol: f.PseudoValue("protocol"), + rp := httpcommon.ServerRequestParam{ + Method: f.PseudoValue("method"), + Scheme: f.PseudoValue("scheme"), + Authority: f.PseudoValue("authority"), + Path: f.PseudoValue("path"), + Protocol: f.PseudoValue("protocol"), } // extended connect is disabled, so we should not see :protocol - if disableExtendedConnectProtocol && rp.protocol != "" { + if disableExtendedConnectProtocol && rp.Protocol != "" { return nil, nil, sc.countError("bad_connect", streamError(f.StreamID, ErrCodeProtocol)) } - isConnect := rp.method == "CONNECT" + isConnect := rp.Method == "CONNECT" if isConnect { - if rp.protocol == "" && (rp.path != "" || rp.scheme != "" || rp.authority == "") { + if rp.Protocol == "" && (rp.Path != "" || rp.Scheme != "" || rp.Authority == "") { return nil, nil, sc.countError("bad_connect", streamError(f.StreamID, ErrCodeProtocol)) } - } else if rp.method == "" || rp.path == "" || (rp.scheme != "https" && rp.scheme != "http") { + } else if rp.Method == "" || rp.Path == "" || (rp.Scheme != "https" && rp.Scheme != "http") { // See 8.1.2.6 Malformed Requests and Responses: // // Malformed requests or responses that are detected @@ -2265,15 +2268,16 @@ func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*res return nil, nil, sc.countError("bad_path_method", streamError(f.StreamID, ErrCodeProtocol)) } - rp.header = make(http.Header) + header := make(http.Header) + rp.Header = header for _, hf := range f.RegularFields() { - rp.header.Add(sc.canonicalHeader(hf.Name), hf.Value) + header.Add(sc.canonicalHeader(hf.Name), hf.Value) } - if rp.authority == "" { - rp.authority = rp.header.Get("Host") + if rp.Authority == "" { + rp.Authority = header.Get("Host") } - if rp.protocol != "" { - rp.header.Set(":protocol", rp.protocol) + if rp.Protocol != "" { + header.Set(":protocol", rp.Protocol) } rw, req, err := sc.newWriterAndRequestNoBody(st, rp) @@ -2282,7 +2286,7 @@ func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*res } bodyOpen := !f.StreamEnded() if bodyOpen { - if vv, ok := rp.header["Content-Length"]; ok { + if vv, ok := rp.Header["Content-Length"]; ok { if cl, err := strconv.ParseUint(vv[0], 10, 63); err == nil { req.ContentLength = int64(cl) } else { @@ -2298,84 +2302,38 @@ func (sc *serverConn) newWriterAndRequest(st *stream, f *MetaHeadersFrame) (*res return rw, req, nil } -type requestParam struct { - method string - scheme, authority, path string - protocol string - header http.Header -} - -func (sc *serverConn) newWriterAndRequestNoBody(st *stream, rp requestParam) (*responseWriter, *http.Request, error) { +func (sc *serverConn) newWriterAndRequestNoBody(st *stream, rp httpcommon.ServerRequestParam) (*responseWriter, *http.Request, error) { sc.serveG.check() var tlsState *tls.ConnectionState // nil if not scheme https - if rp.scheme == "https" { + if rp.Scheme == "https" { tlsState = sc.tlsState } - needsContinue := httpguts.HeaderValuesContainsToken(rp.header["Expect"], "100-continue") - if needsContinue { - rp.header.Del("Expect") - } - // Merge Cookie headers into one "; "-delimited value. - if cookies := rp.header["Cookie"]; len(cookies) > 1 { - rp.header.Set("Cookie", strings.Join(cookies, "; ")) - } - - // Setup Trailers - var trailer http.Header - for _, v := range rp.header["Trailer"] { - for _, key := range strings.Split(v, ",") { - key = http.CanonicalHeaderKey(textproto.TrimString(key)) - switch key { - case "Transfer-Encoding", "Trailer", "Content-Length": - // Bogus. (copy of http1 rules) - // Ignore. - default: - if trailer == nil { - trailer = make(http.Header) - } - trailer[key] = nil - } - } - } - delete(rp.header, "Trailer") - - var url_ *url.URL - var requestURI string - if rp.method == "CONNECT" && rp.protocol == "" { - url_ = &url.URL{Host: rp.authority} - requestURI = rp.authority // mimic HTTP/1 server behavior - } else { - var err error - url_, err = url.ParseRequestURI(rp.path) - if err != nil { - return nil, nil, sc.countError("bad_path", streamError(st.id, ErrCodeProtocol)) - } - requestURI = rp.path + res := httpcommon.NewServerRequest(rp) + if res.InvalidReason != "" { + return nil, nil, sc.countError(res.InvalidReason, streamError(st.id, ErrCodeProtocol)) } body := &requestBody{ conn: sc, stream: st, - needsContinue: needsContinue, + needsContinue: res.NeedsContinue, } - req := &http.Request{ - Method: rp.method, - URL: url_, + req := (&http.Request{ + Method: rp.Method, + URL: res.URL, RemoteAddr: sc.remoteAddrStr, - Header: rp.header, - RequestURI: requestURI, + Header: rp.Header, + RequestURI: res.RequestURI, Proto: "HTTP/2.0", ProtoMajor: 2, ProtoMinor: 0, TLS: tlsState, - Host: rp.authority, + Host: rp.Authority, Body: body, - Trailer: trailer, - } - req = req.WithContext(st.ctx) - + Trailer: res.Trailer, + }).WithContext(st.ctx) rw := sc.newResponseWriter(st, req) return rw, req, nil } @@ -3270,12 +3228,12 @@ func (sc *serverConn) startPush(msg *startPushRequest) { // we start in "half closed (remote)" for simplicity. // See further comments at the definition of stateHalfClosedRemote. promised := sc.newStream(promisedID, msg.parent.id, stateHalfClosedRemote) - rw, req, err := sc.newWriterAndRequestNoBody(promised, requestParam{ - method: msg.method, - scheme: msg.url.Scheme, - authority: msg.url.Host, - path: msg.url.RequestURI(), - header: cloneHeader(msg.header), // clone since handler runs concurrently with writing the PUSH_PROMISE + rw, req, err := sc.newWriterAndRequestNoBody(promised, httpcommon.ServerRequestParam{ + Method: msg.method, + Scheme: msg.url.Scheme, + Authority: msg.url.Host, + Path: msg.url.RequestURI(), + Header: cloneHeader(msg.header), // clone since handler runs concurrently with writing the PUSH_PROMISE }) if err != nil { // Should not happen, since we've already validated msg.url. diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/transport.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/transport.go index b2e2ed33739..f26356b9cd9 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/transport.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/transport.go @@ -25,7 +25,6 @@ import ( "net/http" "net/http/httptrace" "net/textproto" - "sort" "strconv" "strings" "sync" @@ -35,6 +34,7 @@ import ( "golang.org/x/net/http/httpguts" "golang.org/x/net/http2/hpack" "golang.org/x/net/idna" + "golang.org/x/net/internal/httpcommon" ) const ( @@ -1275,23 +1275,6 @@ func (cc *ClientConn) closeForLostPing() { // exported. At least they'll be DeepEqual for h1-vs-h2 comparisons tests. var errRequestCanceled = errors.New("net/http: request canceled") -func commaSeparatedTrailers(req *http.Request) (string, error) { - keys := make([]string, 0, len(req.Trailer)) - for k := range req.Trailer { - k = canonicalHeader(k) - switch k { - case "Transfer-Encoding", "Trailer", "Content-Length": - return "", fmt.Errorf("invalid Trailer key %q", k) - } - keys = append(keys, k) - } - if len(keys) > 0 { - sort.Strings(keys) - return strings.Join(keys, ","), nil - } - return "", nil -} - func (cc *ClientConn) responseHeaderTimeout() time.Duration { if cc.t.t1 != nil { return cc.t.t1.ResponseHeaderTimeout @@ -1303,22 +1286,6 @@ func (cc *ClientConn) responseHeaderTimeout() time.Duration { return 0 } -// checkConnHeaders checks whether req has any invalid connection-level headers. -// per RFC 7540 section 8.1.2.2: Connection-Specific Header Fields. -// Certain headers are special-cased as okay but not transmitted later. -func checkConnHeaders(req *http.Request) error { - if v := req.Header.Get("Upgrade"); v != "" { - return fmt.Errorf("http2: invalid Upgrade request header: %q", req.Header["Upgrade"]) - } - if vv := req.Header["Transfer-Encoding"]; len(vv) > 0 && (len(vv) > 1 || vv[0] != "" && vv[0] != "chunked") { - return fmt.Errorf("http2: invalid Transfer-Encoding request header: %q", vv) - } - if vv := req.Header["Connection"]; len(vv) > 0 && (len(vv) > 1 || vv[0] != "" && !asciiEqualFold(vv[0], "close") && !asciiEqualFold(vv[0], "keep-alive")) { - return fmt.Errorf("http2: invalid Connection request header: %q", vv) - } - return nil -} - // actualContentLength returns a sanitized version of // req.ContentLength, where 0 actually means zero (not unknown) and -1 // means unknown. @@ -1364,25 +1331,7 @@ func (cc *ClientConn) roundTrip(req *http.Request, streamf func(*clientStream)) donec: make(chan struct{}), } - // TODO(bradfitz): this is a copy of the logic in net/http. Unify somewhere? - if !cc.t.disableCompression() && - req.Header.Get("Accept-Encoding") == "" && - req.Header.Get("Range") == "" && - !cs.isHead { - // Request gzip only, not deflate. Deflate is ambiguous and - // not as universally supported anyway. - // See: https://zlib.net/zlib_faq.html#faq39 - // - // Note that we don't request this for HEAD requests, - // due to a bug in nginx: - // http://trac.nginx.org/nginx/ticket/358 - // https://golang.org/issue/5522 - // - // We don't request gzip if the request is for a range, since - // auto-decoding a portion of a gzipped document will just fail - // anyway. See https://golang.org/issue/8923 - cs.requestedGzip = true - } + cs.requestedGzip = httpcommon.IsRequestGzip(req.Method, req.Header, cc.t.disableCompression()) go cs.doRequest(req, streamf) @@ -1496,10 +1445,6 @@ func (cs *clientStream) writeRequest(req *http.Request, streamf func(*clientStre cc := cs.cc ctx := cs.ctx - if err := checkConnHeaders(req); err != nil { - return err - } - // wait for setting frames to be received, a server can change this value later, // but we just wait for the first settings frame var isExtendedConnect bool @@ -1663,26 +1608,39 @@ func (cs *clientStream) encodeAndWriteHeaders(req *http.Request) error { // we send: HEADERS{1}, CONTINUATION{0,} + DATA{0,} (DATA is // sent by writeRequestBody below, along with any Trailers, // again in form HEADERS{1}, CONTINUATION{0,}) - trailers, err := commaSeparatedTrailers(req) - if err != nil { - return err - } - hasTrailers := trailers != "" - contentLen := actualContentLength(req) - hasBody := contentLen != 0 - hdrs, err := cc.encodeHeaders(req, cs.requestedGzip, trailers, contentLen) + cc.hbuf.Reset() + res, err := encodeRequestHeaders(req, cs.requestedGzip, cc.peerMaxHeaderListSize, func(name, value string) { + cc.writeHeader(name, value) + }) if err != nil { - return err + return fmt.Errorf("http2: %w", err) } + hdrs := cc.hbuf.Bytes() // Write the request. - endStream := !hasBody && !hasTrailers + endStream := !res.HasBody && !res.HasTrailers cs.sentHeaders = true err = cc.writeHeaders(cs.ID, endStream, int(cc.maxFrameSize), hdrs) traceWroteHeaders(cs.trace) return err } +func encodeRequestHeaders(req *http.Request, addGzipHeader bool, peerMaxHeaderListSize uint64, headerf func(name, value string)) (httpcommon.EncodeHeadersResult, error) { + return httpcommon.EncodeHeaders(req.Context(), httpcommon.EncodeHeadersParam{ + Request: httpcommon.Request{ + Header: req.Header, + Trailer: req.Trailer, + URL: req.URL, + Host: req.Host, + Method: req.Method, + ActualContentLength: actualContentLength(req), + }, + AddGzipHeader: addGzipHeader, + PeerMaxHeaderListSize: peerMaxHeaderListSize, + DefaultUserAgent: defaultUserAgent, + }, headerf) +} + // cleanupWriteRequest performs post-request tasks. // // If err (the result of writeRequest) is non-nil and the stream is not closed, @@ -2070,218 +2028,6 @@ func (cs *clientStream) awaitFlowControl(maxBytes int) (taken int32, err error) } } -func validateHeaders(hdrs http.Header) string { - for k, vv := range hdrs { - if !httpguts.ValidHeaderFieldName(k) && k != ":protocol" { - return fmt.Sprintf("name %q", k) - } - for _, v := range vv { - if !httpguts.ValidHeaderFieldValue(v) { - // Don't include the value in the error, - // because it may be sensitive. - return fmt.Sprintf("value for header %q", k) - } - } - } - return "" -} - -var errNilRequestURL = errors.New("http2: Request.URI is nil") - -func isNormalConnect(req *http.Request) bool { - return req.Method == "CONNECT" && req.Header.Get(":protocol") == "" -} - -// requires cc.wmu be held. -func (cc *ClientConn) encodeHeaders(req *http.Request, addGzipHeader bool, trailers string, contentLength int64) ([]byte, error) { - cc.hbuf.Reset() - if req.URL == nil { - return nil, errNilRequestURL - } - - host := req.Host - if host == "" { - host = req.URL.Host - } - host, err := httpguts.PunycodeHostPort(host) - if err != nil { - return nil, err - } - if !httpguts.ValidHostHeader(host) { - return nil, errors.New("http2: invalid Host header") - } - - var path string - if !isNormalConnect(req) { - path = req.URL.RequestURI() - if !validPseudoPath(path) { - orig := path - path = strings.TrimPrefix(path, req.URL.Scheme+"://"+host) - if !validPseudoPath(path) { - if req.URL.Opaque != "" { - return nil, fmt.Errorf("invalid request :path %q from URL.Opaque = %q", orig, req.URL.Opaque) - } else { - return nil, fmt.Errorf("invalid request :path %q", orig) - } - } - } - } - - // Check for any invalid headers+trailers and return an error before we - // potentially pollute our hpack state. (We want to be able to - // continue to reuse the hpack encoder for future requests) - if err := validateHeaders(req.Header); err != "" { - return nil, fmt.Errorf("invalid HTTP header %s", err) - } - if err := validateHeaders(req.Trailer); err != "" { - return nil, fmt.Errorf("invalid HTTP trailer %s", err) - } - - enumerateHeaders := func(f func(name, value string)) { - // 8.1.2.3 Request Pseudo-Header Fields - // The :path pseudo-header field includes the path and query parts of the - // target URI (the path-absolute production and optionally a '?' character - // followed by the query production, see Sections 3.3 and 3.4 of - // [RFC3986]). - f(":authority", host) - m := req.Method - if m == "" { - m = http.MethodGet - } - f(":method", m) - if !isNormalConnect(req) { - f(":path", path) - f(":scheme", req.URL.Scheme) - } - if trailers != "" { - f("trailer", trailers) - } - - var didUA bool - for k, vv := range req.Header { - if asciiEqualFold(k, "host") || asciiEqualFold(k, "content-length") { - // Host is :authority, already sent. - // Content-Length is automatic, set below. - continue - } else if asciiEqualFold(k, "connection") || - asciiEqualFold(k, "proxy-connection") || - asciiEqualFold(k, "transfer-encoding") || - asciiEqualFold(k, "upgrade") || - asciiEqualFold(k, "keep-alive") { - // Per 8.1.2.2 Connection-Specific Header - // Fields, don't send connection-specific - // fields. We have already checked if any - // are error-worthy so just ignore the rest. - continue - } else if asciiEqualFold(k, "user-agent") { - // Match Go's http1 behavior: at most one - // User-Agent. If set to nil or empty string, - // then omit it. Otherwise if not mentioned, - // include the default (below). - didUA = true - if len(vv) < 1 { - continue - } - vv = vv[:1] - if vv[0] == "" { - continue - } - } else if asciiEqualFold(k, "cookie") { - // Per 8.1.2.5 To allow for better compression efficiency, the - // Cookie header field MAY be split into separate header fields, - // each with one or more cookie-pairs. - for _, v := range vv { - for { - p := strings.IndexByte(v, ';') - if p < 0 { - break - } - f("cookie", v[:p]) - p++ - // strip space after semicolon if any. - for p+1 <= len(v) && v[p] == ' ' { - p++ - } - v = v[p:] - } - if len(v) > 0 { - f("cookie", v) - } - } - continue - } - - for _, v := range vv { - f(k, v) - } - } - if shouldSendReqContentLength(req.Method, contentLength) { - f("content-length", strconv.FormatInt(contentLength, 10)) - } - if addGzipHeader { - f("accept-encoding", "gzip") - } - if !didUA { - f("user-agent", defaultUserAgent) - } - } - - // Do a first pass over the headers counting bytes to ensure - // we don't exceed cc.peerMaxHeaderListSize. This is done as a - // separate pass before encoding the headers to prevent - // modifying the hpack state. - hlSize := uint64(0) - enumerateHeaders(func(name, value string) { - hf := hpack.HeaderField{Name: name, Value: value} - hlSize += uint64(hf.Size()) - }) - - if hlSize > cc.peerMaxHeaderListSize { - return nil, errRequestHeaderListSize - } - - trace := httptrace.ContextClientTrace(req.Context()) - traceHeaders := traceHasWroteHeaderField(trace) - - // Header list size is ok. Write the headers. - enumerateHeaders(func(name, value string) { - name, ascii := lowerHeader(name) - if !ascii { - // Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header - // field names have to be ASCII characters (just as in HTTP/1.x). - return - } - cc.writeHeader(name, value) - if traceHeaders { - traceWroteHeaderField(trace, name, value) - } - }) - - return cc.hbuf.Bytes(), nil -} - -// shouldSendReqContentLength reports whether the http2.Transport should send -// a "content-length" request header. This logic is basically a copy of the net/http -// transferWriter.shouldSendContentLength. -// The contentLength is the corrected contentLength (so 0 means actually 0, not unknown). -// -1 means unknown. -func shouldSendReqContentLength(method string, contentLength int64) bool { - if contentLength > 0 { - return true - } - if contentLength < 0 { - return false - } - // For zero bodies, whether we send a content-length depends on the method. - // It also kinda doesn't matter for http2 either way, with END_STREAM. - switch method { - case "POST", "PUT", "PATCH": - return true - default: - return false - } -} - // requires cc.wmu be held. func (cc *ClientConn) encodeTrailers(trailer http.Header) ([]byte, error) { cc.hbuf.Reset() @@ -2298,7 +2044,7 @@ func (cc *ClientConn) encodeTrailers(trailer http.Header) ([]byte, error) { } for k, vv := range trailer { - lowKey, ascii := lowerHeader(k) + lowKey, ascii := httpcommon.LowerHeader(k) if !ascii { // Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header // field names have to be ASCII characters (just as in HTTP/1.x). @@ -2464,6 +2210,13 @@ func (rl *clientConnReadLoop) cleanup() { } cc.cond.Broadcast() cc.mu.Unlock() + + if !cc.seenSettings { + // If we have a pending request that wants extended CONNECT, + // let it continue and fail with the connection error. + cc.extendedConnectAllowed = true + close(cc.seenSettingsChan) + } } // countReadFrameError calls Transport.CountError with a string @@ -2556,9 +2309,6 @@ func (rl *clientConnReadLoop) run() error { if VerboseLogs { cc.vlogf("http2: Transport conn %p received error from processing frame %v: %v", cc, summarizeFrame(f), err) } - if !cc.seenSettings { - close(cc.seenSettingsChan) - } return err } } @@ -2653,7 +2403,7 @@ func (rl *clientConnReadLoop) handleResponse(cs *clientStream, f *MetaHeadersFra Status: status + " " + http.StatusText(statusCode), } for _, hf := range regularFields { - key := canonicalHeader(hf.Name) + key := httpcommon.CanonicalHeader(hf.Name) if key == "Trailer" { t := res.Trailer if t == nil { @@ -2661,7 +2411,7 @@ func (rl *clientConnReadLoop) handleResponse(cs *clientStream, f *MetaHeadersFra res.Trailer = t } foreachHeaderElement(hf.Value, func(v string) { - t[canonicalHeader(v)] = nil + t[httpcommon.CanonicalHeader(v)] = nil }) } else { vv := header[key] @@ -2785,7 +2535,7 @@ func (rl *clientConnReadLoop) processTrailers(cs *clientStream, f *MetaHeadersFr trailer := make(http.Header) for _, hf := range f.RegularFields() { - key := canonicalHeader(hf.Name) + key := httpcommon.CanonicalHeader(hf.Name) trailer[key] = append(trailer[key], hf.Value) } cs.trailer = trailer @@ -3331,7 +3081,7 @@ func (cc *ClientConn) writeStreamReset(streamID uint32, code ErrCode, ping bool, var ( errResponseHeaderListSize = errors.New("http2: response header list larger than advertised limit") - errRequestHeaderListSize = errors.New("http2: request header list larger than peer's advertised limit") + errRequestHeaderListSize = httpcommon.ErrRequestHeaderListSize ) func (cc *ClientConn) logf(format string, args ...interface{}) { @@ -3515,16 +3265,6 @@ func traceFirstResponseByte(trace *httptrace.ClientTrace) { } } -func traceHasWroteHeaderField(trace *httptrace.ClientTrace) bool { - return trace != nil && trace.WroteHeaderField != nil -} - -func traceWroteHeaderField(trace *httptrace.ClientTrace, k, v string) { - if trace != nil && trace.WroteHeaderField != nil { - trace.WroteHeaderField(k, []string{v}) - } -} - func traceGot1xxResponseFunc(trace *httptrace.ClientTrace) func(int, textproto.MIMEHeader) error { if trace != nil { return trace.Got1xxResponse diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/write.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/write.go index 6ff6bee7e95..fdb35b9477e 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/write.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/write.go @@ -13,6 +13,7 @@ import ( "golang.org/x/net/http/httpguts" "golang.org/x/net/http2/hpack" + "golang.org/x/net/internal/httpcommon" ) // writeFramer is implemented by any type that is used to write frames. @@ -351,7 +352,7 @@ func encodeHeaders(enc *hpack.Encoder, h http.Header, keys []string) { } for _, k := range keys { vv := h[k] - k, ascii := lowerHeader(k) + k, ascii := httpcommon.LowerHeader(k) if !ascii { // Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header // field names have to be ASCII characters (just as in HTTP/1.x). diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/ascii.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/ascii.go new file mode 100644 index 00000000000..ed14da5afcc --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/ascii.go @@ -0,0 +1,53 @@ +// Copyright 2025 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package httpcommon + +import "strings" + +// The HTTP protocols are defined in terms of ASCII, not Unicode. This file +// contains helper functions which may use Unicode-aware functions which would +// otherwise be unsafe and could introduce vulnerabilities if used improperly. + +// asciiEqualFold is strings.EqualFold, ASCII only. It reports whether s and t +// are equal, ASCII-case-insensitively. +func asciiEqualFold(s, t string) bool { + if len(s) != len(t) { + return false + } + for i := 0; i < len(s); i++ { + if lower(s[i]) != lower(t[i]) { + return false + } + } + return true +} + +// lower returns the ASCII lowercase version of b. +func lower(b byte) byte { + if 'A' <= b && b <= 'Z' { + return b + ('a' - 'A') + } + return b +} + +// isASCIIPrint returns whether s is ASCII and printable according to +// https://tools.ietf.org/html/rfc20#section-4.2. +func isASCIIPrint(s string) bool { + for i := 0; i < len(s); i++ { + if s[i] < ' ' || s[i] > '~' { + return false + } + } + return true +} + +// asciiToLower returns the lowercase version of s if s is ASCII and printable, +// and whether or not it was. +func asciiToLower(s string) (lower string, ok bool) { + if !isASCIIPrint(s) { + return "", false + } + return strings.ToLower(s), true +} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/headermap.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/headermap.go similarity index 74% rename from cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/headermap.go rename to cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/headermap.go index 149b3dd20e4..92483d8e41a 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/http2/headermap.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/headermap.go @@ -1,11 +1,11 @@ -// Copyright 2014 The Go Authors. All rights reserved. +// Copyright 2025 The Go Authors. All rights reserved. // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -package http2 +package httpcommon import ( - "net/http" + "net/textproto" "sync" ) @@ -82,13 +82,15 @@ func buildCommonHeaderMaps() { commonLowerHeader = make(map[string]string, len(common)) commonCanonHeader = make(map[string]string, len(common)) for _, v := range common { - chk := http.CanonicalHeaderKey(v) + chk := textproto.CanonicalMIMEHeaderKey(v) commonLowerHeader[chk] = v commonCanonHeader[v] = chk } } -func lowerHeader(v string) (lower string, ascii bool) { +// LowerHeader returns the lowercase form of a header name, +// used on the wire for HTTP/2 and HTTP/3 requests. +func LowerHeader(v string) (lower string, ascii bool) { buildCommonHeaderMapsOnce() if s, ok := commonLowerHeader[v]; ok { return s, true @@ -96,10 +98,18 @@ func lowerHeader(v string) (lower string, ascii bool) { return asciiToLower(v) } -func canonicalHeader(v string) string { +// CanonicalHeader canonicalizes a header name. (For example, "host" becomes "Host".) +func CanonicalHeader(v string) string { buildCommonHeaderMapsOnce() if s, ok := commonCanonHeader[v]; ok { return s } - return http.CanonicalHeaderKey(v) + return textproto.CanonicalMIMEHeaderKey(v) +} + +// CachedCanonicalHeader returns the canonical form of a well-known header name. +func CachedCanonicalHeader(v string) (string, bool) { + buildCommonHeaderMapsOnce() + s, ok := commonCanonHeader[v] + return s, ok } diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/request.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/request.go new file mode 100644 index 00000000000..4b705531793 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/internal/httpcommon/request.go @@ -0,0 +1,467 @@ +// Copyright 2025 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +package httpcommon + +import ( + "context" + "errors" + "fmt" + "net/http/httptrace" + "net/textproto" + "net/url" + "sort" + "strconv" + "strings" + + "golang.org/x/net/http/httpguts" + "golang.org/x/net/http2/hpack" +) + +var ( + ErrRequestHeaderListSize = errors.New("request header list larger than peer's advertised limit") +) + +// Request is a subset of http.Request. +// It'd be simpler to pass an *http.Request, of course, but we can't depend on net/http +// without creating a dependency cycle. +type Request struct { + URL *url.URL + Method string + Host string + Header map[string][]string + Trailer map[string][]string + ActualContentLength int64 // 0 means 0, -1 means unknown +} + +// EncodeHeadersParam is parameters to EncodeHeaders. +type EncodeHeadersParam struct { + Request Request + + // AddGzipHeader indicates that an "accept-encoding: gzip" header should be + // added to the request. + AddGzipHeader bool + + // PeerMaxHeaderListSize, when non-zero, is the peer's MAX_HEADER_LIST_SIZE setting. + PeerMaxHeaderListSize uint64 + + // DefaultUserAgent is the User-Agent header to send when the request + // neither contains a User-Agent nor disables it. + DefaultUserAgent string +} + +// EncodeHeadersParam is the result of EncodeHeaders. +type EncodeHeadersResult struct { + HasBody bool + HasTrailers bool +} + +// EncodeHeaders constructs request headers common to HTTP/2 and HTTP/3. +// It validates a request and calls headerf with each pseudo-header and header +// for the request. +// The headerf function is called with the validated, canonicalized header name. +func EncodeHeaders(ctx context.Context, param EncodeHeadersParam, headerf func(name, value string)) (res EncodeHeadersResult, _ error) { + req := param.Request + + // Check for invalid connection-level headers. + if err := checkConnHeaders(req.Header); err != nil { + return res, err + } + + if req.URL == nil { + return res, errors.New("Request.URL is nil") + } + + host := req.Host + if host == "" { + host = req.URL.Host + } + host, err := httpguts.PunycodeHostPort(host) + if err != nil { + return res, err + } + if !httpguts.ValidHostHeader(host) { + return res, errors.New("invalid Host header") + } + + // isNormalConnect is true if this is a non-extended CONNECT request. + isNormalConnect := false + var protocol string + if vv := req.Header[":protocol"]; len(vv) > 0 { + protocol = vv[0] + } + if req.Method == "CONNECT" && protocol == "" { + isNormalConnect = true + } else if protocol != "" && req.Method != "CONNECT" { + return res, errors.New("invalid :protocol header in non-CONNECT request") + } + + // Validate the path, except for non-extended CONNECT requests which have no path. + var path string + if !isNormalConnect { + path = req.URL.RequestURI() + if !validPseudoPath(path) { + orig := path + path = strings.TrimPrefix(path, req.URL.Scheme+"://"+host) + if !validPseudoPath(path) { + if req.URL.Opaque != "" { + return res, fmt.Errorf("invalid request :path %q from URL.Opaque = %q", orig, req.URL.Opaque) + } else { + return res, fmt.Errorf("invalid request :path %q", orig) + } + } + } + } + + // Check for any invalid headers+trailers and return an error before we + // potentially pollute our hpack state. (We want to be able to + // continue to reuse the hpack encoder for future requests) + if err := validateHeaders(req.Header); err != "" { + return res, fmt.Errorf("invalid HTTP header %s", err) + } + if err := validateHeaders(req.Trailer); err != "" { + return res, fmt.Errorf("invalid HTTP trailer %s", err) + } + + trailers, err := commaSeparatedTrailers(req.Trailer) + if err != nil { + return res, err + } + + enumerateHeaders := func(f func(name, value string)) { + // 8.1.2.3 Request Pseudo-Header Fields + // The :path pseudo-header field includes the path and query parts of the + // target URI (the path-absolute production and optionally a '?' character + // followed by the query production, see Sections 3.3 and 3.4 of + // [RFC3986]). + f(":authority", host) + m := req.Method + if m == "" { + m = "GET" + } + f(":method", m) + if !isNormalConnect { + f(":path", path) + f(":scheme", req.URL.Scheme) + } + if protocol != "" { + f(":protocol", protocol) + } + if trailers != "" { + f("trailer", trailers) + } + + var didUA bool + for k, vv := range req.Header { + if asciiEqualFold(k, "host") || asciiEqualFold(k, "content-length") { + // Host is :authority, already sent. + // Content-Length is automatic, set below. + continue + } else if asciiEqualFold(k, "connection") || + asciiEqualFold(k, "proxy-connection") || + asciiEqualFold(k, "transfer-encoding") || + asciiEqualFold(k, "upgrade") || + asciiEqualFold(k, "keep-alive") { + // Per 8.1.2.2 Connection-Specific Header + // Fields, don't send connection-specific + // fields. We have already checked if any + // are error-worthy so just ignore the rest. + continue + } else if asciiEqualFold(k, "user-agent") { + // Match Go's http1 behavior: at most one + // User-Agent. If set to nil or empty string, + // then omit it. Otherwise if not mentioned, + // include the default (below). + didUA = true + if len(vv) < 1 { + continue + } + vv = vv[:1] + if vv[0] == "" { + continue + } + } else if asciiEqualFold(k, "cookie") { + // Per 8.1.2.5 To allow for better compression efficiency, the + // Cookie header field MAY be split into separate header fields, + // each with one or more cookie-pairs. + for _, v := range vv { + for { + p := strings.IndexByte(v, ';') + if p < 0 { + break + } + f("cookie", v[:p]) + p++ + // strip space after semicolon if any. + for p+1 <= len(v) && v[p] == ' ' { + p++ + } + v = v[p:] + } + if len(v) > 0 { + f("cookie", v) + } + } + continue + } else if k == ":protocol" { + // :protocol pseudo-header was already sent above. + continue + } + + for _, v := range vv { + f(k, v) + } + } + if shouldSendReqContentLength(req.Method, req.ActualContentLength) { + f("content-length", strconv.FormatInt(req.ActualContentLength, 10)) + } + if param.AddGzipHeader { + f("accept-encoding", "gzip") + } + if !didUA { + f("user-agent", param.DefaultUserAgent) + } + } + + // Do a first pass over the headers counting bytes to ensure + // we don't exceed cc.peerMaxHeaderListSize. This is done as a + // separate pass before encoding the headers to prevent + // modifying the hpack state. + if param.PeerMaxHeaderListSize > 0 { + hlSize := uint64(0) + enumerateHeaders(func(name, value string) { + hf := hpack.HeaderField{Name: name, Value: value} + hlSize += uint64(hf.Size()) + }) + + if hlSize > param.PeerMaxHeaderListSize { + return res, ErrRequestHeaderListSize + } + } + + trace := httptrace.ContextClientTrace(ctx) + + // Header list size is ok. Write the headers. + enumerateHeaders(func(name, value string) { + name, ascii := LowerHeader(name) + if !ascii { + // Skip writing invalid headers. Per RFC 7540, Section 8.1.2, header + // field names have to be ASCII characters (just as in HTTP/1.x). + return + } + + headerf(name, value) + + if trace != nil && trace.WroteHeaderField != nil { + trace.WroteHeaderField(name, []string{value}) + } + }) + + res.HasBody = req.ActualContentLength != 0 + res.HasTrailers = trailers != "" + return res, nil +} + +// IsRequestGzip reports whether we should add an Accept-Encoding: gzip header +// for a request. +func IsRequestGzip(method string, header map[string][]string, disableCompression bool) bool { + // TODO(bradfitz): this is a copy of the logic in net/http. Unify somewhere? + if !disableCompression && + len(header["Accept-Encoding"]) == 0 && + len(header["Range"]) == 0 && + method != "HEAD" { + // Request gzip only, not deflate. Deflate is ambiguous and + // not as universally supported anyway. + // See: https://zlib.net/zlib_faq.html#faq39 + // + // Note that we don't request this for HEAD requests, + // due to a bug in nginx: + // http://trac.nginx.org/nginx/ticket/358 + // https://golang.org/issue/5522 + // + // We don't request gzip if the request is for a range, since + // auto-decoding a portion of a gzipped document will just fail + // anyway. See https://golang.org/issue/8923 + return true + } + return false +} + +// checkConnHeaders checks whether req has any invalid connection-level headers. +// +// https://www.rfc-editor.org/rfc/rfc9114.html#section-4.2-3 +// https://www.rfc-editor.org/rfc/rfc9113.html#section-8.2.2-1 +// +// Certain headers are special-cased as okay but not transmitted later. +// For example, we allow "Transfer-Encoding: chunked", but drop the header when encoding. +func checkConnHeaders(h map[string][]string) error { + if vv := h["Upgrade"]; len(vv) > 0 && (vv[0] != "" && vv[0] != "chunked") { + return fmt.Errorf("invalid Upgrade request header: %q", vv) + } + if vv := h["Transfer-Encoding"]; len(vv) > 0 && (len(vv) > 1 || vv[0] != "" && vv[0] != "chunked") { + return fmt.Errorf("invalid Transfer-Encoding request header: %q", vv) + } + if vv := h["Connection"]; len(vv) > 0 && (len(vv) > 1 || vv[0] != "" && !asciiEqualFold(vv[0], "close") && !asciiEqualFold(vv[0], "keep-alive")) { + return fmt.Errorf("invalid Connection request header: %q", vv) + } + return nil +} + +func commaSeparatedTrailers(trailer map[string][]string) (string, error) { + keys := make([]string, 0, len(trailer)) + for k := range trailer { + k = CanonicalHeader(k) + switch k { + case "Transfer-Encoding", "Trailer", "Content-Length": + return "", fmt.Errorf("invalid Trailer key %q", k) + } + keys = append(keys, k) + } + if len(keys) > 0 { + sort.Strings(keys) + return strings.Join(keys, ","), nil + } + return "", nil +} + +// validPseudoPath reports whether v is a valid :path pseudo-header +// value. It must be either: +// +// - a non-empty string starting with '/' +// - the string '*', for OPTIONS requests. +// +// For now this is only used a quick check for deciding when to clean +// up Opaque URLs before sending requests from the Transport. +// See golang.org/issue/16847 +// +// We used to enforce that the path also didn't start with "//", but +// Google's GFE accepts such paths and Chrome sends them, so ignore +// that part of the spec. See golang.org/issue/19103. +func validPseudoPath(v string) bool { + return (len(v) > 0 && v[0] == '/') || v == "*" +} + +func validateHeaders(hdrs map[string][]string) string { + for k, vv := range hdrs { + if !httpguts.ValidHeaderFieldName(k) && k != ":protocol" { + return fmt.Sprintf("name %q", k) + } + for _, v := range vv { + if !httpguts.ValidHeaderFieldValue(v) { + // Don't include the value in the error, + // because it may be sensitive. + return fmt.Sprintf("value for header %q", k) + } + } + } + return "" +} + +// shouldSendReqContentLength reports whether we should send +// a "content-length" request header. This logic is basically a copy of the net/http +// transferWriter.shouldSendContentLength. +// The contentLength is the corrected contentLength (so 0 means actually 0, not unknown). +// -1 means unknown. +func shouldSendReqContentLength(method string, contentLength int64) bool { + if contentLength > 0 { + return true + } + if contentLength < 0 { + return false + } + // For zero bodies, whether we send a content-length depends on the method. + // It also kinda doesn't matter for http2 either way, with END_STREAM. + switch method { + case "POST", "PUT", "PATCH": + return true + default: + return false + } +} + +// ServerRequestParam is parameters to NewServerRequest. +type ServerRequestParam struct { + Method string + Scheme, Authority, Path string + Protocol string + Header map[string][]string +} + +// ServerRequestResult is the result of NewServerRequest. +type ServerRequestResult struct { + // Various http.Request fields. + URL *url.URL + RequestURI string + Trailer map[string][]string + + NeedsContinue bool // client provided an "Expect: 100-continue" header + + // If the request should be rejected, this is a short string suitable for passing + // to the http2 package's CountError function. + // It might be a bit odd to return errors this way rather than returing an error, + // but this ensures we don't forget to include a CountError reason. + InvalidReason string +} + +func NewServerRequest(rp ServerRequestParam) ServerRequestResult { + needsContinue := httpguts.HeaderValuesContainsToken(rp.Header["Expect"], "100-continue") + if needsContinue { + delete(rp.Header, "Expect") + } + // Merge Cookie headers into one "; "-delimited value. + if cookies := rp.Header["Cookie"]; len(cookies) > 1 { + rp.Header["Cookie"] = []string{strings.Join(cookies, "; ")} + } + + // Setup Trailers + var trailer map[string][]string + for _, v := range rp.Header["Trailer"] { + for _, key := range strings.Split(v, ",") { + key = textproto.CanonicalMIMEHeaderKey(textproto.TrimString(key)) + switch key { + case "Transfer-Encoding", "Trailer", "Content-Length": + // Bogus. (copy of http1 rules) + // Ignore. + default: + if trailer == nil { + trailer = make(map[string][]string) + } + trailer[key] = nil + } + } + } + delete(rp.Header, "Trailer") + + // "':authority' MUST NOT include the deprecated userinfo subcomponent + // for "http" or "https" schemed URIs." + // https://www.rfc-editor.org/rfc/rfc9113.html#section-8.3.1-2.3.8 + if strings.IndexByte(rp.Authority, '@') != -1 && (rp.Scheme == "http" || rp.Scheme == "https") { + return ServerRequestResult{ + InvalidReason: "userinfo_in_authority", + } + } + + var url_ *url.URL + var requestURI string + if rp.Method == "CONNECT" && rp.Protocol == "" { + url_ = &url.URL{Host: rp.Authority} + requestURI = rp.Authority // mimic HTTP/1 server behavior + } else { + var err error + url_, err = url.ParseRequestURI(rp.Path) + if err != nil { + return ServerRequestResult{ + InvalidReason: "bad_path", + } + } + requestURI = rp.Path + } + + return ServerRequestResult{ + URL: url_, + NeedsContinue: needsContinue, + RequestURI: requestURI, + Trailer: trailer, + } +} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/net/websocket/websocket.go b/cluster-api/providers/vsphere/vendor/golang.org/x/net/websocket/websocket.go index ac76165cebb..3448d20395c 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/net/websocket/websocket.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/net/websocket/websocket.go @@ -6,9 +6,10 @@ // as specified in RFC 6455. // // This package currently lacks some features found in an alternative -// and more actively maintained WebSocket package: +// and more actively maintained WebSocket packages: // -// https://pkg.go.dev/github.com/coder/websocket +// - [github.com/gorilla/websocket] +// - [github.com/coder/websocket] package websocket // import "golang.org/x/net/websocket" import ( diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/oauth2.go b/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/oauth2.go index 74f052aa9fa..eacdd7fd933 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/oauth2.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/oauth2.go @@ -288,7 +288,7 @@ func (tf *tokenRefresher) Token() (*Token, error) { if tf.refreshToken != tk.RefreshToken { tf.refreshToken = tk.RefreshToken } - return tk, err + return tk, nil } // reuseTokenSource is a TokenSource that holds a single token in memory @@ -356,11 +356,15 @@ func NewClient(ctx context.Context, src TokenSource) *http.Client { if src == nil { return internal.ContextClient(ctx) } + cc := internal.ContextClient(ctx) return &http.Client{ Transport: &Transport{ - Base: internal.ContextClient(ctx).Transport, + Base: cc.Transport, Source: ReuseTokenSource(nil, src), }, + CheckRedirect: cc.CheckRedirect, + Jar: cc.Jar, + Timeout: cc.Timeout, } } diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/pkce.go b/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/pkce.go index 50593b6dfec..6a95da975ce 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/pkce.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/oauth2/pkce.go @@ -21,7 +21,7 @@ const ( // // A fresh verifier should be generated for each authorization. // S256ChallengeOption(verifier) should then be passed to Config.AuthCodeURL -// (or Config.DeviceAccess) and VerifierOption(verifier) to Config.Exchange +// (or Config.DeviceAuth) and VerifierOption(verifier) to Config.Exchange // (or Config.DeviceAccessToken). func GenerateVerifier() string { // "RECOMMENDED that the output of a suitable random number generator be @@ -51,7 +51,7 @@ func S256ChallengeFromVerifier(verifier string) string { } // S256ChallengeOption derives a PKCE code challenge derived from verifier with -// method S256. It should be passed to Config.AuthCodeURL or Config.DeviceAccess +// method S256. It should be passed to Config.AuthCodeURL or Config.DeviceAuth // only. func S256ChallengeOption(verifier string) AuthCodeOption { return challengeOption{ diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/errgroup.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/errgroup.go index 948a3ee63d4..a4ea5d14f15 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/errgroup.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/errgroup.go @@ -46,7 +46,7 @@ func (g *Group) done() { // returns a non-nil error or the first time Wait returns, whichever occurs // first. func WithContext(ctx context.Context) (*Group, context.Context) { - ctx, cancel := withCancelCause(ctx) + ctx, cancel := context.WithCancelCause(ctx) return &Group{cancel: cancel}, ctx } @@ -118,6 +118,7 @@ func (g *Group) TryGo(f func() error) bool { // SetLimit limits the number of active goroutines in this group to at most n. // A negative value indicates no limit. +// A limit of zero will prevent any new goroutines from being added. // // Any subsequent call to the Go method will block until it can add an active // goroutine without exceeding the configured limit. diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/go120.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/go120.go deleted file mode 100644 index f93c740b638..00000000000 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/go120.go +++ /dev/null @@ -1,13 +0,0 @@ -// Copyright 2023 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -//go:build go1.20 - -package errgroup - -import "context" - -func withCancelCause(parent context.Context) (context.Context, func(error)) { - return context.WithCancelCause(parent) -} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/pre_go120.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/pre_go120.go deleted file mode 100644 index 88ce33434e2..00000000000 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sync/errgroup/pre_go120.go +++ /dev/null @@ -1,14 +0,0 @@ -// Copyright 2023 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -//go:build !go1.20 - -package errgroup - -import "context" - -func withCancelCause(parent context.Context) (context.Context, func(error)) { - ctx, cancel := context.WithCancel(parent) - return ctx, func(error) { cancel() } -} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv.go new file mode 100644 index 00000000000..37a82528f58 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv.go @@ -0,0 +1,36 @@ +// Copyright 2025 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +//go:build go1.21 && (aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd || solaris || zos) + +package unix + +import ( + "syscall" + "unsafe" +) + +//go:linkname runtime_getAuxv runtime.getAuxv +func runtime_getAuxv() []uintptr + +// Auxv returns the ELF auxiliary vector as a sequence of key/value pairs. +// The returned slice is always a fresh copy, owned by the caller. +// It returns an error on non-ELF platforms, or if the auxiliary vector cannot be accessed, +// which happens in some locked-down environments and build modes. +func Auxv() ([][2]uintptr, error) { + vec := runtime_getAuxv() + vecLen := len(vec) + + if vecLen == 0 { + return nil, syscall.ENOENT + } + + if vecLen%2 != 0 { + return nil, syscall.EINVAL + } + + result := make([]uintptr, vecLen) + copy(result, vec) + return unsafe.Slice((*[2]uintptr)(unsafe.Pointer(&result[0])), vecLen/2), nil +} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv_unsupported.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv_unsupported.go new file mode 100644 index 00000000000..1200487f2e8 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/auxv_unsupported.go @@ -0,0 +1,13 @@ +// Copyright 2025 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +//go:build !go1.21 && (aix || darwin || dragonfly || freebsd || linux || netbsd || openbsd || solaris || zos) + +package unix + +import "syscall" + +func Auxv() ([][2]uintptr, error) { + return nil, syscall.ENOTSUP +} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_darwin.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_darwin.go index 099867deede..798f61ad3bf 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_darwin.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_darwin.go @@ -602,7 +602,150 @@ func Connectx(fd int, srcIf uint32, srcAddr, dstAddr Sockaddr, associd SaeAssocI return } -//sys connectx(fd int, endpoints *SaEndpoints, associd SaeAssocID, flags uint32, iov []Iovec, n *uintptr, connid *SaeConnID) (err error) +// sys connectx(fd int, endpoints *SaEndpoints, associd SaeAssocID, flags uint32, iov []Iovec, n *uintptr, connid *SaeConnID) (err error) +const minIovec = 8 + +func Readv(fd int, iovs [][]byte) (n int, err error) { + if !darwinKernelVersionMin(11, 0, 0) { + return 0, ENOSYS + } + + iovecs := make([]Iovec, 0, minIovec) + iovecs = appendBytes(iovecs, iovs) + n, err = readv(fd, iovecs) + readvRacedetect(iovecs, n, err) + return n, err +} + +func Preadv(fd int, iovs [][]byte, offset int64) (n int, err error) { + if !darwinKernelVersionMin(11, 0, 0) { + return 0, ENOSYS + } + iovecs := make([]Iovec, 0, minIovec) + iovecs = appendBytes(iovecs, iovs) + n, err = preadv(fd, iovecs, offset) + readvRacedetect(iovecs, n, err) + return n, err +} + +func Writev(fd int, iovs [][]byte) (n int, err error) { + if !darwinKernelVersionMin(11, 0, 0) { + return 0, ENOSYS + } + + iovecs := make([]Iovec, 0, minIovec) + iovecs = appendBytes(iovecs, iovs) + if raceenabled { + raceReleaseMerge(unsafe.Pointer(&ioSync)) + } + n, err = writev(fd, iovecs) + writevRacedetect(iovecs, n) + return n, err +} + +func Pwritev(fd int, iovs [][]byte, offset int64) (n int, err error) { + if !darwinKernelVersionMin(11, 0, 0) { + return 0, ENOSYS + } + + iovecs := make([]Iovec, 0, minIovec) + iovecs = appendBytes(iovecs, iovs) + if raceenabled { + raceReleaseMerge(unsafe.Pointer(&ioSync)) + } + n, err = pwritev(fd, iovecs, offset) + writevRacedetect(iovecs, n) + return n, err +} + +func appendBytes(vecs []Iovec, bs [][]byte) []Iovec { + for _, b := range bs { + var v Iovec + v.SetLen(len(b)) + if len(b) > 0 { + v.Base = &b[0] + } else { + v.Base = (*byte)(unsafe.Pointer(&_zero)) + } + vecs = append(vecs, v) + } + return vecs +} + +func writevRacedetect(iovecs []Iovec, n int) { + if !raceenabled { + return + } + for i := 0; n > 0 && i < len(iovecs); i++ { + m := int(iovecs[i].Len) + if m > n { + m = n + } + n -= m + if m > 0 { + raceReadRange(unsafe.Pointer(iovecs[i].Base), m) + } + } +} + +func readvRacedetect(iovecs []Iovec, n int, err error) { + if !raceenabled { + return + } + for i := 0; n > 0 && i < len(iovecs); i++ { + m := int(iovecs[i].Len) + if m > n { + m = n + } + n -= m + if m > 0 { + raceWriteRange(unsafe.Pointer(iovecs[i].Base), m) + } + } + if err == nil { + raceAcquire(unsafe.Pointer(&ioSync)) + } +} + +func darwinMajorMinPatch() (maj, min, patch int, err error) { + var un Utsname + err = Uname(&un) + if err != nil { + return + } + + var mmp [3]int + c := 0 +Loop: + for _, b := range un.Release[:] { + switch { + case b >= '0' && b <= '9': + mmp[c] = 10*mmp[c] + int(b-'0') + case b == '.': + c++ + if c > 2 { + return 0, 0, 0, ENOTSUP + } + case b == 0: + break Loop + default: + return 0, 0, 0, ENOTSUP + } + } + if c != 2 { + return 0, 0, 0, ENOTSUP + } + return mmp[0], mmp[1], mmp[2], nil +} + +func darwinKernelVersionMin(maj, min, patch int) bool { + actualMaj, actualMin, actualPatch, err := darwinMajorMinPatch() + if err != nil { + return false + } + return actualMaj > maj || actualMaj == maj && (actualMin > min || actualMin == min && actualPatch >= patch) +} + //sys sendfile(infd int, outfd int, offset int64, len *int64, hdtr unsafe.Pointer, flags int) (err error) //sys shmat(id int, addr uintptr, flag int) (ret uintptr, err error) @@ -705,3 +848,7 @@ func Connectx(fd int, srcIf uint32, srcAddr, dstAddr Sockaddr, associd SaeAssocI //sys write(fd int, p []byte) (n int, err error) //sys mmap(addr uintptr, length uintptr, prot int, flag int, fd int, pos int64) (ret uintptr, err error) //sys munmap(addr uintptr, length uintptr) (err error) +//sys readv(fd int, iovecs []Iovec) (n int, err error) +//sys preadv(fd int, iovecs []Iovec, offset int64) (n int, err error) +//sys writev(fd int, iovecs []Iovec) (n int, err error) +//sys pwritev(fd int, iovecs []Iovec, offset int64) (n int, err error) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_linux.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_linux.go index 230a94549a7..4958a657085 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_linux.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_linux.go @@ -13,6 +13,7 @@ package unix import ( "encoding/binary" + "slices" "strconv" "syscall" "time" @@ -417,7 +418,7 @@ func (sa *SockaddrUnix) sockaddr() (unsafe.Pointer, _Socklen, error) { return nil, 0, EINVAL } sa.raw.Family = AF_UNIX - for i := 0; i < n; i++ { + for i := range n { sa.raw.Path[i] = int8(name[i]) } // length is family (uint16), name, NUL. @@ -507,7 +508,7 @@ func (sa *SockaddrL2) sockaddr() (unsafe.Pointer, _Socklen, error) { psm := (*[2]byte)(unsafe.Pointer(&sa.raw.Psm)) psm[0] = byte(sa.PSM) psm[1] = byte(sa.PSM >> 8) - for i := 0; i < len(sa.Addr); i++ { + for i := range len(sa.Addr) { sa.raw.Bdaddr[i] = sa.Addr[len(sa.Addr)-1-i] } cid := (*[2]byte)(unsafe.Pointer(&sa.raw.Cid)) @@ -589,11 +590,11 @@ func (sa *SockaddrCAN) sockaddr() (unsafe.Pointer, _Socklen, error) { sa.raw.Family = AF_CAN sa.raw.Ifindex = int32(sa.Ifindex) rx := (*[4]byte)(unsafe.Pointer(&sa.RxID)) - for i := 0; i < 4; i++ { + for i := range 4 { sa.raw.Addr[i] = rx[i] } tx := (*[4]byte)(unsafe.Pointer(&sa.TxID)) - for i := 0; i < 4; i++ { + for i := range 4 { sa.raw.Addr[i+4] = tx[i] } return unsafe.Pointer(&sa.raw), SizeofSockaddrCAN, nil @@ -618,11 +619,11 @@ func (sa *SockaddrCANJ1939) sockaddr() (unsafe.Pointer, _Socklen, error) { sa.raw.Family = AF_CAN sa.raw.Ifindex = int32(sa.Ifindex) n := (*[8]byte)(unsafe.Pointer(&sa.Name)) - for i := 0; i < 8; i++ { + for i := range 8 { sa.raw.Addr[i] = n[i] } p := (*[4]byte)(unsafe.Pointer(&sa.PGN)) - for i := 0; i < 4; i++ { + for i := range 4 { sa.raw.Addr[i+8] = p[i] } sa.raw.Addr[12] = sa.Addr @@ -911,7 +912,7 @@ func (sa *SockaddrIUCV) sockaddr() (unsafe.Pointer, _Socklen, error) { // These are EBCDIC encoded by the kernel, but we still need to pad them // with blanks. Initializing with blanks allows the caller to feed in either // a padded or an unpadded string. - for i := 0; i < 8; i++ { + for i := range 8 { sa.raw.Nodeid[i] = ' ' sa.raw.User_id[i] = ' ' sa.raw.Name[i] = ' ' @@ -1148,7 +1149,7 @@ func anyToSockaddr(fd int, rsa *RawSockaddrAny) (Sockaddr, error) { var user [8]byte var name [8]byte - for i := 0; i < 8; i++ { + for i := range 8 { user[i] = byte(pp.User_id[i]) name[i] = byte(pp.Name[i]) } @@ -1173,11 +1174,11 @@ func anyToSockaddr(fd int, rsa *RawSockaddrAny) (Sockaddr, error) { Ifindex: int(pp.Ifindex), } name := (*[8]byte)(unsafe.Pointer(&sa.Name)) - for i := 0; i < 8; i++ { + for i := range 8 { name[i] = pp.Addr[i] } pgn := (*[4]byte)(unsafe.Pointer(&sa.PGN)) - for i := 0; i < 4; i++ { + for i := range 4 { pgn[i] = pp.Addr[i+8] } addr := (*[1]byte)(unsafe.Pointer(&sa.Addr)) @@ -1188,11 +1189,11 @@ func anyToSockaddr(fd int, rsa *RawSockaddrAny) (Sockaddr, error) { Ifindex: int(pp.Ifindex), } rx := (*[4]byte)(unsafe.Pointer(&sa.RxID)) - for i := 0; i < 4; i++ { + for i := range 4 { rx[i] = pp.Addr[i] } tx := (*[4]byte)(unsafe.Pointer(&sa.TxID)) - for i := 0; i < 4; i++ { + for i := range 4 { tx[i] = pp.Addr[i+4] } return sa, nil @@ -2216,10 +2217,7 @@ func readvRacedetect(iovecs []Iovec, n int, err error) { return } for i := 0; n > 0 && i < len(iovecs); i++ { - m := int(iovecs[i].Len) - if m > n { - m = n - } + m := min(int(iovecs[i].Len), n) n -= m if m > 0 { raceWriteRange(unsafe.Pointer(iovecs[i].Base), m) @@ -2270,10 +2268,7 @@ func writevRacedetect(iovecs []Iovec, n int) { return } for i := 0; n > 0 && i < len(iovecs); i++ { - m := int(iovecs[i].Len) - if m > n { - m = n - } + m := min(int(iovecs[i].Len), n) n -= m if m > 0 { raceReadRange(unsafe.Pointer(iovecs[i].Base), m) @@ -2320,12 +2315,7 @@ func isGroupMember(gid int) bool { return false } - for _, g := range groups { - if g == gid { - return true - } - } - return false + return slices.Contains(groups, gid) } func isCapDacOverrideSet() bool { diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_solaris.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_solaris.go index 21974af064d..abc3955477c 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_solaris.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/syscall_solaris.go @@ -1102,3 +1102,90 @@ func (s *Strioctl) SetInt(i int) { func IoctlSetStrioctlRetInt(fd int, req int, s *Strioctl) (int, error) { return ioctlPtrRet(fd, req, unsafe.Pointer(s)) } + +// Ucred Helpers +// See ucred(3c) and getpeerucred(3c) + +//sys getpeerucred(fd uintptr, ucred *uintptr) (err error) +//sys ucredFree(ucred uintptr) = ucred_free +//sys ucredGet(pid int) (ucred uintptr, err error) = ucred_get +//sys ucredGeteuid(ucred uintptr) (uid int) = ucred_geteuid +//sys ucredGetegid(ucred uintptr) (gid int) = ucred_getegid +//sys ucredGetruid(ucred uintptr) (uid int) = ucred_getruid +//sys ucredGetrgid(ucred uintptr) (gid int) = ucred_getrgid +//sys ucredGetsuid(ucred uintptr) (uid int) = ucred_getsuid +//sys ucredGetsgid(ucred uintptr) (gid int) = ucred_getsgid +//sys ucredGetpid(ucred uintptr) (pid int) = ucred_getpid + +// Ucred is an opaque struct that holds user credentials. +type Ucred struct { + ucred uintptr +} + +// We need to ensure that ucredFree is called on the underlying ucred +// when the Ucred is garbage collected. +func ucredFinalizer(u *Ucred) { + ucredFree(u.ucred) +} + +func GetPeerUcred(fd uintptr) (*Ucred, error) { + var ucred uintptr + err := getpeerucred(fd, &ucred) + if err != nil { + return nil, err + } + result := &Ucred{ + ucred: ucred, + } + // set the finalizer on the result so that the ucred will be freed + runtime.SetFinalizer(result, ucredFinalizer) + return result, nil +} + +func UcredGet(pid int) (*Ucred, error) { + ucred, err := ucredGet(pid) + if err != nil { + return nil, err + } + result := &Ucred{ + ucred: ucred, + } + // set the finalizer on the result so that the ucred will be freed + runtime.SetFinalizer(result, ucredFinalizer) + return result, nil +} + +func (u *Ucred) Geteuid() int { + defer runtime.KeepAlive(u) + return ucredGeteuid(u.ucred) +} + +func (u *Ucred) Getruid() int { + defer runtime.KeepAlive(u) + return ucredGetruid(u.ucred) +} + +func (u *Ucred) Getsuid() int { + defer runtime.KeepAlive(u) + return ucredGetsuid(u.ucred) +} + +func (u *Ucred) Getegid() int { + defer runtime.KeepAlive(u) + return ucredGetegid(u.ucred) +} + +func (u *Ucred) Getrgid() int { + defer runtime.KeepAlive(u) + return ucredGetrgid(u.ucred) +} + +func (u *Ucred) Getsgid() int { + defer runtime.KeepAlive(u) + return ucredGetsgid(u.ucred) +} + +func (u *Ucred) Getpid() int { + defer runtime.KeepAlive(u) + return ucredGetpid(u.ucred) +} diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux.go index 6ebc48b3fec..4f432bfe8fe 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux.go @@ -1245,6 +1245,7 @@ const ( FAN_REPORT_DFID_NAME = 0xc00 FAN_REPORT_DFID_NAME_TARGET = 0x1e00 FAN_REPORT_DIR_FID = 0x400 + FAN_REPORT_FD_ERROR = 0x2000 FAN_REPORT_FID = 0x200 FAN_REPORT_NAME = 0x800 FAN_REPORT_PIDFD = 0x80 @@ -1330,8 +1331,10 @@ const ( FUSE_SUPER_MAGIC = 0x65735546 FUTEXFS_SUPER_MAGIC = 0xbad1dea F_ADD_SEALS = 0x409 + F_CREATED_QUERY = 0x404 F_DUPFD = 0x0 F_DUPFD_CLOEXEC = 0x406 + F_DUPFD_QUERY = 0x403 F_EXLCK = 0x4 F_GETFD = 0x1 F_GETFL = 0x3 @@ -1551,6 +1554,7 @@ const ( IPPROTO_ROUTING = 0x2b IPPROTO_RSVP = 0x2e IPPROTO_SCTP = 0x84 + IPPROTO_SMC = 0x100 IPPROTO_TCP = 0x6 IPPROTO_TP = 0x1d IPPROTO_UDP = 0x11 @@ -1623,6 +1627,8 @@ const ( IPV6_UNICAST_IF = 0x4c IPV6_USER_FLOW = 0xe IPV6_V6ONLY = 0x1a + IPV6_VERSION = 0x60 + IPV6_VERSION_MASK = 0xf0 IPV6_XFRM_POLICY = 0x23 IP_ADD_MEMBERSHIP = 0x23 IP_ADD_SOURCE_MEMBERSHIP = 0x27 @@ -1867,6 +1873,7 @@ const ( MADV_UNMERGEABLE = 0xd MADV_WILLNEED = 0x3 MADV_WIPEONFORK = 0x12 + MAP_DROPPABLE = 0x8 MAP_FILE = 0x0 MAP_FIXED = 0x10 MAP_FIXED_NOREPLACE = 0x100000 @@ -1967,6 +1974,7 @@ const ( MSG_PEEK = 0x2 MSG_PROXY = 0x10 MSG_RST = 0x1000 + MSG_SOCK_DEVMEM = 0x2000000 MSG_SYN = 0x400 MSG_TRUNC = 0x20 MSG_TRYHARD = 0x4 @@ -2083,6 +2091,7 @@ const ( NFC_ATR_REQ_MAXSIZE = 0x40 NFC_ATR_RES_GB_MAXSIZE = 0x2f NFC_ATR_RES_MAXSIZE = 0x40 + NFC_ATS_MAXSIZE = 0x14 NFC_COMM_ACTIVE = 0x0 NFC_COMM_PASSIVE = 0x1 NFC_DEVICE_NAME_MAXSIZE = 0x8 @@ -2163,6 +2172,7 @@ const ( NFNL_SUBSYS_QUEUE = 0x3 NFNL_SUBSYS_ULOG = 0x4 NFS_SUPER_MAGIC = 0x6969 + NFT_BITWISE_BOOL = 0x0 NFT_CHAIN_FLAGS = 0x7 NFT_CHAIN_MAXNAMELEN = 0x100 NFT_CT_MAX = 0x17 @@ -2491,6 +2501,7 @@ const ( PR_GET_PDEATHSIG = 0x2 PR_GET_SECCOMP = 0x15 PR_GET_SECUREBITS = 0x1b + PR_GET_SHADOW_STACK_STATUS = 0x4a PR_GET_SPECULATION_CTRL = 0x34 PR_GET_TAGGED_ADDR_CTRL = 0x38 PR_GET_THP_DISABLE = 0x2a @@ -2499,6 +2510,7 @@ const ( PR_GET_TIMING = 0xd PR_GET_TSC = 0x19 PR_GET_UNALIGN = 0x5 + PR_LOCK_SHADOW_STACK_STATUS = 0x4c PR_MCE_KILL = 0x21 PR_MCE_KILL_CLEAR = 0x0 PR_MCE_KILL_DEFAULT = 0x2 @@ -2525,6 +2537,8 @@ const ( PR_PAC_GET_ENABLED_KEYS = 0x3d PR_PAC_RESET_KEYS = 0x36 PR_PAC_SET_ENABLED_KEYS = 0x3c + PR_PMLEN_MASK = 0x7f000000 + PR_PMLEN_SHIFT = 0x18 PR_PPC_DEXCR_CTRL_CLEAR = 0x4 PR_PPC_DEXCR_CTRL_CLEAR_ONEXEC = 0x10 PR_PPC_DEXCR_CTRL_EDITABLE = 0x1 @@ -2592,6 +2606,7 @@ const ( PR_SET_PTRACER = 0x59616d61 PR_SET_SECCOMP = 0x16 PR_SET_SECUREBITS = 0x1c + PR_SET_SHADOW_STACK_STATUS = 0x4b PR_SET_SPECULATION_CTRL = 0x35 PR_SET_SYSCALL_USER_DISPATCH = 0x3b PR_SET_TAGGED_ADDR_CTRL = 0x37 @@ -2602,6 +2617,9 @@ const ( PR_SET_UNALIGN = 0x6 PR_SET_VMA = 0x53564d41 PR_SET_VMA_ANON_NAME = 0x0 + PR_SHADOW_STACK_ENABLE = 0x1 + PR_SHADOW_STACK_PUSH = 0x4 + PR_SHADOW_STACK_WRITE = 0x2 PR_SME_GET_VL = 0x40 PR_SME_SET_VL = 0x3f PR_SME_SET_VL_ONEXEC = 0x40000 @@ -2911,7 +2929,6 @@ const ( RTM_NEWNEXTHOP = 0x68 RTM_NEWNEXTHOPBUCKET = 0x74 RTM_NEWNSID = 0x58 - RTM_NEWNVLAN = 0x70 RTM_NEWPREFIX = 0x34 RTM_NEWQDISC = 0x24 RTM_NEWROUTE = 0x18 @@ -2920,6 +2937,7 @@ const ( RTM_NEWTCLASS = 0x28 RTM_NEWTFILTER = 0x2c RTM_NEWTUNNEL = 0x78 + RTM_NEWVLAN = 0x70 RTM_NR_FAMILIES = 0x1b RTM_NR_MSGTYPES = 0x6c RTM_SETDCB = 0x4f diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_386.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_386.go index c0d45e32050..75207613c78 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_386.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_386.go @@ -116,6 +116,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -304,6 +306,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_amd64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_amd64.go index c731d24f025..c68acda5352 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_amd64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_amd64.go @@ -116,6 +116,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -305,6 +307,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm.go index 680018a4a7c..a8c607ab86b 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -310,6 +312,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm64.go index a63909f308d..18563dd8d33 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_arm64.go @@ -109,6 +109,7 @@ const ( F_SETOWN = 0x8 F_UNLCK = 0x2 F_WRLCK = 0x1 + GCS_MAGIC = 0x47435300 HIDIOCGRAWINFO = 0x80084803 HIDIOCGRDESC = 0x90044802 HIDIOCGRDESCSIZE = 0x80044801 @@ -119,6 +120,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -302,6 +305,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_loong64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_loong64.go index 9b0a2573fe3..22912cdaa94 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_loong64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_loong64.go @@ -116,6 +116,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -297,6 +299,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips.go index 958e6e0645a..29344eb37ab 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x80 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xfffffff + IPV6_FLOWLABEL_MASK = 0xfffff ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -303,6 +305,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64.go index 50c7f25bd16..20d51fb96a8 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x80 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xfffffff + IPV6_FLOWLABEL_MASK = 0xfffff ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -303,6 +305,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64le.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64le.go index ced21d66d95..321b60902ae 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64le.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mips64le.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x80 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -303,6 +305,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mipsle.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mipsle.go index 226c0441902..9bacdf1e279 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mipsle.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_mipsle.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x80 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -303,6 +305,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc.go index 3122737cd46..c2242726156 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xfffffff + IPV6_FLOWLABEL_MASK = 0xfffff ISIG = 0x80 IUCLC = 0x1000 IXOFF = 0x400 @@ -358,6 +360,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64.go index eb5d3467edf..6270c8ee13e 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xfffffff + IPV6_FLOWLABEL_MASK = 0xfffff ISIG = 0x80 IUCLC = 0x1000 IXOFF = 0x400 @@ -362,6 +364,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64le.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64le.go index e921ebc60b7..9966c1941f8 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64le.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_ppc64le.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x80 IUCLC = 0x1000 IXOFF = 0x400 @@ -362,6 +364,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_riscv64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_riscv64.go index 38ba81c55c1..848e5fcc42e 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_riscv64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_riscv64.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xffffff0f + IPV6_FLOWLABEL_MASK = 0xffff0f00 ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -294,6 +296,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_s390x.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_s390x.go index 71f0400977b..669b2adb80b 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_s390x.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_s390x.go @@ -115,6 +115,8 @@ const ( IN_CLOEXEC = 0x80000 IN_NONBLOCK = 0x800 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x7b9 + IPV6_FLOWINFO_MASK = 0xfffffff + IPV6_FLOWLABEL_MASK = 0xfffff ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -366,6 +368,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x36 SCM_TIMESTAMPING_PKTINFO = 0x3a SCM_TIMESTAMPNS = 0x23 + SCM_TS_OPT_ID = 0x51 SCM_TXTIME = 0x3d SCM_WIFI_STATUS = 0x29 SECCOMP_IOCTL_NOTIF_ADDFD = 0x40182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_sparc64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_sparc64.go index c44a313322c..4834e57514e 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_sparc64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zerrors_linux_sparc64.go @@ -119,6 +119,8 @@ const ( IN_CLOEXEC = 0x400000 IN_NONBLOCK = 0x4000 IOCTL_VM_SOCKETS_GET_LOCAL_CID = 0x200007b9 + IPV6_FLOWINFO_MASK = 0xfffffff + IPV6_FLOWLABEL_MASK = 0xfffff ISIG = 0x1 IUCLC = 0x200 IXOFF = 0x1000 @@ -357,6 +359,7 @@ const ( SCM_TIMESTAMPING_OPT_STATS = 0x38 SCM_TIMESTAMPING_PKTINFO = 0x3c SCM_TIMESTAMPNS = 0x21 + SCM_TS_OPT_ID = 0x5a SCM_TXTIME = 0x3f SCM_WIFI_STATUS = 0x25 SECCOMP_IOCTL_NOTIF_ADDFD = 0x80182103 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.go index 24b346e1a35..813c05b6647 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.go @@ -2512,6 +2512,90 @@ var libc_munmap_trampoline_addr uintptr // THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT +func readv(fd int, iovecs []Iovec) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall(libc_readv_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs))) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_readv_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_readv readv "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func preadv(fd int, iovecs []Iovec, offset int64) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall6(libc_preadv_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs)), uintptr(offset), 0, 0) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_preadv_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_preadv preadv "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func writev(fd int, iovecs []Iovec) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall(libc_writev_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs))) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_writev_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_writev writev "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func pwritev(fd int, iovecs []Iovec, offset int64) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall6(libc_pwritev_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs)), uintptr(offset), 0, 0) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_pwritev_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_pwritev pwritev "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + func Fstat(fd int, stat *Stat_t) (err error) { _, _, e1 := syscall_syscall(libc_fstat64_trampoline_addr, uintptr(fd), uintptr(unsafe.Pointer(stat)), 0) if e1 != 0 { diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.s b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.s index ebd213100b3..fda328582b2 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.s +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_amd64.s @@ -738,6 +738,26 @@ TEXT libc_munmap_trampoline<>(SB),NOSPLIT,$0-0 GLOBL ·libc_munmap_trampoline_addr(SB), RODATA, $8 DATA ·libc_munmap_trampoline_addr(SB)/8, $libc_munmap_trampoline<>(SB) +TEXT libc_readv_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_readv(SB) +GLOBL ·libc_readv_trampoline_addr(SB), RODATA, $8 +DATA ·libc_readv_trampoline_addr(SB)/8, $libc_readv_trampoline<>(SB) + +TEXT libc_preadv_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_preadv(SB) +GLOBL ·libc_preadv_trampoline_addr(SB), RODATA, $8 +DATA ·libc_preadv_trampoline_addr(SB)/8, $libc_preadv_trampoline<>(SB) + +TEXT libc_writev_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_writev(SB) +GLOBL ·libc_writev_trampoline_addr(SB), RODATA, $8 +DATA ·libc_writev_trampoline_addr(SB)/8, $libc_writev_trampoline<>(SB) + +TEXT libc_pwritev_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_pwritev(SB) +GLOBL ·libc_pwritev_trampoline_addr(SB), RODATA, $8 +DATA ·libc_pwritev_trampoline_addr(SB)/8, $libc_pwritev_trampoline<>(SB) + TEXT libc_fstat64_trampoline<>(SB),NOSPLIT,$0-0 JMP libc_fstat64(SB) GLOBL ·libc_fstat64_trampoline_addr(SB), RODATA, $8 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.go index 824b9c2d5e0..e6f58f3c6f4 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.go @@ -2512,6 +2512,90 @@ var libc_munmap_trampoline_addr uintptr // THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT +func readv(fd int, iovecs []Iovec) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall(libc_readv_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs))) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_readv_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_readv readv "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func preadv(fd int, iovecs []Iovec, offset int64) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall6(libc_preadv_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs)), uintptr(offset), 0, 0) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_preadv_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_preadv preadv "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func writev(fd int, iovecs []Iovec) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall(libc_writev_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs))) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_writev_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_writev writev "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func pwritev(fd int, iovecs []Iovec, offset int64) (n int, err error) { + var _p0 unsafe.Pointer + if len(iovecs) > 0 { + _p0 = unsafe.Pointer(&iovecs[0]) + } else { + _p0 = unsafe.Pointer(&_zero) + } + r0, _, e1 := syscall_syscall6(libc_pwritev_trampoline_addr, uintptr(fd), uintptr(_p0), uintptr(len(iovecs)), uintptr(offset), 0, 0) + n = int(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +var libc_pwritev_trampoline_addr uintptr + +//go:cgo_import_dynamic libc_pwritev pwritev "/usr/lib/libSystem.B.dylib" + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + func Fstat(fd int, stat *Stat_t) (err error) { _, _, e1 := syscall_syscall(libc_fstat_trampoline_addr, uintptr(fd), uintptr(unsafe.Pointer(stat)), 0) if e1 != 0 { diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.s b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.s index 4f178a22934..7f8998b905b 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.s +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_darwin_arm64.s @@ -738,6 +738,26 @@ TEXT libc_munmap_trampoline<>(SB),NOSPLIT,$0-0 GLOBL ·libc_munmap_trampoline_addr(SB), RODATA, $8 DATA ·libc_munmap_trampoline_addr(SB)/8, $libc_munmap_trampoline<>(SB) +TEXT libc_readv_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_readv(SB) +GLOBL ·libc_readv_trampoline_addr(SB), RODATA, $8 +DATA ·libc_readv_trampoline_addr(SB)/8, $libc_readv_trampoline<>(SB) + +TEXT libc_preadv_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_preadv(SB) +GLOBL ·libc_preadv_trampoline_addr(SB), RODATA, $8 +DATA ·libc_preadv_trampoline_addr(SB)/8, $libc_preadv_trampoline<>(SB) + +TEXT libc_writev_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_writev(SB) +GLOBL ·libc_writev_trampoline_addr(SB), RODATA, $8 +DATA ·libc_writev_trampoline_addr(SB)/8, $libc_writev_trampoline<>(SB) + +TEXT libc_pwritev_trampoline<>(SB),NOSPLIT,$0-0 + JMP libc_pwritev(SB) +GLOBL ·libc_pwritev_trampoline_addr(SB), RODATA, $8 +DATA ·libc_pwritev_trampoline_addr(SB)/8, $libc_pwritev_trampoline<>(SB) + TEXT libc_fstat_trampoline<>(SB),NOSPLIT,$0-0 JMP libc_fstat(SB) GLOBL ·libc_fstat_trampoline_addr(SB), RODATA, $8 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_solaris_amd64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_solaris_amd64.go index 829b87feb8d..c6545413c45 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_solaris_amd64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsyscall_solaris_amd64.go @@ -141,6 +141,16 @@ import ( //go:cgo_import_dynamic libc_getpeername getpeername "libsocket.so" //go:cgo_import_dynamic libc_setsockopt setsockopt "libsocket.so" //go:cgo_import_dynamic libc_recvfrom recvfrom "libsocket.so" +//go:cgo_import_dynamic libc_getpeerucred getpeerucred "libc.so" +//go:cgo_import_dynamic libc_ucred_get ucred_get "libc.so" +//go:cgo_import_dynamic libc_ucred_geteuid ucred_geteuid "libc.so" +//go:cgo_import_dynamic libc_ucred_getegid ucred_getegid "libc.so" +//go:cgo_import_dynamic libc_ucred_getruid ucred_getruid "libc.so" +//go:cgo_import_dynamic libc_ucred_getrgid ucred_getrgid "libc.so" +//go:cgo_import_dynamic libc_ucred_getsuid ucred_getsuid "libc.so" +//go:cgo_import_dynamic libc_ucred_getsgid ucred_getsgid "libc.so" +//go:cgo_import_dynamic libc_ucred_getpid ucred_getpid "libc.so" +//go:cgo_import_dynamic libc_ucred_free ucred_free "libc.so" //go:cgo_import_dynamic libc_port_create port_create "libc.so" //go:cgo_import_dynamic libc_port_associate port_associate "libc.so" //go:cgo_import_dynamic libc_port_dissociate port_dissociate "libc.so" @@ -280,6 +290,16 @@ import ( //go:linkname procgetpeername libc_getpeername //go:linkname procsetsockopt libc_setsockopt //go:linkname procrecvfrom libc_recvfrom +//go:linkname procgetpeerucred libc_getpeerucred +//go:linkname procucred_get libc_ucred_get +//go:linkname procucred_geteuid libc_ucred_geteuid +//go:linkname procucred_getegid libc_ucred_getegid +//go:linkname procucred_getruid libc_ucred_getruid +//go:linkname procucred_getrgid libc_ucred_getrgid +//go:linkname procucred_getsuid libc_ucred_getsuid +//go:linkname procucred_getsgid libc_ucred_getsgid +//go:linkname procucred_getpid libc_ucred_getpid +//go:linkname procucred_free libc_ucred_free //go:linkname procport_create libc_port_create //go:linkname procport_associate libc_port_associate //go:linkname procport_dissociate libc_port_dissociate @@ -420,6 +440,16 @@ var ( procgetpeername, procsetsockopt, procrecvfrom, + procgetpeerucred, + procucred_get, + procucred_geteuid, + procucred_getegid, + procucred_getruid, + procucred_getrgid, + procucred_getsuid, + procucred_getsgid, + procucred_getpid, + procucred_free, procport_create, procport_associate, procport_dissociate, @@ -2029,6 +2059,90 @@ func recvfrom(fd int, p []byte, flags int, from *RawSockaddrAny, fromlen *_Sockl // THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT +func getpeerucred(fd uintptr, ucred *uintptr) (err error) { + _, _, e1 := sysvicall6(uintptr(unsafe.Pointer(&procgetpeerucred)), 2, uintptr(fd), uintptr(unsafe.Pointer(ucred)), 0, 0, 0, 0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGet(pid int) (ucred uintptr, err error) { + r0, _, e1 := sysvicall6(uintptr(unsafe.Pointer(&procucred_get)), 1, uintptr(pid), 0, 0, 0, 0, 0) + ucred = uintptr(r0) + if e1 != 0 { + err = errnoErr(e1) + } + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGeteuid(ucred uintptr) (uid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_geteuid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + uid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGetegid(ucred uintptr) (gid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_getegid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + gid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGetruid(ucred uintptr) (uid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_getruid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + uid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGetrgid(ucred uintptr) (gid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_getrgid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + gid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGetsuid(ucred uintptr) (uid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_getsuid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + uid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGetsgid(ucred uintptr) (gid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_getsgid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + gid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredGetpid(ucred uintptr) (pid int) { + r0, _, _ := sysvicall6(uintptr(unsafe.Pointer(&procucred_getpid)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + pid = int(r0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + +func ucredFree(ucred uintptr) { + sysvicall6(uintptr(unsafe.Pointer(&procucred_free)), 1, uintptr(ucred), 0, 0, 0, 0, 0) + return +} + +// THIS FILE IS GENERATED BY THE COMMAND AT THE TOP; DO NOT EDIT + func port_create() (n int, err error) { r0, _, e1 := sysvicall6(uintptr(unsafe.Pointer(&procport_create)), 0, 0, 0, 0, 0, 0, 0) n = int(r0) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_386.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_386.go index 524b0820cbc..c79aaff306a 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_386.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_386.go @@ -458,4 +458,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_amd64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_amd64.go index f485dbf4565..5eb450695e9 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_amd64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_amd64.go @@ -381,4 +381,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm.go index 70b35bf3b09..05e50297445 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm.go @@ -422,4 +422,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm64.go index 1893e2fe884..38c53ec51bb 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_arm64.go @@ -325,4 +325,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_loong64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_loong64.go index 16a4017da0a..31d2e71a18e 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_loong64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_loong64.go @@ -321,4 +321,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips.go index 7e567f1efff..f4184a336b0 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips.go @@ -442,4 +442,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 4460 SYS_LSM_LIST_MODULES = 4461 SYS_MSEAL = 4462 + SYS_SETXATTRAT = 4463 + SYS_GETXATTRAT = 4464 + SYS_LISTXATTRAT = 4465 + SYS_REMOVEXATTRAT = 4466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64.go index 38ae55e5ef8..05b9962278f 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64.go @@ -372,4 +372,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 5460 SYS_LSM_LIST_MODULES = 5461 SYS_MSEAL = 5462 + SYS_SETXATTRAT = 5463 + SYS_GETXATTRAT = 5464 + SYS_LISTXATTRAT = 5465 + SYS_REMOVEXATTRAT = 5466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64le.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64le.go index 55e92e60a82..43a256e9e67 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64le.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mips64le.go @@ -372,4 +372,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 5460 SYS_LSM_LIST_MODULES = 5461 SYS_MSEAL = 5462 + SYS_SETXATTRAT = 5463 + SYS_GETXATTRAT = 5464 + SYS_LISTXATTRAT = 5465 + SYS_REMOVEXATTRAT = 5466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mipsle.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mipsle.go index 60658d6a021..eea5ddfc220 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mipsle.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_mipsle.go @@ -442,4 +442,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 4460 SYS_LSM_LIST_MODULES = 4461 SYS_MSEAL = 4462 + SYS_SETXATTRAT = 4463 + SYS_GETXATTRAT = 4464 + SYS_LISTXATTRAT = 4465 + SYS_REMOVEXATTRAT = 4466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc.go index e203e8a7ed4..0d777bfbb14 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc.go @@ -449,4 +449,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64.go index 5944b97d546..b4463650256 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64.go @@ -421,4 +421,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64le.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64le.go index c66d416dad1..0c7d21c1881 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64le.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_ppc64le.go @@ -421,4 +421,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_riscv64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_riscv64.go index a5459e766f5..84053916987 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_riscv64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_riscv64.go @@ -326,4 +326,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_s390x.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_s390x.go index 01d86825bb9..fcf1b790d6c 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_s390x.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_s390x.go @@ -387,4 +387,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_sparc64.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_sparc64.go index 7b703e77cda..52d15b5f9d4 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_sparc64.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/zsysnum_linux_sparc64.go @@ -400,4 +400,8 @@ const ( SYS_LSM_SET_SELF_ATTR = 460 SYS_LSM_LIST_MODULES = 461 SYS_MSEAL = 462 + SYS_SETXATTRAT = 463 + SYS_GETXATTRAT = 464 + SYS_LISTXATTRAT = 465 + SYS_REMOVEXATTRAT = 466 ) diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/ztypes_linux.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/ztypes_linux.go index 5537148dcbb..a46abe64720 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/ztypes_linux.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/unix/ztypes_linux.go @@ -4747,7 +4747,7 @@ const ( NL80211_ATTR_MAC_HINT = 0xc8 NL80211_ATTR_MAC_MASK = 0xd7 NL80211_ATTR_MAX_AP_ASSOC_STA = 0xca - NL80211_ATTR_MAX = 0x14c + NL80211_ATTR_MAX = 0x14d NL80211_ATTR_MAX_CRIT_PROT_DURATION = 0xb4 NL80211_ATTR_MAX_CSA_COUNTERS = 0xce NL80211_ATTR_MAX_MATCH_SETS = 0x85 @@ -5519,7 +5519,7 @@ const ( NL80211_MNTR_FLAG_CONTROL = 0x3 NL80211_MNTR_FLAG_COOK_FRAMES = 0x5 NL80211_MNTR_FLAG_FCSFAIL = 0x1 - NL80211_MNTR_FLAG_MAX = 0x6 + NL80211_MNTR_FLAG_MAX = 0x7 NL80211_MNTR_FLAG_OTHER_BSS = 0x4 NL80211_MNTR_FLAG_PLCPFAIL = 0x2 NL80211_MPATH_FLAG_ACTIVE = 0x1 @@ -6174,3 +6174,5 @@ type SockDiagReq struct { Family uint8 Protocol uint8 } + +const RTM_NEWNVLAN = 0x70 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/key.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/key.go index fd8632444ec..39aeeb644f5 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/key.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/key.go @@ -164,7 +164,12 @@ loopItems: func CreateKey(k Key, path string, access uint32) (newk Key, openedExisting bool, err error) { var h syscall.Handle var d uint32 - err = regCreateKeyEx(syscall.Handle(k), syscall.StringToUTF16Ptr(path), + var pathPointer *uint16 + pathPointer, err = syscall.UTF16PtrFromString(path) + if err != nil { + return 0, false, err + } + err = regCreateKeyEx(syscall.Handle(k), pathPointer, 0, nil, _REG_OPTION_NON_VOLATILE, access, nil, &h, &d) if err != nil { return 0, false, err @@ -174,7 +179,11 @@ func CreateKey(k Key, path string, access uint32) (newk Key, openedExisting bool // DeleteKey deletes the subkey path of key k and its values. func DeleteKey(k Key, path string) error { - return regDeleteKey(syscall.Handle(k), syscall.StringToUTF16Ptr(path)) + pathPointer, err := syscall.UTF16PtrFromString(path) + if err != nil { + return err + } + return regDeleteKey(syscall.Handle(k), pathPointer) } // A KeyInfo describes the statistics of a key. It is returned by Stat. diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/value.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/value.go index 74db26b94df..a1bcbb2362c 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/value.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/registry/value.go @@ -340,7 +340,11 @@ func (k Key) SetBinaryValue(name string, value []byte) error { // DeleteValue removes a named value from the key k. func (k Key) DeleteValue(name string) error { - return regDeleteValue(syscall.Handle(k), syscall.StringToUTF16Ptr(name)) + namePointer, err := syscall.UTF16PtrFromString(name) + if err != nil { + return err + } + return regDeleteValue(syscall.Handle(k), namePointer) } // ReadValueNames returns the value names of key k. diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/types_windows.go b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/types_windows.go index 9d138de5fed..ad67df2fdb6 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/types_windows.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/sys/windows/types_windows.go @@ -1074,6 +1074,7 @@ const ( IP_ADD_MEMBERSHIP = 0xc IP_DROP_MEMBERSHIP = 0xd IP_PKTINFO = 0x13 + IP_MTU_DISCOVER = 0x47 IPV6_V6ONLY = 0x1b IPV6_UNICAST_HOPS = 0x4 @@ -1083,6 +1084,7 @@ const ( IPV6_JOIN_GROUP = 0xc IPV6_LEAVE_GROUP = 0xd IPV6_PKTINFO = 0x13 + IPV6_MTU_DISCOVER = 0x47 MSG_OOB = 0x1 MSG_PEEK = 0x2 @@ -1132,6 +1134,15 @@ const ( WSASYS_STATUS_LEN = 128 ) +// enum PMTUD_STATE from ws2ipdef.h +const ( + IP_PMTUDISC_NOT_SET = 0 + IP_PMTUDISC_DO = 1 + IP_PMTUDISC_DONT = 2 + IP_PMTUDISC_PROBE = 3 + IP_PMTUDISC_MAX = 4 +) + type WSABuf struct { Len uint32 Buf *byte @@ -1146,6 +1157,22 @@ type WSAMsg struct { Flags uint32 } +type WSACMSGHDR struct { + Len uintptr + Level int32 + Type int32 +} + +type IN_PKTINFO struct { + Addr [4]byte + Ifindex uint32 +} + +type IN6_PKTINFO struct { + Addr [16]byte + Ifindex uint32 +} + // Flags for WSASocket const ( WSA_FLAG_OVERLAPPED = 0x01 diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/text/internal/number/format.go b/cluster-api/providers/vsphere/vendor/golang.org/x/text/internal/number/format.go index cd94c5dc4e6..1aadcf40777 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/text/internal/number/format.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/text/internal/number/format.go @@ -394,9 +394,7 @@ func appendScientific(dst []byte, f *Formatter, n *Digits) (b []byte, postPre, p exp := n.Exp - int32(n.Comma) exponential := f.Symbol(SymExponential) if exponential == "E" { - dst = append(dst, "\u202f"...) // NARROW NO-BREAK SPACE dst = append(dst, f.Symbol(SymSuperscriptingExponent)...) - dst = append(dst, "\u202f"...) // NARROW NO-BREAK SPACE dst = f.AppendDigit(dst, 1) dst = f.AppendDigit(dst, 0) switch { diff --git a/cluster-api/providers/vsphere/vendor/golang.org/x/text/language/parse.go b/cluster-api/providers/vsphere/vendor/golang.org/x/text/language/parse.go index 4d57222e770..053336e2866 100644 --- a/cluster-api/providers/vsphere/vendor/golang.org/x/text/language/parse.go +++ b/cluster-api/providers/vsphere/vendor/golang.org/x/text/language/parse.go @@ -59,7 +59,7 @@ func (c CanonType) Parse(s string) (t Tag, err error) { if changed { tt.RemakeString() } - return makeTag(tt), err + return makeTag(tt), nil } // Compose creates a Tag from individual parts, which may be of type Tag, Base, diff --git a/cluster-api/providers/vsphere/vendor/gomodules.xyz/jsonpatch/v2/jsonpatch.go b/cluster-api/providers/vsphere/vendor/gomodules.xyz/jsonpatch/v2/jsonpatch.go index 0d7823b3cd6..d88162ff578 100644 --- a/cluster-api/providers/vsphere/vendor/gomodules.xyz/jsonpatch/v2/jsonpatch.go +++ b/cluster-api/providers/vsphere/vendor/gomodules.xyz/jsonpatch/v2/jsonpatch.go @@ -70,12 +70,14 @@ func CreatePatch(a, b []byte) ([]Operation, error) { } var aI interface{} var bI interface{} - err := json.Unmarshal(a, &aI) - if err != nil { + aDec := json.NewDecoder(bytes.NewReader(a)) + aDec.UseNumber() + if err := aDec.Decode(&aI); err != nil { return nil, errBadJSONDoc } - err = json.Unmarshal(b, &bI) - if err != nil { + bDec := json.NewDecoder(bytes.NewReader(b)) + bDec.UseNumber() + if err := bDec.Decode(&bI); err != nil { return nil, errBadJSONDoc } return handleValues(aI, bI, "", []Operation{}) @@ -94,6 +96,11 @@ func matchesValue(av, bv interface{}) bool { if ok && bt == at { return true } + case json.Number: + bt, ok := bv.(json.Number) + if ok && bt == at { + return true + } case float64: bt, ok := bv.(float64) if ok && bt == at { @@ -212,7 +219,7 @@ func handleValues(av, bv interface{}, p string, patch []Operation) ([]Operation, if err != nil { return nil, err } - case string, float64, bool: + case string, float64, bool, json.Number: if !matchesValue(av, bv) { patch = append(patch, NewOperation("replace", p, bv)) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/api/httpbody/httpbody.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/api/httpbody/httpbody.pb.go index e7d3805e365..f388426b08f 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/api/httpbody/httpbody.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/api/httpbody/httpbody.pb.go @@ -159,14 +159,14 @@ var file_google_api_httpbody_proto_rawDesc = []byte{ 0x04, 0x64, 0x61, 0x74, 0x61, 0x12, 0x34, 0x0a, 0x0a, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x03, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x14, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x41, 0x6e, 0x79, 0x52, - 0x0a, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x42, 0x68, 0x0a, 0x0e, 0x63, + 0x0a, 0x65, 0x78, 0x74, 0x65, 0x6e, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x42, 0x65, 0x0a, 0x0e, 0x63, 0x6f, 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x61, 0x70, 0x69, 0x42, 0x0d, 0x48, 0x74, 0x74, 0x70, 0x42, 0x6f, 0x64, 0x79, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3b, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, 0x6e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, 0x73, 0x2f, 0x61, 0x70, 0x69, 0x2f, 0x68, 0x74, 0x74, 0x70, 0x62, 0x6f, - 0x64, 0x79, 0x3b, 0x68, 0x74, 0x74, 0x70, 0x62, 0x6f, 0x64, 0x79, 0xf8, 0x01, 0x01, 0xa2, 0x02, - 0x04, 0x47, 0x41, 0x50, 0x49, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x64, 0x79, 0x3b, 0x68, 0x74, 0x74, 0x70, 0x62, 0x6f, 0x64, 0x79, 0xa2, 0x02, 0x04, 0x47, 0x41, + 0x50, 0x49, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, } var ( diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/rpc/errdetails/error_details.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/rpc/errdetails/error_details.pb.go index 3e562182792..3cd9a5bb8e6 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/rpc/errdetails/error_details.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/genproto/googleapis/rpc/errdetails/error_details.pb.go @@ -80,11 +80,12 @@ type ErrorInfo struct { Domain string `protobuf:"bytes,2,opt,name=domain,proto3" json:"domain,omitempty"` // Additional structured details about this error. // - // Keys should match /[a-zA-Z0-9-_]/ and be limited to 64 characters in + // Keys must match a regular expression of `[a-z][a-zA-Z0-9-_]+` but should + // ideally be lowerCamelCase. Also, they must be limited to 64 characters in // length. When identifying the current value of an exceeded limit, the units // should be contained in the key, not the value. For example, rather than - // {"instanceLimit": "100/request"}, should be returned as, - // {"instanceLimitPerRequest": "100"}, if the client exceeds the number of + // `{"instanceLimit": "100/request"}`, should be returned as, + // `{"instanceLimitPerRequest": "100"}`, if the client exceeds the number of // instances that can be created in a single (batch) request. Metadata map[string]string `protobuf:"bytes,3,rep,name=metadata,proto3" json:"metadata,omitempty" protobuf_key:"bytes,1,opt,name=key,proto3" protobuf_val:"bytes,2,opt,name=value,proto3"` } @@ -870,6 +871,16 @@ type BadRequest_FieldViolation struct { Field string `protobuf:"bytes,1,opt,name=field,proto3" json:"field,omitempty"` // A description of why the request element is bad. Description string `protobuf:"bytes,2,opt,name=description,proto3" json:"description,omitempty"` + // The reason of the field-level error. This is a constant value that + // identifies the proximate cause of the field-level error. It should + // uniquely identify the type of the FieldViolation within the scope of the + // google.rpc.ErrorInfo.domain. This should be at most 63 + // characters and match a regular expression of `[A-Z][A-Z0-9_]+[A-Z0-9]`, + // which represents UPPER_SNAKE_CASE. + Reason string `protobuf:"bytes,3,opt,name=reason,proto3" json:"reason,omitempty"` + // Provides a localized error message for field-level errors that is safe to + // return to the API consumer. + LocalizedMessage *LocalizedMessage `protobuf:"bytes,4,opt,name=localized_message,json=localizedMessage,proto3" json:"localized_message,omitempty"` } func (x *BadRequest_FieldViolation) Reset() { @@ -918,6 +929,20 @@ func (x *BadRequest_FieldViolation) GetDescription() string { return "" } +func (x *BadRequest_FieldViolation) GetReason() string { + if x != nil { + return x.Reason + } + return "" +} + +func (x *BadRequest_FieldViolation) GetLocalizedMessage() *LocalizedMessage { + if x != nil { + return x.LocalizedMessage + } + return nil +} + // Describes a URL link. type Help_Link struct { state protoimpl.MessageState @@ -1026,51 +1051,57 @@ var file_google_rpc_error_details_proto_rawDesc = []byte{ 0x07, 0x73, 0x75, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x73, 0x75, 0x62, 0x6a, 0x65, 0x63, 0x74, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, - 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0xa8, 0x01, 0x0a, 0x0a, 0x42, 0x61, + 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x8c, 0x02, 0x0a, 0x0a, 0x42, 0x61, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x50, 0x0a, 0x10, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x5f, 0x76, 0x69, 0x6f, 0x6c, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x25, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x72, 0x70, 0x63, 0x2e, 0x42, 0x61, 0x64, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x2e, 0x46, 0x69, 0x65, 0x6c, 0x64, 0x56, 0x69, 0x6f, 0x6c, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x0f, 0x66, 0x69, 0x65, 0x6c, 0x64, - 0x56, 0x69, 0x6f, 0x6c, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x1a, 0x48, 0x0a, 0x0e, 0x46, 0x69, - 0x65, 0x6c, 0x64, 0x56, 0x69, 0x6f, 0x6c, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x14, 0x0a, 0x05, - 0x66, 0x69, 0x65, 0x6c, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x66, 0x69, 0x65, - 0x6c, 0x64, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, - 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, - 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x4f, 0x0a, 0x0b, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x49, - 0x6e, 0x66, 0x6f, 0x12, 0x1d, 0x0a, 0x0a, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x5f, 0x69, - 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x72, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, - 0x49, 0x64, 0x12, 0x21, 0x0a, 0x0c, 0x73, 0x65, 0x72, 0x76, 0x69, 0x6e, 0x67, 0x5f, 0x64, 0x61, - 0x74, 0x61, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x73, 0x65, 0x72, 0x76, 0x69, 0x6e, - 0x67, 0x44, 0x61, 0x74, 0x61, 0x22, 0x90, 0x01, 0x0a, 0x0c, 0x52, 0x65, 0x73, 0x6f, 0x75, 0x72, - 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x23, 0x0a, 0x0d, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, - 0x63, 0x65, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x72, - 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, 0x23, 0x0a, 0x0d, 0x72, - 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x02, 0x20, 0x01, - 0x28, 0x09, 0x52, 0x0c, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x4e, 0x61, 0x6d, 0x65, - 0x12, 0x14, 0x0a, 0x05, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, - 0x05, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, - 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, - 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x6f, 0x0a, 0x04, 0x48, 0x65, 0x6c, 0x70, - 0x12, 0x2b, 0x0a, 0x05, 0x6c, 0x69, 0x6e, 0x6b, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, - 0x15, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x72, 0x70, 0x63, 0x2e, 0x48, 0x65, 0x6c, - 0x70, 0x2e, 0x4c, 0x69, 0x6e, 0x6b, 0x52, 0x05, 0x6c, 0x69, 0x6e, 0x6b, 0x73, 0x1a, 0x3a, 0x0a, - 0x04, 0x4c, 0x69, 0x6e, 0x6b, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, - 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, - 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x10, 0x0a, 0x03, 0x75, 0x72, 0x6c, 0x18, 0x02, - 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x22, 0x44, 0x0a, 0x10, 0x4c, 0x6f, 0x63, - 0x61, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x12, 0x16, 0x0a, - 0x06, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x6c, - 0x6f, 0x63, 0x61, 0x6c, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, - 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x42, - 0x6c, 0x0a, 0x0e, 0x63, 0x6f, 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x72, 0x70, - 0x63, 0x42, 0x11, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x44, 0x65, 0x74, 0x61, 0x69, 0x6c, 0x73, 0x50, - 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x67, - 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, 0x6e, 0x70, 0x72, 0x6f, - 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, 0x73, 0x2f, 0x72, 0x70, - 0x63, 0x2f, 0x65, 0x72, 0x72, 0x64, 0x65, 0x74, 0x61, 0x69, 0x6c, 0x73, 0x3b, 0x65, 0x72, 0x72, - 0x64, 0x65, 0x74, 0x61, 0x69, 0x6c, 0x73, 0xa2, 0x02, 0x03, 0x52, 0x50, 0x43, 0x62, 0x06, 0x70, - 0x72, 0x6f, 0x74, 0x6f, 0x33, + 0x56, 0x69, 0x6f, 0x6c, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x73, 0x1a, 0xab, 0x01, 0x0a, 0x0e, 0x46, + 0x69, 0x65, 0x6c, 0x64, 0x56, 0x69, 0x6f, 0x6c, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x14, 0x0a, + 0x05, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x05, 0x66, 0x69, + 0x65, 0x6c, 0x64, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, + 0x6f, 0x6e, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, + 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x16, 0x0a, 0x06, 0x72, 0x65, 0x61, 0x73, 0x6f, 0x6e, 0x18, + 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x72, 0x65, 0x61, 0x73, 0x6f, 0x6e, 0x12, 0x49, 0x0a, + 0x11, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x5f, 0x6d, 0x65, 0x73, 0x73, 0x61, + 0x67, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, + 0x65, 0x2e, 0x72, 0x70, 0x63, 0x2e, 0x4c, 0x6f, 0x63, 0x61, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x4d, + 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x52, 0x10, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x69, 0x7a, 0x65, + 0x64, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, 0x65, 0x22, 0x4f, 0x0a, 0x0b, 0x52, 0x65, 0x71, 0x75, + 0x65, 0x73, 0x74, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x1d, 0x0a, 0x0a, 0x72, 0x65, 0x71, 0x75, 0x65, + 0x73, 0x74, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x72, 0x65, 0x71, + 0x75, 0x65, 0x73, 0x74, 0x49, 0x64, 0x12, 0x21, 0x0a, 0x0c, 0x73, 0x65, 0x72, 0x76, 0x69, 0x6e, + 0x67, 0x5f, 0x64, 0x61, 0x74, 0x61, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x73, 0x65, + 0x72, 0x76, 0x69, 0x6e, 0x67, 0x44, 0x61, 0x74, 0x61, 0x22, 0x90, 0x01, 0x0a, 0x0c, 0x52, 0x65, + 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x49, 0x6e, 0x66, 0x6f, 0x12, 0x23, 0x0a, 0x0d, 0x72, 0x65, + 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x5f, 0x74, 0x79, 0x70, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x0c, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x54, 0x79, 0x70, 0x65, 0x12, + 0x23, 0x0a, 0x0d, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, 0x5f, 0x6e, 0x61, 0x6d, 0x65, + 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x72, 0x65, 0x73, 0x6f, 0x75, 0x72, 0x63, 0x65, + 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x14, 0x0a, 0x05, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x18, 0x03, 0x20, + 0x01, 0x28, 0x09, 0x52, 0x05, 0x6f, 0x77, 0x6e, 0x65, 0x72, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, + 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, + 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x6f, 0x0a, 0x04, + 0x48, 0x65, 0x6c, 0x70, 0x12, 0x2b, 0x0a, 0x05, 0x6c, 0x69, 0x6e, 0x6b, 0x73, 0x18, 0x01, 0x20, + 0x03, 0x28, 0x0b, 0x32, 0x15, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x72, 0x70, 0x63, + 0x2e, 0x48, 0x65, 0x6c, 0x70, 0x2e, 0x4c, 0x69, 0x6e, 0x6b, 0x52, 0x05, 0x6c, 0x69, 0x6e, 0x6b, + 0x73, 0x1a, 0x3a, 0x0a, 0x04, 0x4c, 0x69, 0x6e, 0x6b, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, + 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, + 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x10, 0x0a, 0x03, 0x75, + 0x72, 0x6c, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x03, 0x75, 0x72, 0x6c, 0x22, 0x44, 0x0a, + 0x10, 0x4c, 0x6f, 0x63, 0x61, 0x6c, 0x69, 0x7a, 0x65, 0x64, 0x4d, 0x65, 0x73, 0x73, 0x61, 0x67, + 0x65, 0x12, 0x16, 0x0a, 0x06, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x65, 0x18, 0x01, 0x20, 0x01, 0x28, + 0x09, 0x52, 0x06, 0x6c, 0x6f, 0x63, 0x61, 0x6c, 0x65, 0x12, 0x18, 0x0a, 0x07, 0x6d, 0x65, 0x73, + 0x73, 0x61, 0x67, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x6d, 0x65, 0x73, 0x73, + 0x61, 0x67, 0x65, 0x42, 0x6c, 0x0a, 0x0e, 0x63, 0x6f, 0x6d, 0x2e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, + 0x65, 0x2e, 0x72, 0x70, 0x63, 0x42, 0x11, 0x45, 0x72, 0x72, 0x6f, 0x72, 0x44, 0x65, 0x74, 0x61, + 0x69, 0x6c, 0x73, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x50, 0x01, 0x5a, 0x3f, 0x67, 0x6f, 0x6f, 0x67, + 0x6c, 0x65, 0x2e, 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x67, 0x65, + 0x6e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x2f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x61, 0x70, 0x69, + 0x73, 0x2f, 0x72, 0x70, 0x63, 0x2f, 0x65, 0x72, 0x72, 0x64, 0x65, 0x74, 0x61, 0x69, 0x6c, 0x73, + 0x3b, 0x65, 0x72, 0x72, 0x64, 0x65, 0x74, 0x61, 0x69, 0x6c, 0x73, 0xa2, 0x02, 0x03, 0x52, 0x50, + 0x43, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, } var ( @@ -1111,11 +1142,12 @@ var file_google_rpc_error_details_proto_depIdxs = []int32{ 12, // 3: google.rpc.PreconditionFailure.violations:type_name -> google.rpc.PreconditionFailure.Violation 13, // 4: google.rpc.BadRequest.field_violations:type_name -> google.rpc.BadRequest.FieldViolation 14, // 5: google.rpc.Help.links:type_name -> google.rpc.Help.Link - 6, // [6:6] is the sub-list for method output_type - 6, // [6:6] is the sub-list for method input_type - 6, // [6:6] is the sub-list for extension type_name - 6, // [6:6] is the sub-list for extension extendee - 0, // [0:6] is the sub-list for field type_name + 9, // 6: google.rpc.BadRequest.FieldViolation.localized_message:type_name -> google.rpc.LocalizedMessage + 7, // [7:7] is the sub-list for method output_type + 7, // [7:7] is the sub-list for method input_type + 7, // [7:7] is the sub-list for extension type_name + 7, // [7:7] is the sub-list for extension extendee + 0, // [0:7] is the sub-list for field type_name } func init() { file_google_rpc_error_details_proto_init() } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/MAINTAINERS.md b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/MAINTAINERS.md index 6a8a07781ae..5d4096d46a0 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/MAINTAINERS.md +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/MAINTAINERS.md @@ -9,21 +9,28 @@ for general contribution guidelines. ## Maintainers (in alphabetical order) +- [aranjans](https://github.com/aranjans), Google LLC +- [arjan-bal](https://github.com/arjan-bal), Google LLC +- [arvindbr8](https://github.com/arvindbr8), Google LLC - [atollena](https://github.com/atollena), Datadog, Inc. -- [cesarghali](https://github.com/cesarghali), Google LLC - [dfawley](https://github.com/dfawley), Google LLC - [easwars](https://github.com/easwars), Google LLC -- [menghanl](https://github.com/menghanl), Google LLC -- [srini100](https://github.com/srini100), Google LLC +- [erm-g](https://github.com/erm-g), Google LLC +- [gtcooke94](https://github.com/gtcooke94), Google LLC +- [purnesh42h](https://github.com/purnesh42h), Google LLC +- [zasweq](https://github.com/zasweq), Google LLC ## Emeritus Maintainers (in alphabetical order) -- [adelez](https://github.com/adelez), Google LLC -- [canguler](https://github.com/canguler), Google LLC -- [iamqizhao](https://github.com/iamqizhao), Google LLC -- [jadekler](https://github.com/jadekler), Google LLC -- [jtattermusch](https://github.com/jtattermusch), Google LLC -- [lyuxuan](https://github.com/lyuxuan), Google LLC -- [makmukhi](https://github.com/makmukhi), Google LLC -- [matt-kwong](https://github.com/matt-kwong), Google LLC -- [nicolasnoble](https://github.com/nicolasnoble), Google LLC -- [yongni](https://github.com/yongni), Google LLC +- [adelez](https://github.com/adelez) +- [canguler](https://github.com/canguler) +- [cesarghali](https://github.com/cesarghali) +- [iamqizhao](https://github.com/iamqizhao) +- [jeanbza](https://github.com/jeanbza) +- [jtattermusch](https://github.com/jtattermusch) +- [lyuxuan](https://github.com/lyuxuan) +- [makmukhi](https://github.com/makmukhi) +- [matt-kwong](https://github.com/matt-kwong) +- [menghanl](https://github.com/menghanl) +- [nicolasnoble](https://github.com/nicolasnoble) +- [srini100](https://github.com/srini100) +- [yongni](https://github.com/yongni) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/SECURITY.md b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/SECURITY.md index be6e108705c..abab279379b 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/SECURITY.md +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/SECURITY.md @@ -1,3 +1,3 @@ # Security Policy -For information on gRPC Security Policy and reporting potentional security issues, please see [gRPC CVE Process](https://github.com/grpc/proposal/blob/master/P4-grpc-cve-process.md). +For information on gRPC Security Policy and reporting potential security issues, please see [gRPC CVE Process](https://github.com/grpc/proposal/blob/master/P4-grpc-cve-process.md). diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/backoff/backoff.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/backoff/backoff.go index 0787d0b50ce..d7b40b7cb66 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/backoff/backoff.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/backoff/backoff.go @@ -39,7 +39,7 @@ type Config struct { MaxDelay time.Duration } -// DefaultConfig is a backoff configuration with the default values specfied +// DefaultConfig is a backoff configuration with the default values specified // at https://github.com/grpc/grpc/blob/master/doc/connection-backoff.md. // // This should be useful for callers who want to configure backoff with diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/balancer.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/balancer.go index f391744f729..b181f386a1b 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/balancer.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/balancer.go @@ -30,6 +30,7 @@ import ( "google.golang.org/grpc/channelz" "google.golang.org/grpc/connectivity" "google.golang.org/grpc/credentials" + estats "google.golang.org/grpc/experimental/stats" "google.golang.org/grpc/grpclog" "google.golang.org/grpc/internal" "google.golang.org/grpc/metadata" @@ -72,8 +73,21 @@ func unregisterForTesting(name string) { delete(m, name) } +// connectedAddress returns the connected address for a SubConnState. The +// address is only valid if the state is READY. +func connectedAddress(scs SubConnState) resolver.Address { + return scs.connectedAddress +} + +// setConnectedAddress sets the connected address for a SubConnState. +func setConnectedAddress(scs *SubConnState, addr resolver.Address) { + scs.connectedAddress = addr +} + func init() { internal.BalancerUnregister = unregisterForTesting + internal.ConnectedAddress = connectedAddress + internal.SetConnectedAddress = setConnectedAddress } // Get returns the resolver builder registered with the given name. @@ -243,6 +257,10 @@ type BuildOptions struct { // same resolver.Target as passed to the resolver. See the documentation for // the resolver.Target type for details about what it contains. Target resolver.Target + // MetricsRecorder is the metrics recorder that balancers can use to record + // metrics. Balancer implementations which do not register metrics on + // metrics registry and record on them can ignore this field. + MetricsRecorder estats.MetricsRecorder } // Builder creates a balancer. @@ -410,6 +428,9 @@ type SubConnState struct { // ConnectionError is set if the ConnectivityState is TransientFailure, // describing the reason the SubConn failed. Otherwise, it is nil. ConnectionError error + // connectedAddr contains the connected address when ConnectivityState is + // Ready. Otherwise, it is indeterminate. + connectedAddress resolver.Address } // ClientConnState describes the state of a ClientConn relevant to the diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/base/balancer.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/base/balancer.go index a7f1eeec8e6..2b87bd79c75 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/base/balancer.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/base/balancer.go @@ -36,7 +36,7 @@ type baseBuilder struct { config Config } -func (bb *baseBuilder) Build(cc balancer.ClientConn, opt balancer.BuildOptions) balancer.Balancer { +func (bb *baseBuilder) Build(cc balancer.ClientConn, _ balancer.BuildOptions) balancer.Balancer { bal := &baseBalancer{ cc: cc, pickerBuilder: bb.pickerBuilder, @@ -259,6 +259,6 @@ type errPicker struct { err error // Pick() always returns this err. } -func (p *errPicker) Pick(info balancer.PickInfo) (balancer.PickResult, error) { +func (p *errPicker) Pick(balancer.PickInfo) (balancer.PickResult, error) { return balancer.PickResult{}, p.err } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/pickfirst/pickfirst.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/pickfirst/pickfirst.go index 07527603f1d..4d69b4052f8 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/pickfirst/pickfirst.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer/pickfirst/pickfirst.go @@ -50,7 +50,7 @@ const ( type pickfirstBuilder struct{} -func (pickfirstBuilder) Build(cc balancer.ClientConn, opt balancer.BuildOptions) balancer.Balancer { +func (pickfirstBuilder) Build(cc balancer.ClientConn, _ balancer.BuildOptions) balancer.Balancer { b := &pickfirstBalancer{cc: cc} b.logger = internalgrpclog.NewPrefixLogger(logger, fmt.Sprintf(logPrefix, b)) return b @@ -155,7 +155,7 @@ func (b *pickfirstBalancer) UpdateClientConnState(state balancer.ClientConnState // Endpoints not set, process addresses until we migrate resolver // emissions fully to Endpoints. The top channel does wrap emitted // addresses with endpoints, however some balancers such as weighted - // target do not forwarrd the corresponding correct endpoints down/split + // target do not forward the corresponding correct endpoints down/split // endpoints properly. Once all balancers correctly forward endpoints // down, can delete this else conditional. addrs = state.ResolverState.Addresses diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer_wrapper.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer_wrapper.go index 4161fdf47a8..8ad6ce2f095 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer_wrapper.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/balancer_wrapper.go @@ -25,12 +25,15 @@ import ( "google.golang.org/grpc/balancer" "google.golang.org/grpc/connectivity" + "google.golang.org/grpc/internal" "google.golang.org/grpc/internal/balancer/gracefulswitch" "google.golang.org/grpc/internal/channelz" "google.golang.org/grpc/internal/grpcsync" "google.golang.org/grpc/resolver" ) +var setConnectedAddress = internal.SetConnectedAddress.(func(*balancer.SubConnState, resolver.Address)) + // ccBalancerWrapper sits between the ClientConn and the Balancer. // // ccBalancerWrapper implements methods corresponding to the ones on the @@ -79,6 +82,7 @@ func newCCBalancerWrapper(cc *ClientConn) *ccBalancerWrapper { CustomUserAgent: cc.dopts.copts.UserAgent, ChannelzParent: cc.channelz, Target: cc.parsedTarget, + MetricsRecorder: cc.metricsRecorderList, }, serializer: grpcsync.NewCallbackSerializer(ctx), serializerCancel: cancel, @@ -92,7 +96,7 @@ func newCCBalancerWrapper(cc *ClientConn) *ccBalancerWrapper { // it is safe to call into the balancer here. func (ccb *ccBalancerWrapper) updateClientConnState(ccs *balancer.ClientConnState) error { errCh := make(chan error) - ok := ccb.serializer.Schedule(func(ctx context.Context) { + uccs := func(ctx context.Context) { defer close(errCh) if ctx.Err() != nil || ccb.balancer == nil { return @@ -107,17 +111,23 @@ func (ccb *ccBalancerWrapper) updateClientConnState(ccs *balancer.ClientConnStat logger.Infof("error from balancer.UpdateClientConnState: %v", err) } errCh <- err - }) - if !ok { - return nil } + onFailure := func() { close(errCh) } + + // UpdateClientConnState can race with Close, and when the latter wins, the + // serializer is closed, and the attempt to schedule the callback will fail. + // It is acceptable to ignore this failure. But since we want to handle the + // state update in a blocking fashion (when we successfully schedule the + // callback), we have to use the ScheduleOr method and not the MaybeSchedule + // method on the serializer. + ccb.serializer.ScheduleOr(uccs, onFailure) return <-errCh } // resolverError is invoked by grpc to push a resolver error to the underlying // balancer. The call to the balancer is executed from the serializer. func (ccb *ccBalancerWrapper) resolverError(err error) { - ccb.serializer.Schedule(func(ctx context.Context) { + ccb.serializer.TrySchedule(func(ctx context.Context) { if ctx.Err() != nil || ccb.balancer == nil { return } @@ -133,7 +143,7 @@ func (ccb *ccBalancerWrapper) close() { ccb.closed = true ccb.mu.Unlock() channelz.Info(logger, ccb.cc.channelz, "ccBalancerWrapper: closing") - ccb.serializer.Schedule(func(context.Context) { + ccb.serializer.TrySchedule(func(context.Context) { if ccb.balancer == nil { return } @@ -145,7 +155,7 @@ func (ccb *ccBalancerWrapper) close() { // exitIdle invokes the balancer's exitIdle method in the serializer. func (ccb *ccBalancerWrapper) exitIdle() { - ccb.serializer.Schedule(func(ctx context.Context) { + ccb.serializer.TrySchedule(func(ctx context.Context) { if ctx.Err() != nil || ccb.balancer == nil { return } @@ -182,7 +192,7 @@ func (ccb *ccBalancerWrapper) NewSubConn(addrs []resolver.Address, opts balancer return acbw, nil } -func (ccb *ccBalancerWrapper) RemoveSubConn(sc balancer.SubConn) { +func (ccb *ccBalancerWrapper) RemoveSubConn(balancer.SubConn) { // The graceful switch balancer will never call this. logger.Errorf("ccb RemoveSubConn(%v) called unexpectedly, sc") } @@ -252,15 +262,29 @@ type acBalancerWrapper struct { // updateState is invoked by grpc to push a subConn state update to the // underlying balancer. -func (acbw *acBalancerWrapper) updateState(s connectivity.State, err error) { - acbw.ccb.serializer.Schedule(func(ctx context.Context) { +func (acbw *acBalancerWrapper) updateState(s connectivity.State, curAddr resolver.Address, err error) { + acbw.ccb.serializer.TrySchedule(func(ctx context.Context) { if ctx.Err() != nil || acbw.ccb.balancer == nil { return } // Even though it is optional for balancers, gracefulswitch ensures // opts.StateListener is set, so this cannot ever be nil. // TODO: delete this comment when UpdateSubConnState is removed. - acbw.stateListener(balancer.SubConnState{ConnectivityState: s, ConnectionError: err}) + scs := balancer.SubConnState{ConnectivityState: s, ConnectionError: err} + if s == connectivity.Ready { + setConnectedAddress(&scs, curAddr) + } + acbw.stateListener(scs) + acbw.ac.mu.Lock() + defer acbw.ac.mu.Unlock() + if s == connectivity.Ready { + // When changing states to READY, reset stateReadyChan. Wait until + // after we notify the LB policy's listener(s) in order to prevent + // ac.getTransport() from unblocking before the LB policy starts + // tracking the subchannel as READY. + close(acbw.ac.stateReadyChan) + acbw.ac.stateReadyChan = make(chan struct{}) + } }) } @@ -318,8 +342,8 @@ func (acbw *acBalancerWrapper) GetOrBuildProducer(pb balancer.ProducerBuilder) ( pData := acbw.producers[pb] if pData == nil { // Not found; create a new one and add it to the producers map. - p, close := pb.Build(acbw) - pData = &refCountedProducer{producer: p, close: close} + p, closeFn := pb.Build(acbw) + pData = &refCountedProducer{producer: p, close: closeFn} acbw.producers[pb] = pData } // Account for this new reference. diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/binarylog/grpc_binarylog_v1/binarylog.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/binarylog/grpc_binarylog_v1/binarylog.pb.go index 63c639e4fe9..55bffaa77ef 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/binarylog/grpc_binarylog_v1/binarylog.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/binarylog/grpc_binarylog_v1/binarylog.pb.go @@ -18,8 +18,8 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: -// protoc-gen-go v1.34.1 -// protoc v4.25.2 +// protoc-gen-go v1.34.2 +// protoc v5.27.1 // source: grpc/binlog/v1/binarylog.proto package grpc_binarylog_v1 @@ -1015,7 +1015,7 @@ func file_grpc_binlog_v1_binarylog_proto_rawDescGZIP() []byte { var file_grpc_binlog_v1_binarylog_proto_enumTypes = make([]protoimpl.EnumInfo, 3) var file_grpc_binlog_v1_binarylog_proto_msgTypes = make([]protoimpl.MessageInfo, 8) -var file_grpc_binlog_v1_binarylog_proto_goTypes = []interface{}{ +var file_grpc_binlog_v1_binarylog_proto_goTypes = []any{ (GrpcLogEntry_EventType)(0), // 0: grpc.binarylog.v1.GrpcLogEntry.EventType (GrpcLogEntry_Logger)(0), // 1: grpc.binarylog.v1.GrpcLogEntry.Logger (Address_Type)(0), // 2: grpc.binarylog.v1.Address.Type @@ -1058,7 +1058,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return } if !protoimpl.UnsafeEnabled { - file_grpc_binlog_v1_binarylog_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[0].Exporter = func(v any, i int) any { switch v := v.(*GrpcLogEntry); i { case 0: return &v.state @@ -1070,7 +1070,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[1].Exporter = func(v any, i int) any { switch v := v.(*ClientHeader); i { case 0: return &v.state @@ -1082,7 +1082,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[2].Exporter = func(v any, i int) any { switch v := v.(*ServerHeader); i { case 0: return &v.state @@ -1094,7 +1094,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[3].Exporter = func(v any, i int) any { switch v := v.(*Trailer); i { case 0: return &v.state @@ -1106,7 +1106,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[4].Exporter = func(v any, i int) any { switch v := v.(*Message); i { case 0: return &v.state @@ -1118,7 +1118,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[5].Exporter = func(v any, i int) any { switch v := v.(*Metadata); i { case 0: return &v.state @@ -1130,7 +1130,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[6].Exporter = func(v any, i int) any { switch v := v.(*MetadataEntry); i { case 0: return &v.state @@ -1142,7 +1142,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { return nil } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} { + file_grpc_binlog_v1_binarylog_proto_msgTypes[7].Exporter = func(v any, i int) any { switch v := v.(*Address); i { case 0: return &v.state @@ -1155,7 +1155,7 @@ func file_grpc_binlog_v1_binarylog_proto_init() { } } } - file_grpc_binlog_v1_binarylog_proto_msgTypes[0].OneofWrappers = []interface{}{ + file_grpc_binlog_v1_binarylog_proto_msgTypes[0].OneofWrappers = []any{ (*GrpcLogEntry_ClientHeader)(nil), (*GrpcLogEntry_ServerHeader)(nil), (*GrpcLogEntry_Message)(nil), diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/clientconn.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/clientconn.go index 423be7b43b0..9c8850e3fdd 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/clientconn.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/clientconn.go @@ -24,6 +24,7 @@ import ( "fmt" "math" "net/url" + "slices" "strings" "sync" "sync/atomic" @@ -39,6 +40,7 @@ import ( "google.golang.org/grpc/internal/grpcsync" "google.golang.org/grpc/internal/idle" iresolver "google.golang.org/grpc/internal/resolver" + "google.golang.org/grpc/internal/stats" "google.golang.org/grpc/internal/transport" "google.golang.org/grpc/keepalive" "google.golang.org/grpc/resolver" @@ -194,8 +196,11 @@ func NewClient(target string, opts ...DialOption) (conn *ClientConn, err error) cc.csMgr = newConnectivityStateManager(cc.ctx, cc.channelz) cc.pickerWrapper = newPickerWrapper(cc.dopts.copts.StatsHandlers) + cc.metricsRecorderList = stats.NewMetricsRecorderList(cc.dopts.copts.StatsHandlers) + cc.initIdleStateLocked() // Safe to call without the lock, since nothing else has a reference to cc. cc.idlenessMgr = idle.NewManager((*idler)(cc), cc.dopts.idleTimeout) + return cc, nil } @@ -590,13 +595,14 @@ type ClientConn struct { cancel context.CancelFunc // Cancelled on close. // The following are initialized at dial time, and are read-only after that. - target string // User's dial target. - parsedTarget resolver.Target // See initParsedTargetAndResolverBuilder(). - authority string // See initAuthority(). - dopts dialOptions // Default and user specified dial options. - channelz *channelz.Channel // Channelz object. - resolverBuilder resolver.Builder // See initParsedTargetAndResolverBuilder(). - idlenessMgr *idle.Manager + target string // User's dial target. + parsedTarget resolver.Target // See initParsedTargetAndResolverBuilder(). + authority string // See initAuthority(). + dopts dialOptions // Default and user specified dial options. + channelz *channelz.Channel // Channelz object. + resolverBuilder resolver.Builder // See initParsedTargetAndResolverBuilder(). + idlenessMgr *idle.Manager + metricsRecorderList *stats.MetricsRecorderList // The following provide their own synchronization, and therefore don't // require cc.mu to be held to access them. @@ -626,11 +632,6 @@ type ClientConn struct { // WaitForStateChange waits until the connectivity.State of ClientConn changes from sourceState or // ctx expires. A true value is returned in former case and false in latter. -// -// # Experimental -// -// Notice: This API is EXPERIMENTAL and may be changed or removed in a -// later release. func (cc *ClientConn) WaitForStateChange(ctx context.Context, sourceState connectivity.State) bool { ch := cc.csMgr.getNotifyChan() if cc.csMgr.getState() != sourceState { @@ -645,11 +646,6 @@ func (cc *ClientConn) WaitForStateChange(ctx context.Context, sourceState connec } // GetState returns the connectivity.State of ClientConn. -// -// # Experimental -// -// Notice: This API is EXPERIMENTAL and may be changed or removed in a later -// release. func (cc *ClientConn) GetState() connectivity.State { return cc.csMgr.getState() } @@ -812,17 +808,11 @@ func (cc *ClientConn) applyFailingLBLocked(sc *serviceconfig.ParseResult) { cc.csMgr.updateState(connectivity.TransientFailure) } -// Makes a copy of the input addresses slice and clears out the balancer -// attributes field. Addresses are passed during subconn creation and address -// update operations. In both cases, we will clear the balancer attributes by -// calling this function, and therefore we will be able to use the Equal method -// provided by the resolver.Address type for comparison. -func copyAddressesWithoutBalancerAttributes(in []resolver.Address) []resolver.Address { +// Makes a copy of the input addresses slice. Addresses are passed during +// subconn creation and address update operations. +func copyAddresses(in []resolver.Address) []resolver.Address { out := make([]resolver.Address, len(in)) - for i := range in { - out[i] = in[i] - out[i].BalancerAttributes = nil - } + copy(out, in) return out } @@ -835,14 +825,14 @@ func (cc *ClientConn) newAddrConnLocked(addrs []resolver.Address, opts balancer. } ac := &addrConn{ - state: connectivity.Idle, - cc: cc, - addrs: copyAddressesWithoutBalancerAttributes(addrs), - scopts: opts, - dopts: cc.dopts, - channelz: channelz.RegisterSubChannel(cc.channelz, ""), - resetBackoff: make(chan struct{}), - stateChan: make(chan struct{}), + state: connectivity.Idle, + cc: cc, + addrs: copyAddresses(addrs), + scopts: opts, + dopts: cc.dopts, + channelz: channelz.RegisterSubChannel(cc.channelz, ""), + resetBackoff: make(chan struct{}), + stateReadyChan: make(chan struct{}), } ac.ctx, ac.cancel = context.WithCancel(cc.ctx) // Start with our address set to the first address; this may be updated if @@ -918,28 +908,29 @@ func (ac *addrConn) connect() error { ac.mu.Unlock() return nil } - ac.mu.Unlock() - ac.resetTransport() + ac.resetTransportAndUnlock() return nil } -func equalAddresses(a, b []resolver.Address) bool { - if len(a) != len(b) { - return false - } - for i, v := range a { - if !v.Equal(b[i]) { - return false - } - } - return true +// equalAddressIgnoringBalAttributes returns true is a and b are considered equal. +// This is different from the Equal method on the resolver.Address type which +// considers all fields to determine equality. Here, we only consider fields +// that are meaningful to the subConn. +func equalAddressIgnoringBalAttributes(a, b *resolver.Address) bool { + return a.Addr == b.Addr && a.ServerName == b.ServerName && + a.Attributes.Equal(b.Attributes) && + a.Metadata == b.Metadata +} + +func equalAddressesIgnoringBalAttributes(a, b []resolver.Address) bool { + return slices.EqualFunc(a, b, func(a, b resolver.Address) bool { return equalAddressIgnoringBalAttributes(&a, &b) }) } // updateAddrs updates ac.addrs with the new addresses list and handles active // connections or connection attempts. func (ac *addrConn) updateAddrs(addrs []resolver.Address) { - addrs = copyAddressesWithoutBalancerAttributes(addrs) + addrs = copyAddresses(addrs) limit := len(addrs) if limit > 5 { limit = 5 @@ -947,7 +938,7 @@ func (ac *addrConn) updateAddrs(addrs []resolver.Address) { channelz.Infof(logger, ac.channelz, "addrConn: updateAddrs addrs (%d of %d): %v", limit, len(addrs), addrs[:limit]) ac.mu.Lock() - if equalAddresses(ac.addrs, addrs) { + if equalAddressesIgnoringBalAttributes(ac.addrs, addrs) { ac.mu.Unlock() return } @@ -966,7 +957,7 @@ func (ac *addrConn) updateAddrs(addrs []resolver.Address) { // Try to find the connected address. for _, a := range addrs { a.ServerName = ac.cc.getServerName(a) - if a.Equal(ac.curAddr) { + if equalAddressIgnoringBalAttributes(&a, &ac.curAddr) { // We are connected to a valid address, so do nothing but // update the addresses. ac.mu.Unlock() @@ -992,11 +983,9 @@ func (ac *addrConn) updateAddrs(addrs []resolver.Address) { ac.updateConnectivityState(connectivity.Idle, nil) } - ac.mu.Unlock() - // Since we were connecting/connected, we should start a new connection // attempt. - go ac.resetTransport() + go ac.resetTransportAndUnlock() } // getServerName determines the serverName to be used in the connection @@ -1190,8 +1179,8 @@ type addrConn struct { addrs []resolver.Address // All addresses that the resolver resolved to. // Use updateConnectivityState for updating addrConn's connectivity state. - state connectivity.State - stateChan chan struct{} // closed and recreated on every state change. + state connectivity.State + stateReadyChan chan struct{} // closed and recreated on every READY state change. backoffIdx int // Needs to be stateful for resetConnectBackoff. resetBackoff chan struct{} @@ -1204,9 +1193,6 @@ func (ac *addrConn) updateConnectivityState(s connectivity.State, lastErr error) if ac.state == s { return } - // When changing states, reset the state change channel. - close(ac.stateChan) - ac.stateChan = make(chan struct{}) ac.state = s ac.channelz.ChannelMetrics.State.Store(&s) if lastErr == nil { @@ -1214,7 +1200,7 @@ func (ac *addrConn) updateConnectivityState(s connectivity.State, lastErr error) } else { channelz.Infof(logger, ac.channelz, "Subchannel Connectivity change to %v, last error: %s", s, lastErr) } - ac.acbw.updateState(s, lastErr) + ac.acbw.updateState(s, ac.curAddr, lastErr) } // adjustParams updates parameters used to create transports upon @@ -1231,8 +1217,10 @@ func (ac *addrConn) adjustParams(r transport.GoAwayReason) { } } -func (ac *addrConn) resetTransport() { - ac.mu.Lock() +// resetTransportAndUnlock unconditionally connects the addrConn. +// +// ac.mu must be held by the caller, and this function will guarantee it is released. +func (ac *addrConn) resetTransportAndUnlock() { acCtx := ac.ctx if acCtx.Err() != nil { ac.mu.Unlock() @@ -1522,7 +1510,7 @@ func (ac *addrConn) getReadyTransport() transport.ClientTransport { func (ac *addrConn) getTransport(ctx context.Context) (transport.ClientTransport, error) { for ctx.Err() == nil { ac.mu.Lock() - t, state, sc := ac.transport, ac.state, ac.stateChan + t, state, sc := ac.transport, ac.state, ac.stateReadyChan ac.mu.Unlock() if state == connectivity.Ready { return t, nil @@ -1585,7 +1573,7 @@ func (ac *addrConn) tearDown(err error) { } else { // Hard close the transport when the channel is entering idle or is // being shutdown. In the case where the channel is being shutdown, - // closing of transports is also taken care of by cancelation of cc.ctx. + // closing of transports is also taken care of by cancellation of cc.ctx. // But in the case where the channel is entering idle, we need to // explicitly close the transports here. Instead of distinguishing // between these two cases, it is simpler to close the transport diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/codec.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/codec.go index 411e3dfd47c..e840858b77b 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/codec.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/codec.go @@ -21,18 +21,73 @@ package grpc import ( "google.golang.org/grpc/encoding" _ "google.golang.org/grpc/encoding/proto" // to register the Codec for "proto" + "google.golang.org/grpc/mem" ) -// baseCodec contains the functionality of both Codec and encoding.Codec, but -// omits the name/string, which vary between the two and are not needed for -// anything besides the registry in the encoding package. +// baseCodec captures the new encoding.CodecV2 interface without the Name +// function, allowing it to be implemented by older Codec and encoding.Codec +// implementations. The omitted Name function is only needed for the register in +// the encoding package and is not part of the core functionality. type baseCodec interface { - Marshal(v any) ([]byte, error) - Unmarshal(data []byte, v any) error + Marshal(v any) (mem.BufferSlice, error) + Unmarshal(data mem.BufferSlice, v any) error +} + +// getCodec returns an encoding.CodecV2 for the codec of the given name (if +// registered). Initially checks the V2 registry with encoding.GetCodecV2 and +// returns the V2 codec if it is registered. Otherwise, it checks the V1 registry +// with encoding.GetCodec and if it is registered wraps it with newCodecV1Bridge +// to turn it into an encoding.CodecV2. Returns nil otherwise. +func getCodec(name string) encoding.CodecV2 { + if codecV1 := encoding.GetCodec(name); codecV1 != nil { + return newCodecV1Bridge(codecV1) + } + + return encoding.GetCodecV2(name) +} + +func newCodecV0Bridge(c Codec) baseCodec { + return codecV0Bridge{codec: c} +} + +func newCodecV1Bridge(c encoding.Codec) encoding.CodecV2 { + return codecV1Bridge{ + codecV0Bridge: codecV0Bridge{codec: c}, + name: c.Name(), + } +} + +var _ baseCodec = codecV0Bridge{} + +type codecV0Bridge struct { + codec interface { + Marshal(v any) ([]byte, error) + Unmarshal(data []byte, v any) error + } +} + +func (c codecV0Bridge) Marshal(v any) (mem.BufferSlice, error) { + data, err := c.codec.Marshal(v) + if err != nil { + return nil, err + } + return mem.BufferSlice{mem.NewBuffer(&data, nil)}, nil +} + +func (c codecV0Bridge) Unmarshal(data mem.BufferSlice, v any) (err error) { + return c.codec.Unmarshal(data.Materialize(), v) } -var _ baseCodec = Codec(nil) -var _ baseCodec = encoding.Codec(nil) +var _ encoding.CodecV2 = codecV1Bridge{} + +type codecV1Bridge struct { + codecV0Bridge + name string +} + +func (c codecV1Bridge) Name() string { + return c.name +} // Codec defines the interface gRPC uses to encode and decode messages. // Note that implementations of this interface must be thread safe; diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/credentials/insecure/insecure.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/credentials/insecure/insecure.go index 82bee1443bf..4c805c64462 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/credentials/insecure/insecure.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/credentials/insecure/insecure.go @@ -40,7 +40,7 @@ func NewCredentials() credentials.TransportCredentials { // NoSecurity. type insecureTC struct{} -func (insecureTC) ClientHandshake(ctx context.Context, _ string, conn net.Conn) (net.Conn, credentials.AuthInfo, error) { +func (insecureTC) ClientHandshake(_ context.Context, _ string, conn net.Conn) (net.Conn, credentials.AuthInfo, error) { return conn, info{credentials.CommonAuthInfo{SecurityLevel: credentials.NoSecurity}}, nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/dialoptions.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/dialoptions.go index f5453d48a53..2b285beee37 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/dialoptions.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/dialoptions.go @@ -33,6 +33,7 @@ import ( "google.golang.org/grpc/internal/binarylog" "google.golang.org/grpc/internal/transport" "google.golang.org/grpc/keepalive" + "google.golang.org/grpc/mem" "google.golang.org/grpc/resolver" "google.golang.org/grpc/stats" ) @@ -60,7 +61,7 @@ func init() { internal.WithBinaryLogger = withBinaryLogger internal.JoinDialOptions = newJoinDialOption internal.DisableGlobalDialOptions = newDisableGlobalDialOptions - internal.WithRecvBufferPool = withRecvBufferPool + internal.WithBufferPool = withBufferPool } // dialOptions configure a Dial call. dialOptions are set by the DialOption @@ -92,7 +93,6 @@ type dialOptions struct { defaultServiceConfigRawJSON *string resolvers []resolver.Builder idleTimeout time.Duration - recvBufferPool SharedBufferPool defaultScheme string maxCallAttempts int } @@ -518,6 +518,8 @@ func WithUserAgent(s string) DialOption { // WithKeepaliveParams returns a DialOption that specifies keepalive parameters // for the client transport. +// +// Keepalive is disabled by default. func WithKeepaliveParams(kp keepalive.ClientParameters) DialOption { if kp.Time < internal.KeepaliveMinPingTime { logger.Warningf("Adjusting keepalive ping interval to minimum period of %v", internal.KeepaliveMinPingTime) @@ -677,11 +679,11 @@ func defaultDialOptions() dialOptions { WriteBufferSize: defaultWriteBufSize, UseProxy: true, UserAgent: grpcUA, + BufferPool: mem.DefaultBufferPool(), }, bs: internalbackoff.DefaultExponential, healthCheckFunc: internal.HealthCheckFunc, idleTimeout: 30 * time.Minute, - recvBufferPool: nopBufferPool{}, defaultScheme: "dns", maxCallAttempts: defaultMaxCallAttempts, } @@ -758,25 +760,8 @@ func WithMaxCallAttempts(n int) DialOption { }) } -// WithRecvBufferPool returns a DialOption that configures the ClientConn -// to use the provided shared buffer pool for parsing incoming messages. Depending -// on the application's workload, this could result in reduced memory allocation. -// -// If you are unsure about how to implement a memory pool but want to utilize one, -// begin with grpc.NewSharedBufferPool. -// -// Note: The shared buffer pool feature will not be active if any of the following -// options are used: WithStatsHandler, EnableTracing, or binary logging. In such -// cases, the shared buffer pool will be ignored. -// -// Deprecated: use experimental.WithRecvBufferPool instead. Will be deleted in -// v1.60.0 or later. -func WithRecvBufferPool(bufferPool SharedBufferPool) DialOption { - return withRecvBufferPool(bufferPool) -} - -func withRecvBufferPool(bufferPool SharedBufferPool) DialOption { +func withBufferPool(bufferPool mem.BufferPool) DialOption { return newFuncDialOption(func(o *dialOptions) { - o.recvBufferPool = bufferPool + o.copts.BufferPool = bufferPool }) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/doc.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/doc.go index 0022859ad74..e7b532b6f80 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/doc.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/doc.go @@ -16,7 +16,7 @@ * */ -//go:generate ./regenerate.sh +//go:generate ./scripts/regenerate.sh /* Package grpc implements an RPC system called gRPC. diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding.go index 5ebf88d7147..11d0ae142c4 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding.go @@ -94,7 +94,7 @@ type Codec interface { Name() string } -var registeredCodecs = make(map[string]Codec) +var registeredCodecs = make(map[string]any) // RegisterCodec registers the provided Codec for use with all gRPC clients and // servers. @@ -126,5 +126,6 @@ func RegisterCodec(codec Codec) { // // The content-subtype is expected to be lowercase. func GetCodec(contentSubtype string) Codec { - return registeredCodecs[contentSubtype] + c, _ := registeredCodecs[contentSubtype].(Codec) + return c } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding_v2.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding_v2.go new file mode 100644 index 00000000000..074c5e234a7 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/encoding_v2.go @@ -0,0 +1,81 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 encoding + +import ( + "strings" + + "google.golang.org/grpc/mem" +) + +// CodecV2 defines the interface gRPC uses to encode and decode messages. Note +// that implementations of this interface must be thread safe; a CodecV2's +// methods can be called from concurrent goroutines. +type CodecV2 interface { + // Marshal returns the wire format of v. The buffers in the returned + // [mem.BufferSlice] must have at least one reference each, which will be freed + // by gRPC when they are no longer needed. + Marshal(v any) (out mem.BufferSlice, err error) + // Unmarshal parses the wire format into v. Note that data will be freed as soon + // as this function returns. If the codec wishes to guarantee access to the data + // after this function, it must take its own reference that it frees when it is + // no longer needed. + Unmarshal(data mem.BufferSlice, v any) error + // Name returns the name of the Codec implementation. The returned string + // will be used as part of content type in transmission. The result must be + // static; the result cannot change between calls. + Name() string +} + +// RegisterCodecV2 registers the provided CodecV2 for use with all gRPC clients and +// servers. +// +// The CodecV2 will be stored and looked up by result of its Name() method, which +// should match the content-subtype of the encoding handled by the CodecV2. This +// is case-insensitive, and is stored and looked up as lowercase. If the +// result of calling Name() is an empty string, RegisterCodecV2 will panic. See +// Content-Type on +// https://github.com/grpc/grpc/blob/master/doc/PROTOCOL-HTTP2.md#requests for +// more details. +// +// If both a Codec and CodecV2 are registered with the same name, the CodecV2 +// will be used. +// +// NOTE: this function must only be called during initialization time (i.e. in +// an init() function), and is not thread-safe. If multiple Codecs are +// registered with the same name, the one registered last will take effect. +func RegisterCodecV2(codec CodecV2) { + if codec == nil { + panic("cannot register a nil CodecV2") + } + if codec.Name() == "" { + panic("cannot register CodecV2 with empty string result for Name()") + } + contentSubtype := strings.ToLower(codec.Name()) + registeredCodecs[contentSubtype] = codec +} + +// GetCodecV2 gets a registered CodecV2 by content-subtype, or nil if no CodecV2 is +// registered for the content-subtype. +// +// The content-subtype is expected to be lowercase. +func GetCodecV2(contentSubtype string) CodecV2 { + c, _ := registeredCodecs[contentSubtype].(CodecV2) + return c +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/proto/proto.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/proto/proto.go index 66d5cdf03ec..ceec319dd2f 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/proto/proto.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/encoding/proto/proto.go @@ -1,6 +1,6 @@ /* * - * Copyright 2018 gRPC authors. + * Copyright 2024 gRPC authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -24,6 +24,7 @@ import ( "fmt" "google.golang.org/grpc/encoding" + "google.golang.org/grpc/mem" "google.golang.org/protobuf/proto" "google.golang.org/protobuf/protoadapt" ) @@ -32,28 +33,51 @@ import ( const Name = "proto" func init() { - encoding.RegisterCodec(codec{}) + encoding.RegisterCodecV2(&codecV2{}) } -// codec is a Codec implementation with protobuf. It is the default codec for gRPC. -type codec struct{} +// codec is a CodecV2 implementation with protobuf. It is the default codec for +// gRPC. +type codecV2 struct{} -func (codec) Marshal(v any) ([]byte, error) { +func (c *codecV2) Marshal(v any) (data mem.BufferSlice, err error) { vv := messageV2Of(v) if vv == nil { - return nil, fmt.Errorf("failed to marshal, message is %T, want proto.Message", v) + return nil, fmt.Errorf("proto: failed to marshal, message is %T, want proto.Message", v) } - return proto.Marshal(vv) + size := proto.Size(vv) + if mem.IsBelowBufferPoolingThreshold(size) { + buf, err := proto.Marshal(vv) + if err != nil { + return nil, err + } + data = append(data, mem.SliceBuffer(buf)) + } else { + pool := mem.DefaultBufferPool() + buf := pool.Get(size) + if _, err := (proto.MarshalOptions{}).MarshalAppend((*buf)[:0], vv); err != nil { + pool.Put(buf) + return nil, err + } + data = append(data, mem.NewBuffer(buf, pool)) + } + + return data, nil } -func (codec) Unmarshal(data []byte, v any) error { +func (c *codecV2) Unmarshal(data mem.BufferSlice, v any) (err error) { vv := messageV2Of(v) if vv == nil { return fmt.Errorf("failed to unmarshal, message is %T, want proto.Message", v) } - return proto.Unmarshal(data, vv) + buf := data.MaterializeToBuffer(mem.DefaultBufferPool()) + defer buf.Free() + // TODO: Upgrade proto.Unmarshal to support mem.BufferSlice. Right now, it's not + // really possible without a major overhaul of the proto package, but the + // vtprotobuf library may be able to support this. + return proto.Unmarshal(buf.ReadOnlyData(), vv) } func messageV2Of(v any) proto.Message { @@ -67,6 +91,6 @@ func messageV2Of(v any) proto.Message { return nil } -func (codec) Name() string { +func (c *codecV2) Name() string { return Name } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metricregistry.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metricregistry.go new file mode 100644 index 00000000000..1d827dd5d9d --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metricregistry.go @@ -0,0 +1,269 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 stats + +import ( + "maps" + + "google.golang.org/grpc/grpclog" + "google.golang.org/grpc/internal" +) + +func init() { + internal.SnapshotMetricRegistryForTesting = snapshotMetricsRegistryForTesting +} + +var logger = grpclog.Component("metrics-registry") + +// DefaultMetrics are the default metrics registered through global metrics +// registry. This is written to at initialization time only, and is read only +// after initialization. +var DefaultMetrics = NewMetrics() + +// MetricDescriptor is the data for a registered metric. +type MetricDescriptor struct { + // The name of this metric. This name must be unique across the whole binary + // (including any per call metrics). See + // https://github.com/grpc/proposal/blob/master/A79-non-per-call-metrics-architecture.md#metric-instrument-naming-conventions + // for metric naming conventions. + Name Metric + // The description of this metric. + Description string + // The unit (e.g. entries, seconds) of this metric. + Unit string + // The required label keys for this metric. These are intended to + // metrics emitted from a stats handler. + Labels []string + // The optional label keys for this metric. These are intended to attached + // to metrics emitted from a stats handler if configured. + OptionalLabels []string + // Whether this metric is on by default. + Default bool + // The type of metric. This is set by the metric registry, and not intended + // to be set by a component registering a metric. + Type MetricType + // Bounds are the bounds of this metric. This only applies to histogram + // metrics. If unset or set with length 0, stats handlers will fall back to + // default bounds. + Bounds []float64 +} + +// MetricType is the type of metric. +type MetricType int + +// Type of metric supported by this instrument registry. +const ( + MetricTypeIntCount MetricType = iota + MetricTypeFloatCount + MetricTypeIntHisto + MetricTypeFloatHisto + MetricTypeIntGauge +) + +// Int64CountHandle is a typed handle for a int count metric. This handle +// is passed at the recording point in order to know which metric to record +// on. +type Int64CountHandle MetricDescriptor + +// Descriptor returns the int64 count handle typecast to a pointer to a +// MetricDescriptor. +func (h *Int64CountHandle) Descriptor() *MetricDescriptor { + return (*MetricDescriptor)(h) +} + +// Record records the int64 count value on the metrics recorder provided. +func (h *Int64CountHandle) Record(recorder MetricsRecorder, incr int64, labels ...string) { + recorder.RecordInt64Count(h, incr, labels...) +} + +// Float64CountHandle is a typed handle for a float count metric. This handle is +// passed at the recording point in order to know which metric to record on. +type Float64CountHandle MetricDescriptor + +// Descriptor returns the float64 count handle typecast to a pointer to a +// MetricDescriptor. +func (h *Float64CountHandle) Descriptor() *MetricDescriptor { + return (*MetricDescriptor)(h) +} + +// Record records the float64 count value on the metrics recorder provided. +func (h *Float64CountHandle) Record(recorder MetricsRecorder, incr float64, labels ...string) { + recorder.RecordFloat64Count(h, incr, labels...) +} + +// Int64HistoHandle is a typed handle for an int histogram metric. This handle +// is passed at the recording point in order to know which metric to record on. +type Int64HistoHandle MetricDescriptor + +// Descriptor returns the int64 histo handle typecast to a pointer to a +// MetricDescriptor. +func (h *Int64HistoHandle) Descriptor() *MetricDescriptor { + return (*MetricDescriptor)(h) +} + +// Record records the int64 histo value on the metrics recorder provided. +func (h *Int64HistoHandle) Record(recorder MetricsRecorder, incr int64, labels ...string) { + recorder.RecordInt64Histo(h, incr, labels...) +} + +// Float64HistoHandle is a typed handle for a float histogram metric. This +// handle is passed at the recording point in order to know which metric to +// record on. +type Float64HistoHandle MetricDescriptor + +// Descriptor returns the float64 histo handle typecast to a pointer to a +// MetricDescriptor. +func (h *Float64HistoHandle) Descriptor() *MetricDescriptor { + return (*MetricDescriptor)(h) +} + +// Record records the float64 histo value on the metrics recorder provided. +func (h *Float64HistoHandle) Record(recorder MetricsRecorder, incr float64, labels ...string) { + recorder.RecordFloat64Histo(h, incr, labels...) +} + +// Int64GaugeHandle is a typed handle for an int gauge metric. This handle is +// passed at the recording point in order to know which metric to record on. +type Int64GaugeHandle MetricDescriptor + +// Descriptor returns the int64 gauge handle typecast to a pointer to a +// MetricDescriptor. +func (h *Int64GaugeHandle) Descriptor() *MetricDescriptor { + return (*MetricDescriptor)(h) +} + +// Record records the int64 histo value on the metrics recorder provided. +func (h *Int64GaugeHandle) Record(recorder MetricsRecorder, incr int64, labels ...string) { + recorder.RecordInt64Gauge(h, incr, labels...) +} + +// registeredMetrics are the registered metric descriptor names. +var registeredMetrics = make(map[Metric]bool) + +// metricsRegistry contains all of the registered metrics. +// +// This is written to only at init time, and read only after that. +var metricsRegistry = make(map[Metric]*MetricDescriptor) + +// DescriptorForMetric returns the MetricDescriptor from the global registry. +// +// Returns nil if MetricDescriptor not present. +func DescriptorForMetric(metric Metric) *MetricDescriptor { + return metricsRegistry[metric] +} + +func registerMetric(name Metric, def bool) { + if registeredMetrics[name] { + logger.Fatalf("metric %v already registered", name) + } + registeredMetrics[name] = true + if def { + DefaultMetrics = DefaultMetrics.Add(name) + } +} + +// RegisterInt64Count registers the metric description onto the global registry. +// It returns a typed handle to use to recording data. +// +// NOTE: this function must only be called during initialization time (i.e. in +// an init() function), and is not thread-safe. If multiple metrics are +// registered with the same name, this function will panic. +func RegisterInt64Count(descriptor MetricDescriptor) *Int64CountHandle { + registerMetric(descriptor.Name, descriptor.Default) + descriptor.Type = MetricTypeIntCount + descPtr := &descriptor + metricsRegistry[descriptor.Name] = descPtr + return (*Int64CountHandle)(descPtr) +} + +// RegisterFloat64Count registers the metric description onto the global +// registry. It returns a typed handle to use to recording data. +// +// NOTE: this function must only be called during initialization time (i.e. in +// an init() function), and is not thread-safe. If multiple metrics are +// registered with the same name, this function will panic. +func RegisterFloat64Count(descriptor MetricDescriptor) *Float64CountHandle { + registerMetric(descriptor.Name, descriptor.Default) + descriptor.Type = MetricTypeFloatCount + descPtr := &descriptor + metricsRegistry[descriptor.Name] = descPtr + return (*Float64CountHandle)(descPtr) +} + +// RegisterInt64Histo registers the metric description onto the global registry. +// It returns a typed handle to use to recording data. +// +// NOTE: this function must only be called during initialization time (i.e. in +// an init() function), and is not thread-safe. If multiple metrics are +// registered with the same name, this function will panic. +func RegisterInt64Histo(descriptor MetricDescriptor) *Int64HistoHandle { + registerMetric(descriptor.Name, descriptor.Default) + descriptor.Type = MetricTypeIntHisto + descPtr := &descriptor + metricsRegistry[descriptor.Name] = descPtr + return (*Int64HistoHandle)(descPtr) +} + +// RegisterFloat64Histo registers the metric description onto the global +// registry. It returns a typed handle to use to recording data. +// +// NOTE: this function must only be called during initialization time (i.e. in +// an init() function), and is not thread-safe. If multiple metrics are +// registered with the same name, this function will panic. +func RegisterFloat64Histo(descriptor MetricDescriptor) *Float64HistoHandle { + registerMetric(descriptor.Name, descriptor.Default) + descriptor.Type = MetricTypeFloatHisto + descPtr := &descriptor + metricsRegistry[descriptor.Name] = descPtr + return (*Float64HistoHandle)(descPtr) +} + +// RegisterInt64Gauge registers the metric description onto the global registry. +// It returns a typed handle to use to recording data. +// +// NOTE: this function must only be called during initialization time (i.e. in +// an init() function), and is not thread-safe. If multiple metrics are +// registered with the same name, this function will panic. +func RegisterInt64Gauge(descriptor MetricDescriptor) *Int64GaugeHandle { + registerMetric(descriptor.Name, descriptor.Default) + descriptor.Type = MetricTypeIntGauge + descPtr := &descriptor + metricsRegistry[descriptor.Name] = descPtr + return (*Int64GaugeHandle)(descPtr) +} + +// snapshotMetricsRegistryForTesting snapshots the global data of the metrics +// registry. Returns a cleanup function that sets the metrics registry to its +// original state. +func snapshotMetricsRegistryForTesting() func() { + oldDefaultMetrics := DefaultMetrics + oldRegisteredMetrics := registeredMetrics + oldMetricsRegistry := metricsRegistry + + registeredMetrics = make(map[Metric]bool) + metricsRegistry = make(map[Metric]*MetricDescriptor) + maps.Copy(registeredMetrics, registeredMetrics) + maps.Copy(metricsRegistry, metricsRegistry) + + return func() { + DefaultMetrics = oldDefaultMetrics + registeredMetrics = oldRegisteredMetrics + metricsRegistry = oldMetricsRegistry + } +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metrics.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metrics.go new file mode 100644 index 00000000000..3221f7a633a --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/experimental/stats/metrics.go @@ -0,0 +1,114 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 stats contains experimental metrics/stats API's. +package stats + +import "maps" + +// MetricsRecorder records on metrics derived from metric registry. +type MetricsRecorder interface { + // RecordInt64Count records the measurement alongside labels on the int + // count associated with the provided handle. + RecordInt64Count(handle *Int64CountHandle, incr int64, labels ...string) + // RecordFloat64Count records the measurement alongside labels on the float + // count associated with the provided handle. + RecordFloat64Count(handle *Float64CountHandle, incr float64, labels ...string) + // RecordInt64Histo records the measurement alongside labels on the int + // histo associated with the provided handle. + RecordInt64Histo(handle *Int64HistoHandle, incr int64, labels ...string) + // RecordFloat64Histo records the measurement alongside labels on the float + // histo associated with the provided handle. + RecordFloat64Histo(handle *Float64HistoHandle, incr float64, labels ...string) + // RecordInt64Gauge records the measurement alongside labels on the int + // gauge associated with the provided handle. + RecordInt64Gauge(handle *Int64GaugeHandle, incr int64, labels ...string) +} + +// Metric is an identifier for a metric. +type Metric string + +// Metrics is a set of metrics to record. Once created, Metrics is immutable, +// however Add and Remove can make copies with specific metrics added or +// removed, respectively. +// +// Do not construct directly; use NewMetrics instead. +type Metrics struct { + // metrics are the set of metrics to initialize. + metrics map[Metric]bool +} + +// NewMetrics returns a Metrics containing Metrics. +func NewMetrics(metrics ...Metric) *Metrics { + newMetrics := make(map[Metric]bool) + for _, metric := range metrics { + newMetrics[metric] = true + } + return &Metrics{ + metrics: newMetrics, + } +} + +// Metrics returns the metrics set. The returned map is read-only and must not +// be modified. +func (m *Metrics) Metrics() map[Metric]bool { + return m.metrics +} + +// Add adds the metrics to the metrics set and returns a new copy with the +// additional metrics. +func (m *Metrics) Add(metrics ...Metric) *Metrics { + newMetrics := make(map[Metric]bool) + for metric := range m.metrics { + newMetrics[metric] = true + } + + for _, metric := range metrics { + newMetrics[metric] = true + } + return &Metrics{ + metrics: newMetrics, + } +} + +// Join joins the metrics passed in with the metrics set, and returns a new copy +// with the merged metrics. +func (m *Metrics) Join(metrics *Metrics) *Metrics { + newMetrics := make(map[Metric]bool) + maps.Copy(newMetrics, m.metrics) + maps.Copy(newMetrics, metrics.metrics) + return &Metrics{ + metrics: newMetrics, + } +} + +// Remove removes the metrics from the metrics set and returns a new copy with +// the metrics removed. +func (m *Metrics) Remove(metrics ...Metric) *Metrics { + newMetrics := make(map[Metric]bool) + for metric := range m.metrics { + newMetrics[metric] = true + } + + for _, metric := range metrics { + delete(newMetrics, metric) + } + return &Metrics{ + metrics: newMetrics, + } +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/component.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/component.go index ac73c9ced25..f1ae080dcb8 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/component.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/component.go @@ -20,8 +20,6 @@ package grpclog import ( "fmt" - - "google.golang.org/grpc/internal/grpclog" ) // componentData records the settings for a component. @@ -33,22 +31,22 @@ var cache = map[string]*componentData{} func (c *componentData) InfoDepth(depth int, args ...any) { args = append([]any{"[" + string(c.name) + "]"}, args...) - grpclog.InfoDepth(depth+1, args...) + InfoDepth(depth+1, args...) } func (c *componentData) WarningDepth(depth int, args ...any) { args = append([]any{"[" + string(c.name) + "]"}, args...) - grpclog.WarningDepth(depth+1, args...) + WarningDepth(depth+1, args...) } func (c *componentData) ErrorDepth(depth int, args ...any) { args = append([]any{"[" + string(c.name) + "]"}, args...) - grpclog.ErrorDepth(depth+1, args...) + ErrorDepth(depth+1, args...) } func (c *componentData) FatalDepth(depth int, args ...any) { args = append([]any{"[" + string(c.name) + "]"}, args...) - grpclog.FatalDepth(depth+1, args...) + FatalDepth(depth+1, args...) } func (c *componentData) Info(args ...any) { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/grpclog.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/grpclog.go index 16928c9cb99..db320105e64 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/grpclog.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/grpclog.go @@ -18,18 +18,15 @@ // Package grpclog defines logging for grpc. // -// All logs in transport and grpclb packages only go to verbose level 2. -// All logs in other packages in grpc are logged in spite of the verbosity level. -// -// In the default logger, -// severity level can be set by environment variable GRPC_GO_LOG_SEVERITY_LEVEL, -// verbosity level can be set by GRPC_GO_LOG_VERBOSITY_LEVEL. -package grpclog // import "google.golang.org/grpc/grpclog" +// In the default logger, severity level can be set by environment variable +// GRPC_GO_LOG_SEVERITY_LEVEL, verbosity level can be set by +// GRPC_GO_LOG_VERBOSITY_LEVEL. +package grpclog import ( "os" - "google.golang.org/grpc/internal/grpclog" + "google.golang.org/grpc/grpclog/internal" ) func init() { @@ -38,58 +35,58 @@ func init() { // V reports whether verbosity level l is at least the requested verbose level. func V(l int) bool { - return grpclog.Logger.V(l) + return internal.LoggerV2Impl.V(l) } // Info logs to the INFO log. func Info(args ...any) { - grpclog.Logger.Info(args...) + internal.LoggerV2Impl.Info(args...) } // Infof logs to the INFO log. Arguments are handled in the manner of fmt.Printf. func Infof(format string, args ...any) { - grpclog.Logger.Infof(format, args...) + internal.LoggerV2Impl.Infof(format, args...) } // Infoln logs to the INFO log. Arguments are handled in the manner of fmt.Println. func Infoln(args ...any) { - grpclog.Logger.Infoln(args...) + internal.LoggerV2Impl.Infoln(args...) } // Warning logs to the WARNING log. func Warning(args ...any) { - grpclog.Logger.Warning(args...) + internal.LoggerV2Impl.Warning(args...) } // Warningf logs to the WARNING log. Arguments are handled in the manner of fmt.Printf. func Warningf(format string, args ...any) { - grpclog.Logger.Warningf(format, args...) + internal.LoggerV2Impl.Warningf(format, args...) } // Warningln logs to the WARNING log. Arguments are handled in the manner of fmt.Println. func Warningln(args ...any) { - grpclog.Logger.Warningln(args...) + internal.LoggerV2Impl.Warningln(args...) } // Error logs to the ERROR log. func Error(args ...any) { - grpclog.Logger.Error(args...) + internal.LoggerV2Impl.Error(args...) } // Errorf logs to the ERROR log. Arguments are handled in the manner of fmt.Printf. func Errorf(format string, args ...any) { - grpclog.Logger.Errorf(format, args...) + internal.LoggerV2Impl.Errorf(format, args...) } // Errorln logs to the ERROR log. Arguments are handled in the manner of fmt.Println. func Errorln(args ...any) { - grpclog.Logger.Errorln(args...) + internal.LoggerV2Impl.Errorln(args...) } // Fatal logs to the FATAL log. Arguments are handled in the manner of fmt.Print. // It calls os.Exit() with exit code 1. func Fatal(args ...any) { - grpclog.Logger.Fatal(args...) + internal.LoggerV2Impl.Fatal(args...) // Make sure fatal logs will exit. os.Exit(1) } @@ -97,15 +94,15 @@ func Fatal(args ...any) { // Fatalf logs to the FATAL log. Arguments are handled in the manner of fmt.Printf. // It calls os.Exit() with exit code 1. func Fatalf(format string, args ...any) { - grpclog.Logger.Fatalf(format, args...) + internal.LoggerV2Impl.Fatalf(format, args...) // Make sure fatal logs will exit. os.Exit(1) } // Fatalln logs to the FATAL log. Arguments are handled in the manner of fmt.Println. -// It calle os.Exit()) with exit code 1. +// It calls os.Exit() with exit code 1. func Fatalln(args ...any) { - grpclog.Logger.Fatalln(args...) + internal.LoggerV2Impl.Fatalln(args...) // Make sure fatal logs will exit. os.Exit(1) } @@ -114,19 +111,76 @@ func Fatalln(args ...any) { // // Deprecated: use Info. func Print(args ...any) { - grpclog.Logger.Info(args...) + internal.LoggerV2Impl.Info(args...) } // Printf prints to the logger. Arguments are handled in the manner of fmt.Printf. // // Deprecated: use Infof. func Printf(format string, args ...any) { - grpclog.Logger.Infof(format, args...) + internal.LoggerV2Impl.Infof(format, args...) } // Println prints to the logger. Arguments are handled in the manner of fmt.Println. // // Deprecated: use Infoln. func Println(args ...any) { - grpclog.Logger.Infoln(args...) + internal.LoggerV2Impl.Infoln(args...) +} + +// InfoDepth logs to the INFO log at the specified depth. +// +// # Experimental +// +// Notice: This API is EXPERIMENTAL and may be changed or removed in a +// later release. +func InfoDepth(depth int, args ...any) { + if internal.DepthLoggerV2Impl != nil { + internal.DepthLoggerV2Impl.InfoDepth(depth, args...) + } else { + internal.LoggerV2Impl.Infoln(args...) + } +} + +// WarningDepth logs to the WARNING log at the specified depth. +// +// # Experimental +// +// Notice: This API is EXPERIMENTAL and may be changed or removed in a +// later release. +func WarningDepth(depth int, args ...any) { + if internal.DepthLoggerV2Impl != nil { + internal.DepthLoggerV2Impl.WarningDepth(depth, args...) + } else { + internal.LoggerV2Impl.Warningln(args...) + } +} + +// ErrorDepth logs to the ERROR log at the specified depth. +// +// # Experimental +// +// Notice: This API is EXPERIMENTAL and may be changed or removed in a +// later release. +func ErrorDepth(depth int, args ...any) { + if internal.DepthLoggerV2Impl != nil { + internal.DepthLoggerV2Impl.ErrorDepth(depth, args...) + } else { + internal.LoggerV2Impl.Errorln(args...) + } +} + +// FatalDepth logs to the FATAL log at the specified depth. +// +// # Experimental +// +// Notice: This API is EXPERIMENTAL and may be changed or removed in a +// later release. +func FatalDepth(depth int, args ...any) { + if internal.DepthLoggerV2Impl != nil { + internal.DepthLoggerV2Impl.FatalDepth(depth, args...) + } else { + internal.LoggerV2Impl.Fatalln(args...) + } + os.Exit(1) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/grpclog.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/grpclog.go new file mode 100644 index 00000000000..59c03bc14c2 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/grpclog.go @@ -0,0 +1,26 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 internal contains functionality internal to the grpclog package. +package internal + +// LoggerV2Impl is the logger used for the non-depth log functions. +var LoggerV2Impl LoggerV2 + +// DepthLoggerV2Impl is the logger used for the depth log functions. +var DepthLoggerV2Impl DepthLoggerV2 diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/logger.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/logger.go new file mode 100644 index 00000000000..e524fdd40b2 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/logger.go @@ -0,0 +1,87 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 internal + +// Logger mimics golang's standard Logger as an interface. +// +// Deprecated: use LoggerV2. +type Logger interface { + Fatal(args ...any) + Fatalf(format string, args ...any) + Fatalln(args ...any) + Print(args ...any) + Printf(format string, args ...any) + Println(args ...any) +} + +// LoggerWrapper wraps Logger into a LoggerV2. +type LoggerWrapper struct { + Logger +} + +// Info logs to INFO log. Arguments are handled in the manner of fmt.Print. +func (l *LoggerWrapper) Info(args ...any) { + l.Logger.Print(args...) +} + +// Infoln logs to INFO log. Arguments are handled in the manner of fmt.Println. +func (l *LoggerWrapper) Infoln(args ...any) { + l.Logger.Println(args...) +} + +// Infof logs to INFO log. Arguments are handled in the manner of fmt.Printf. +func (l *LoggerWrapper) Infof(format string, args ...any) { + l.Logger.Printf(format, args...) +} + +// Warning logs to WARNING log. Arguments are handled in the manner of fmt.Print. +func (l *LoggerWrapper) Warning(args ...any) { + l.Logger.Print(args...) +} + +// Warningln logs to WARNING log. Arguments are handled in the manner of fmt.Println. +func (l *LoggerWrapper) Warningln(args ...any) { + l.Logger.Println(args...) +} + +// Warningf logs to WARNING log. Arguments are handled in the manner of fmt.Printf. +func (l *LoggerWrapper) Warningf(format string, args ...any) { + l.Logger.Printf(format, args...) +} + +// Error logs to ERROR log. Arguments are handled in the manner of fmt.Print. +func (l *LoggerWrapper) Error(args ...any) { + l.Logger.Print(args...) +} + +// Errorln logs to ERROR log. Arguments are handled in the manner of fmt.Println. +func (l *LoggerWrapper) Errorln(args ...any) { + l.Logger.Println(args...) +} + +// Errorf logs to ERROR log. Arguments are handled in the manner of fmt.Printf. +func (l *LoggerWrapper) Errorf(format string, args ...any) { + l.Logger.Printf(format, args...) +} + +// V reports whether verbosity level l is at least the requested verbose level. +func (*LoggerWrapper) V(int) bool { + // Returns true for all verbose level. + return true +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/grpclog.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/loggerv2.go similarity index 52% rename from cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/grpclog.go rename to cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/loggerv2.go index bfc45102ab2..07df71e98a8 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/grpclog.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/internal/loggerv2.go @@ -1,6 +1,6 @@ /* * - * Copyright 2020 gRPC authors. + * Copyright 2024 gRPC authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -16,59 +16,17 @@ * */ -// Package grpclog (internal) defines depth logging for grpc. -package grpclog +package internal import ( + "encoding/json" + "fmt" + "io" + "log" "os" ) -// Logger is the logger used for the non-depth log functions. -var Logger LoggerV2 - -// DepthLogger is the logger used for the depth log functions. -var DepthLogger DepthLoggerV2 - -// InfoDepth logs to the INFO log at the specified depth. -func InfoDepth(depth int, args ...any) { - if DepthLogger != nil { - DepthLogger.InfoDepth(depth, args...) - } else { - Logger.Infoln(args...) - } -} - -// WarningDepth logs to the WARNING log at the specified depth. -func WarningDepth(depth int, args ...any) { - if DepthLogger != nil { - DepthLogger.WarningDepth(depth, args...) - } else { - Logger.Warningln(args...) - } -} - -// ErrorDepth logs to the ERROR log at the specified depth. -func ErrorDepth(depth int, args ...any) { - if DepthLogger != nil { - DepthLogger.ErrorDepth(depth, args...) - } else { - Logger.Errorln(args...) - } -} - -// FatalDepth logs to the FATAL log at the specified depth. -func FatalDepth(depth int, args ...any) { - if DepthLogger != nil { - DepthLogger.FatalDepth(depth, args...) - } else { - Logger.Fatalln(args...) - } - os.Exit(1) -} - // LoggerV2 does underlying logging work for grpclog. -// This is a copy of the LoggerV2 defined in the external grpclog package. It -// is defined here to avoid a circular dependency. type LoggerV2 interface { // Info logs to INFO log. Arguments are handled in the manner of fmt.Print. Info(args ...any) @@ -107,14 +65,13 @@ type LoggerV2 interface { // DepthLoggerV2 logs at a specified call frame. If a LoggerV2 also implements // DepthLoggerV2, the below functions will be called with the appropriate stack // depth set for trivial functions the logger may ignore. -// This is a copy of the DepthLoggerV2 defined in the external grpclog package. -// It is defined here to avoid a circular dependency. // // # Experimental // // Notice: This type is EXPERIMENTAL and may be changed or removed in a // later release. type DepthLoggerV2 interface { + LoggerV2 // InfoDepth logs to INFO log at the specified depth. Arguments are handled in the manner of fmt.Println. InfoDepth(depth int, args ...any) // WarningDepth logs to WARNING log at the specified depth. Arguments are handled in the manner of fmt.Println. @@ -124,3 +81,124 @@ type DepthLoggerV2 interface { // FatalDepth logs to FATAL log at the specified depth. Arguments are handled in the manner of fmt.Println. FatalDepth(depth int, args ...any) } + +const ( + // infoLog indicates Info severity. + infoLog int = iota + // warningLog indicates Warning severity. + warningLog + // errorLog indicates Error severity. + errorLog + // fatalLog indicates Fatal severity. + fatalLog +) + +// severityName contains the string representation of each severity. +var severityName = []string{ + infoLog: "INFO", + warningLog: "WARNING", + errorLog: "ERROR", + fatalLog: "FATAL", +} + +// loggerT is the default logger used by grpclog. +type loggerT struct { + m []*log.Logger + v int + jsonFormat bool +} + +func (g *loggerT) output(severity int, s string) { + sevStr := severityName[severity] + if !g.jsonFormat { + g.m[severity].Output(2, fmt.Sprintf("%v: %v", sevStr, s)) + return + } + // TODO: we can also include the logging component, but that needs more + // (API) changes. + b, _ := json.Marshal(map[string]string{ + "severity": sevStr, + "message": s, + }) + g.m[severity].Output(2, string(b)) +} + +func (g *loggerT) Info(args ...any) { + g.output(infoLog, fmt.Sprint(args...)) +} + +func (g *loggerT) Infoln(args ...any) { + g.output(infoLog, fmt.Sprintln(args...)) +} + +func (g *loggerT) Infof(format string, args ...any) { + g.output(infoLog, fmt.Sprintf(format, args...)) +} + +func (g *loggerT) Warning(args ...any) { + g.output(warningLog, fmt.Sprint(args...)) +} + +func (g *loggerT) Warningln(args ...any) { + g.output(warningLog, fmt.Sprintln(args...)) +} + +func (g *loggerT) Warningf(format string, args ...any) { + g.output(warningLog, fmt.Sprintf(format, args...)) +} + +func (g *loggerT) Error(args ...any) { + g.output(errorLog, fmt.Sprint(args...)) +} + +func (g *loggerT) Errorln(args ...any) { + g.output(errorLog, fmt.Sprintln(args...)) +} + +func (g *loggerT) Errorf(format string, args ...any) { + g.output(errorLog, fmt.Sprintf(format, args...)) +} + +func (g *loggerT) Fatal(args ...any) { + g.output(fatalLog, fmt.Sprint(args...)) + os.Exit(1) +} + +func (g *loggerT) Fatalln(args ...any) { + g.output(fatalLog, fmt.Sprintln(args...)) + os.Exit(1) +} + +func (g *loggerT) Fatalf(format string, args ...any) { + g.output(fatalLog, fmt.Sprintf(format, args...)) + os.Exit(1) +} + +func (g *loggerT) V(l int) bool { + return l <= g.v +} + +// LoggerV2Config configures the LoggerV2 implementation. +type LoggerV2Config struct { + // Verbosity sets the verbosity level of the logger. + Verbosity int + // FormatJSON controls whether the logger should output logs in JSON format. + FormatJSON bool +} + +// NewLoggerV2 creates a new LoggerV2 instance with the provided configuration. +// The infoW, warningW, and errorW writers are used to write log messages of +// different severity levels. +func NewLoggerV2(infoW, warningW, errorW io.Writer, c LoggerV2Config) LoggerV2 { + var m []*log.Logger + flag := log.LstdFlags + if c.FormatJSON { + flag = 0 + } + m = append(m, log.New(infoW, "", flag)) + m = append(m, log.New(io.MultiWriter(infoW, warningW), "", flag)) + ew := io.MultiWriter(infoW, warningW, errorW) // ew will be used for error and fatal. + m = append(m, log.New(ew, "", flag)) + m = append(m, log.New(ew, "", flag)) + return &loggerT{m: m, v: c.Verbosity, jsonFormat: c.FormatJSON} +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/logger.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/logger.go index b1674d8267c..4b203585707 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/logger.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/logger.go @@ -18,70 +18,17 @@ package grpclog -import "google.golang.org/grpc/internal/grpclog" +import "google.golang.org/grpc/grpclog/internal" // Logger mimics golang's standard Logger as an interface. // // Deprecated: use LoggerV2. -type Logger interface { - Fatal(args ...any) - Fatalf(format string, args ...any) - Fatalln(args ...any) - Print(args ...any) - Printf(format string, args ...any) - Println(args ...any) -} +type Logger internal.Logger // SetLogger sets the logger that is used in grpc. Call only from // init() functions. // // Deprecated: use SetLoggerV2. func SetLogger(l Logger) { - grpclog.Logger = &loggerWrapper{Logger: l} -} - -// loggerWrapper wraps Logger into a LoggerV2. -type loggerWrapper struct { - Logger -} - -func (g *loggerWrapper) Info(args ...any) { - g.Logger.Print(args...) -} - -func (g *loggerWrapper) Infoln(args ...any) { - g.Logger.Println(args...) -} - -func (g *loggerWrapper) Infof(format string, args ...any) { - g.Logger.Printf(format, args...) -} - -func (g *loggerWrapper) Warning(args ...any) { - g.Logger.Print(args...) -} - -func (g *loggerWrapper) Warningln(args ...any) { - g.Logger.Println(args...) -} - -func (g *loggerWrapper) Warningf(format string, args ...any) { - g.Logger.Printf(format, args...) -} - -func (g *loggerWrapper) Error(args ...any) { - g.Logger.Print(args...) -} - -func (g *loggerWrapper) Errorln(args ...any) { - g.Logger.Println(args...) -} - -func (g *loggerWrapper) Errorf(format string, args ...any) { - g.Logger.Printf(format, args...) -} - -func (g *loggerWrapper) V(l int) bool { - // Returns true for all verbose level. - return true + internal.LoggerV2Impl = &internal.LoggerWrapper{Logger: l} } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/loggerv2.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/loggerv2.go index ecfd36d7130..892dc13d164 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/loggerv2.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/grpclog/loggerv2.go @@ -19,52 +19,16 @@ package grpclog import ( - "encoding/json" - "fmt" "io" - "log" "os" "strconv" "strings" - "google.golang.org/grpc/internal/grpclog" + "google.golang.org/grpc/grpclog/internal" ) // LoggerV2 does underlying logging work for grpclog. -type LoggerV2 interface { - // Info logs to INFO log. Arguments are handled in the manner of fmt.Print. - Info(args ...any) - // Infoln logs to INFO log. Arguments are handled in the manner of fmt.Println. - Infoln(args ...any) - // Infof logs to INFO log. Arguments are handled in the manner of fmt.Printf. - Infof(format string, args ...any) - // Warning logs to WARNING log. Arguments are handled in the manner of fmt.Print. - Warning(args ...any) - // Warningln logs to WARNING log. Arguments are handled in the manner of fmt.Println. - Warningln(args ...any) - // Warningf logs to WARNING log. Arguments are handled in the manner of fmt.Printf. - Warningf(format string, args ...any) - // Error logs to ERROR log. Arguments are handled in the manner of fmt.Print. - Error(args ...any) - // Errorln logs to ERROR log. Arguments are handled in the manner of fmt.Println. - Errorln(args ...any) - // Errorf logs to ERROR log. Arguments are handled in the manner of fmt.Printf. - Errorf(format string, args ...any) - // Fatal logs to ERROR log. Arguments are handled in the manner of fmt.Print. - // gRPC ensures that all Fatal logs will exit with os.Exit(1). - // Implementations may also call os.Exit() with a non-zero exit code. - Fatal(args ...any) - // Fatalln logs to ERROR log. Arguments are handled in the manner of fmt.Println. - // gRPC ensures that all Fatal logs will exit with os.Exit(1). - // Implementations may also call os.Exit() with a non-zero exit code. - Fatalln(args ...any) - // Fatalf logs to ERROR log. Arguments are handled in the manner of fmt.Printf. - // gRPC ensures that all Fatal logs will exit with os.Exit(1). - // Implementations may also call os.Exit() with a non-zero exit code. - Fatalf(format string, args ...any) - // V reports whether verbosity level l is at least the requested verbose level. - V(l int) bool -} +type LoggerV2 internal.LoggerV2 // SetLoggerV2 sets logger that is used in grpc to a V2 logger. // Not mutex-protected, should be called before any gRPC functions. @@ -72,34 +36,8 @@ func SetLoggerV2(l LoggerV2) { if _, ok := l.(*componentData); ok { panic("cannot use component logger as grpclog logger") } - grpclog.Logger = l - grpclog.DepthLogger, _ = l.(grpclog.DepthLoggerV2) -} - -const ( - // infoLog indicates Info severity. - infoLog int = iota - // warningLog indicates Warning severity. - warningLog - // errorLog indicates Error severity. - errorLog - // fatalLog indicates Fatal severity. - fatalLog -) - -// severityName contains the string representation of each severity. -var severityName = []string{ - infoLog: "INFO", - warningLog: "WARNING", - errorLog: "ERROR", - fatalLog: "FATAL", -} - -// loggerT is the default logger used by grpclog. -type loggerT struct { - m []*log.Logger - v int - jsonFormat bool + internal.LoggerV2Impl = l + internal.DepthLoggerV2Impl, _ = l.(internal.DepthLoggerV2) } // NewLoggerV2 creates a loggerV2 with the provided writers. @@ -108,32 +46,13 @@ type loggerT struct { // Warning logs will be written to warningW and infoW. // Info logs will be written to infoW. func NewLoggerV2(infoW, warningW, errorW io.Writer) LoggerV2 { - return newLoggerV2WithConfig(infoW, warningW, errorW, loggerV2Config{}) + return internal.NewLoggerV2(infoW, warningW, errorW, internal.LoggerV2Config{}) } // NewLoggerV2WithVerbosity creates a loggerV2 with the provided writers and // verbosity level. func NewLoggerV2WithVerbosity(infoW, warningW, errorW io.Writer, v int) LoggerV2 { - return newLoggerV2WithConfig(infoW, warningW, errorW, loggerV2Config{verbose: v}) -} - -type loggerV2Config struct { - verbose int - jsonFormat bool -} - -func newLoggerV2WithConfig(infoW, warningW, errorW io.Writer, c loggerV2Config) LoggerV2 { - var m []*log.Logger - flag := log.LstdFlags - if c.jsonFormat { - flag = 0 - } - m = append(m, log.New(infoW, "", flag)) - m = append(m, log.New(io.MultiWriter(infoW, warningW), "", flag)) - ew := io.MultiWriter(infoW, warningW, errorW) // ew will be used for error and fatal. - m = append(m, log.New(ew, "", flag)) - m = append(m, log.New(ew, "", flag)) - return &loggerT{m: m, v: c.verbose, jsonFormat: c.jsonFormat} + return internal.NewLoggerV2(infoW, warningW, errorW, internal.LoggerV2Config{Verbosity: v}) } // newLoggerV2 creates a loggerV2 to be used as default logger. @@ -161,80 +80,10 @@ func newLoggerV2() LoggerV2 { jsonFormat := strings.EqualFold(os.Getenv("GRPC_GO_LOG_FORMATTER"), "json") - return newLoggerV2WithConfig(infoW, warningW, errorW, loggerV2Config{ - verbose: v, - jsonFormat: jsonFormat, - }) -} - -func (g *loggerT) output(severity int, s string) { - sevStr := severityName[severity] - if !g.jsonFormat { - g.m[severity].Output(2, fmt.Sprintf("%v: %v", sevStr, s)) - return - } - // TODO: we can also include the logging component, but that needs more - // (API) changes. - b, _ := json.Marshal(map[string]string{ - "severity": sevStr, - "message": s, + return internal.NewLoggerV2(infoW, warningW, errorW, internal.LoggerV2Config{ + Verbosity: v, + FormatJSON: jsonFormat, }) - g.m[severity].Output(2, string(b)) -} - -func (g *loggerT) Info(args ...any) { - g.output(infoLog, fmt.Sprint(args...)) -} - -func (g *loggerT) Infoln(args ...any) { - g.output(infoLog, fmt.Sprintln(args...)) -} - -func (g *loggerT) Infof(format string, args ...any) { - g.output(infoLog, fmt.Sprintf(format, args...)) -} - -func (g *loggerT) Warning(args ...any) { - g.output(warningLog, fmt.Sprint(args...)) -} - -func (g *loggerT) Warningln(args ...any) { - g.output(warningLog, fmt.Sprintln(args...)) -} - -func (g *loggerT) Warningf(format string, args ...any) { - g.output(warningLog, fmt.Sprintf(format, args...)) -} - -func (g *loggerT) Error(args ...any) { - g.output(errorLog, fmt.Sprint(args...)) -} - -func (g *loggerT) Errorln(args ...any) { - g.output(errorLog, fmt.Sprintln(args...)) -} - -func (g *loggerT) Errorf(format string, args ...any) { - g.output(errorLog, fmt.Sprintf(format, args...)) -} - -func (g *loggerT) Fatal(args ...any) { - g.output(fatalLog, fmt.Sprint(args...)) - os.Exit(1) -} - -func (g *loggerT) Fatalln(args ...any) { - g.output(fatalLog, fmt.Sprintln(args...)) - os.Exit(1) -} - -func (g *loggerT) Fatalf(format string, args ...any) { - g.output(fatalLog, fmt.Sprintf(format, args...)) - os.Exit(1) -} - -func (g *loggerT) V(l int) bool { - return l <= g.v } // DepthLoggerV2 logs at a specified call frame. If a LoggerV2 also implements @@ -245,14 +94,4 @@ func (g *loggerT) V(l int) bool { // // Notice: This type is EXPERIMENTAL and may be changed or removed in a // later release. -type DepthLoggerV2 interface { - LoggerV2 - // InfoDepth logs to INFO log at the specified depth. Arguments are handled in the manner of fmt.Println. - InfoDepth(depth int, args ...any) - // WarningDepth logs to WARNING log at the specified depth. Arguments are handled in the manner of fmt.Println. - WarningDepth(depth int, args ...any) - // ErrorDepth logs to ERROR log at the specified depth. Arguments are handled in the manner of fmt.Println. - ErrorDepth(depth int, args ...any) - // FatalDepth logs to FATAL log at the specified depth. Arguments are handled in the manner of fmt.Println. - FatalDepth(depth int, args ...any) -} +type DepthLoggerV2 internal.DepthLoggerV2 diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go index 38b88350735..d92335445f6 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health.pb.go @@ -17,8 +17,8 @@ // Code generated by protoc-gen-go. DO NOT EDIT. // versions: -// protoc-gen-go v1.34.1 -// protoc v4.25.2 +// protoc-gen-go v1.34.2 +// protoc v5.27.1 // source: grpc/health/v1/health.proto package grpc_health_v1 @@ -237,7 +237,7 @@ func file_grpc_health_v1_health_proto_rawDescGZIP() []byte { var file_grpc_health_v1_health_proto_enumTypes = make([]protoimpl.EnumInfo, 1) var file_grpc_health_v1_health_proto_msgTypes = make([]protoimpl.MessageInfo, 2) -var file_grpc_health_v1_health_proto_goTypes = []interface{}{ +var file_grpc_health_v1_health_proto_goTypes = []any{ (HealthCheckResponse_ServingStatus)(0), // 0: grpc.health.v1.HealthCheckResponse.ServingStatus (*HealthCheckRequest)(nil), // 1: grpc.health.v1.HealthCheckRequest (*HealthCheckResponse)(nil), // 2: grpc.health.v1.HealthCheckResponse @@ -261,7 +261,7 @@ func file_grpc_health_v1_health_proto_init() { return } if !protoimpl.UnsafeEnabled { - file_grpc_health_v1_health_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { + file_grpc_health_v1_health_proto_msgTypes[0].Exporter = func(v any, i int) any { switch v := v.(*HealthCheckRequest); i { case 0: return &v.state @@ -273,7 +273,7 @@ func file_grpc_health_v1_health_proto_init() { return nil } } - file_grpc_health_v1_health_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { + file_grpc_health_v1_health_proto_msgTypes[1].Exporter = func(v any, i int) any { switch v := v.(*HealthCheckResponse); i { case 0: return &v.state diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health_grpc.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health_grpc.pb.go index 51b736ba06e..f96b8ab4927 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health_grpc.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/health/grpc_health_v1/health_grpc.pb.go @@ -17,8 +17,8 @@ // Code generated by protoc-gen-go-grpc. DO NOT EDIT. // versions: -// - protoc-gen-go-grpc v1.4.0 -// - protoc v4.25.2 +// - protoc-gen-go-grpc v1.5.1 +// - protoc v5.27.1 // source: grpc/health/v1/health.proto package grpc_health_v1 @@ -32,8 +32,8 @@ import ( // This is a compile-time assertion to ensure that this generated file // is compatible with the grpc package it is being compiled against. -// Requires gRPC-Go v1.62.0 or later. -const _ = grpc.SupportPackageIsVersion8 +// Requires gRPC-Go v1.64.0 or later. +const _ = grpc.SupportPackageIsVersion9 const ( Health_Check_FullMethodName = "/grpc.health.v1.Health/Check" @@ -73,7 +73,7 @@ type HealthClient interface { // should assume this method is not supported and should not retry the // call. If the call terminates with any other status (including OK), // clients should retry the call with appropriate exponential backoff. - Watch(ctx context.Context, in *HealthCheckRequest, opts ...grpc.CallOption) (Health_WatchClient, error) + Watch(ctx context.Context, in *HealthCheckRequest, opts ...grpc.CallOption) (grpc.ServerStreamingClient[HealthCheckResponse], error) } type healthClient struct { @@ -94,13 +94,13 @@ func (c *healthClient) Check(ctx context.Context, in *HealthCheckRequest, opts . return out, nil } -func (c *healthClient) Watch(ctx context.Context, in *HealthCheckRequest, opts ...grpc.CallOption) (Health_WatchClient, error) { +func (c *healthClient) Watch(ctx context.Context, in *HealthCheckRequest, opts ...grpc.CallOption) (grpc.ServerStreamingClient[HealthCheckResponse], error) { cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) stream, err := c.cc.NewStream(ctx, &Health_ServiceDesc.Streams[0], Health_Watch_FullMethodName, cOpts...) if err != nil { return nil, err } - x := &healthWatchClient{ClientStream: stream} + x := &grpc.GenericClientStream[HealthCheckRequest, HealthCheckResponse]{ClientStream: stream} if err := x.ClientStream.SendMsg(in); err != nil { return nil, err } @@ -110,26 +110,12 @@ func (c *healthClient) Watch(ctx context.Context, in *HealthCheckRequest, opts . return x, nil } -type Health_WatchClient interface { - Recv() (*HealthCheckResponse, error) - grpc.ClientStream -} - -type healthWatchClient struct { - grpc.ClientStream -} - -func (x *healthWatchClient) Recv() (*HealthCheckResponse, error) { - m := new(HealthCheckResponse) - if err := x.ClientStream.RecvMsg(m); err != nil { - return nil, err - } - return m, nil -} +// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. +type Health_WatchClient = grpc.ServerStreamingClient[HealthCheckResponse] // HealthServer is the server API for Health service. // All implementations should embed UnimplementedHealthServer -// for forward compatibility +// for forward compatibility. // // Health is gRPC's mechanism for checking whether a server is able to handle // RPCs. Its semantics are documented in @@ -160,19 +146,23 @@ type HealthServer interface { // should assume this method is not supported and should not retry the // call. If the call terminates with any other status (including OK), // clients should retry the call with appropriate exponential backoff. - Watch(*HealthCheckRequest, Health_WatchServer) error + Watch(*HealthCheckRequest, grpc.ServerStreamingServer[HealthCheckResponse]) error } -// UnimplementedHealthServer should be embedded to have forward compatible implementations. -type UnimplementedHealthServer struct { -} +// UnimplementedHealthServer should be embedded to have +// forward compatible implementations. +// +// NOTE: this should be embedded by value instead of pointer to avoid a nil +// pointer dereference when methods are called. +type UnimplementedHealthServer struct{} func (UnimplementedHealthServer) Check(context.Context, *HealthCheckRequest) (*HealthCheckResponse, error) { return nil, status.Errorf(codes.Unimplemented, "method Check not implemented") } -func (UnimplementedHealthServer) Watch(*HealthCheckRequest, Health_WatchServer) error { +func (UnimplementedHealthServer) Watch(*HealthCheckRequest, grpc.ServerStreamingServer[HealthCheckResponse]) error { return status.Errorf(codes.Unimplemented, "method Watch not implemented") } +func (UnimplementedHealthServer) testEmbeddedByValue() {} // UnsafeHealthServer may be embedded to opt out of forward compatibility for this service. // Use of this interface is not recommended, as added methods to HealthServer will @@ -182,6 +172,13 @@ type UnsafeHealthServer interface { } func RegisterHealthServer(s grpc.ServiceRegistrar, srv HealthServer) { + // If the following call panics, it indicates UnimplementedHealthServer was + // embedded by pointer and is nil. This will cause panics if an + // unimplemented method is ever invoked, so we test this at initialization + // time to prevent it from happening at runtime later due to I/O. + if t, ok := srv.(interface{ testEmbeddedByValue() }); ok { + t.testEmbeddedByValue() + } s.RegisterService(&Health_ServiceDesc, srv) } @@ -208,21 +205,11 @@ func _Health_Watch_Handler(srv interface{}, stream grpc.ServerStream) error { if err := stream.RecvMsg(m); err != nil { return err } - return srv.(HealthServer).Watch(m, &healthWatchServer{ServerStream: stream}) -} - -type Health_WatchServer interface { - Send(*HealthCheckResponse) error - grpc.ServerStream + return srv.(HealthServer).Watch(m, &grpc.GenericServerStream[HealthCheckRequest, HealthCheckResponse]{ServerStream: stream}) } -type healthWatchServer struct { - grpc.ServerStream -} - -func (x *healthWatchServer) Send(m *HealthCheckResponse) error { - return x.ServerStream.SendMsg(m) -} +// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. +type Health_WatchServer = grpc.ServerStreamingServer[HealthCheckResponse] // Health_ServiceDesc is the grpc.ServiceDesc for Health service. // It's only intended for direct use with grpc.RegisterService, diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/binarylog/method_logger.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/binarylog/method_logger.go index aa4505a871d..9669328914a 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/binarylog/method_logger.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/binarylog/method_logger.go @@ -106,7 +106,7 @@ func (ml *TruncatingMethodLogger) Build(c LogEntryConfig) *binlogpb.GrpcLogEntry } // Log creates a proto binary log entry, and logs it to the sink. -func (ml *TruncatingMethodLogger) Log(ctx context.Context, c LogEntryConfig) { +func (ml *TruncatingMethodLogger) Log(_ context.Context, c LogEntryConfig) { ml.sink.Write(ml.Build(c)) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/channelmap.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/channelmap.go index dfe18b08925..64c791953d0 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/channelmap.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/channelmap.go @@ -46,7 +46,7 @@ type entry interface { // channelMap is the storage data structure for channelz. // -// Methods of channelMap can be divided in two two categories with respect to +// Methods of channelMap can be divided into two categories with respect to // locking. // // 1. Methods acquire the global lock. @@ -234,13 +234,6 @@ func copyMap(m map[int64]string) map[int64]string { return n } -func min(a, b int) int { - if a < b { - return a - } - return b -} - func (c *channelMap) getTopChannels(id int64, maxResults int) ([]*Channel, bool) { if maxResults <= 0 { maxResults = EntriesPerPage diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/funcs.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/funcs.go index 03e24e1507a..078bb81238b 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/funcs.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/funcs.go @@ -33,7 +33,7 @@ var ( // outside this package except by tests. IDGen IDGenerator - db *channelMap = newChannelMap() + db = newChannelMap() // EntriesPerPage defines the number of channelz entries to be shown on a web page. EntriesPerPage = 50 curState int32 diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/syscall_nonlinux.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/syscall_nonlinux.go index d1ed8df6a51..0e6e18e185c 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/syscall_nonlinux.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/channelz/syscall_nonlinux.go @@ -35,13 +35,13 @@ type SocketOptionData struct { // Getsockopt defines the function to get socket options requested by channelz. // It is to be passed to syscall.RawConn.Control(). // Windows OS doesn't support Socket Option -func (s *SocketOptionData) Getsockopt(fd uintptr) { +func (s *SocketOptionData) Getsockopt(uintptr) { once.Do(func() { logger.Warning("Channelz: socket options are not supported on non-linux environments") }) } // GetSocketOption gets the socket option info of the conn. -func GetSocketOption(c any) *SocketOptionData { +func GetSocketOption(any) *SocketOptionData { return nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/envconfig/envconfig.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/envconfig/envconfig.go index d9064871394..452985f8d8f 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/envconfig/envconfig.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/envconfig/envconfig.go @@ -45,7 +45,11 @@ var ( // option is present for backward compatibility. This option may be overridden // by setting the environment variable "GRPC_ENFORCE_ALPN_ENABLED" to "true" // or "false". - EnforceALPNEnabled = boolFromEnv("GRPC_ENFORCE_ALPN_ENABLED", false) + EnforceALPNEnabled = boolFromEnv("GRPC_ENFORCE_ALPN_ENABLED", true) + // XDSFallbackSupport is the env variable that controls whether support for + // xDS fallback is turned on. If this is unset or is false, only the first + // xDS server in the list of server configs will be used. + XDSFallbackSupport = boolFromEnv("GRPC_EXPERIMENTAL_XDS_FALLBACK", false) ) func boolFromEnv(envVar string, def bool) bool { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/experimental.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/experimental.go index 7f7044e1731..7617be21589 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/experimental.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/experimental.go @@ -18,11 +18,11 @@ package internal var ( - // WithRecvBufferPool is implemented by the grpc package and returns a dial + // WithBufferPool is implemented by the grpc package and returns a dial // option to configure a shared buffer pool for a grpc.ClientConn. - WithRecvBufferPool any // func (grpc.SharedBufferPool) grpc.DialOption + WithBufferPool any // func (grpc.SharedBufferPool) grpc.DialOption - // RecvBufferPool is implemented by the grpc package and returns a server + // BufferPool is implemented by the grpc package and returns a server // option to configure a shared buffer pool for a grpc.Server. - RecvBufferPool any // func (grpc.SharedBufferPool) grpc.ServerOption + BufferPool any // func (grpc.SharedBufferPool) grpc.ServerOption ) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/prefixLogger.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/prefix_logger.go similarity index 63% rename from cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/prefixLogger.go rename to cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/prefix_logger.go index faa998de763..092ad187a2c 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/prefixLogger.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpclog/prefix_logger.go @@ -16,17 +16,21 @@ * */ +// Package grpclog provides logging functionality for internal gRPC packages, +// outside of the functionality provided by the external `grpclog` package. package grpclog import ( "fmt" + + "google.golang.org/grpc/grpclog" ) // PrefixLogger does logging with a prefix. // // Logging method on a nil logs without any prefix. type PrefixLogger struct { - logger DepthLoggerV2 + logger grpclog.DepthLoggerV2 prefix string } @@ -38,7 +42,7 @@ func (pl *PrefixLogger) Infof(format string, args ...any) { pl.logger.InfoDepth(1, fmt.Sprintf(format, args...)) return } - InfoDepth(1, fmt.Sprintf(format, args...)) + grpclog.InfoDepth(1, fmt.Sprintf(format, args...)) } // Warningf does warning logging. @@ -48,7 +52,7 @@ func (pl *PrefixLogger) Warningf(format string, args ...any) { pl.logger.WarningDepth(1, fmt.Sprintf(format, args...)) return } - WarningDepth(1, fmt.Sprintf(format, args...)) + grpclog.WarningDepth(1, fmt.Sprintf(format, args...)) } // Errorf does error logging. @@ -58,36 +62,18 @@ func (pl *PrefixLogger) Errorf(format string, args ...any) { pl.logger.ErrorDepth(1, fmt.Sprintf(format, args...)) return } - ErrorDepth(1, fmt.Sprintf(format, args...)) -} - -// Debugf does info logging at verbose level 2. -func (pl *PrefixLogger) Debugf(format string, args ...any) { - // TODO(6044): Refactor interfaces LoggerV2 and DepthLogger, and maybe - // rewrite PrefixLogger a little to ensure that we don't use the global - // `Logger` here, and instead use the `logger` field. - if !Logger.V(2) { - return - } - if pl != nil { - // Handle nil, so the tests can pass in a nil logger. - format = pl.prefix + format - pl.logger.InfoDepth(1, fmt.Sprintf(format, args...)) - return - } - InfoDepth(1, fmt.Sprintf(format, args...)) - + grpclog.ErrorDepth(1, fmt.Sprintf(format, args...)) } // V reports whether verbosity level l is at least the requested verbose level. func (pl *PrefixLogger) V(l int) bool { - // TODO(6044): Refactor interfaces LoggerV2 and DepthLogger, and maybe - // rewrite PrefixLogger a little to ensure that we don't use the global - // `Logger` here, and instead use the `logger` field. - return Logger.V(l) + if pl != nil { + return pl.logger.V(l) + } + return true } // NewPrefixLogger creates a prefix logger with the given prefix. -func NewPrefixLogger(logger DepthLoggerV2, prefix string) *PrefixLogger { +func NewPrefixLogger(logger grpclog.DepthLoggerV2, prefix string) *PrefixLogger { return &PrefixLogger{logger: logger, prefix: prefix} } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/callback_serializer.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/callback_serializer.go index f7f40a16ace..19b9d639275 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/callback_serializer.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/callback_serializer.go @@ -53,16 +53,28 @@ func NewCallbackSerializer(ctx context.Context) *CallbackSerializer { return cs } -// Schedule adds a callback to be scheduled after existing callbacks are run. +// TrySchedule tries to schedules the provided callback function f to be +// executed in the order it was added. This is a best-effort operation. If the +// context passed to NewCallbackSerializer was canceled before this method is +// called, the callback will not be scheduled. // // Callbacks are expected to honor the context when performing any blocking // operations, and should return early when the context is canceled. +func (cs *CallbackSerializer) TrySchedule(f func(ctx context.Context)) { + cs.callbacks.Put(f) +} + +// ScheduleOr schedules the provided callback function f to be executed in the +// order it was added. If the context passed to NewCallbackSerializer has been +// canceled before this method is called, the onFailure callback will be +// executed inline instead. // -// Return value indicates if the callback was successfully added to the list of -// callbacks to be executed by the serializer. It is not possible to add -// callbacks once the context passed to NewCallbackSerializer is cancelled. -func (cs *CallbackSerializer) Schedule(f func(ctx context.Context)) bool { - return cs.callbacks.Put(f) == nil +// Callbacks are expected to honor the context when performing any blocking +// operations, and should return early when the context is canceled. +func (cs *CallbackSerializer) ScheduleOr(f func(ctx context.Context), onFailure func()) { + if cs.callbacks.Put(f) != nil { + onFailure() + } } func (cs *CallbackSerializer) run(ctx context.Context) { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/pubsub.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/pubsub.go index aef8cec1ab0..6d8c2f518df 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/pubsub.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/grpcsync/pubsub.go @@ -77,7 +77,7 @@ func (ps *PubSub) Subscribe(sub Subscriber) (cancel func()) { if ps.msg != nil { msg := ps.msg - ps.cs.Schedule(func(context.Context) { + ps.cs.TrySchedule(func(context.Context) { ps.mu.Lock() defer ps.mu.Unlock() if !ps.subscribers[sub] { @@ -103,7 +103,7 @@ func (ps *PubSub) Publish(msg any) { ps.msg = msg for sub := range ps.subscribers { s := sub - ps.cs.Schedule(func(context.Context) { + ps.cs.TrySchedule(func(context.Context) { ps.mu.Lock() defer ps.mu.Unlock() if !ps.subscribers[s] { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/internal.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/internal.go index 5d665398692..7aae9240ffc 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/internal.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/internal.go @@ -183,7 +183,7 @@ var ( // GRPCResolverSchemeExtraMetadata determines when gRPC will add extra // metadata to RPCs. - GRPCResolverSchemeExtraMetadata string = "xds" + GRPCResolverSchemeExtraMetadata = "xds" // EnterIdleModeForTesting gets the ClientConn to enter IDLE mode. EnterIdleModeForTesting any // func(*grpc.ClientConn) @@ -203,11 +203,31 @@ var ( // UserSetDefaultScheme is set to true if the user has overridden the // default resolver scheme. - UserSetDefaultScheme bool = false + UserSetDefaultScheme = false // ShuffleAddressListForTesting pseudo-randomizes the order of addresses. n // is the number of elements. swap swaps the elements with indexes i and j. ShuffleAddressListForTesting any // func(n int, swap func(i, j int)) + + // ConnectedAddress returns the connected address for a SubConnState. The + // address is only valid if the state is READY. + ConnectedAddress any // func (scs SubConnState) resolver.Address + + // SetConnectedAddress sets the connected address for a SubConnState. + SetConnectedAddress any // func(scs *SubConnState, addr resolver.Address) + + // SnapshotMetricRegistryForTesting snapshots the global data of the metric + // registry. Returns a cleanup function that sets the metric registry to its + // original state. Only called in testing functions. + SnapshotMetricRegistryForTesting func() func() + + // SetDefaultBufferPoolForTesting updates the default buffer pool, for + // testing purposes. + SetDefaultBufferPoolForTesting any // func(mem.BufferPool) + + // SetBufferPoolingThresholdForTesting updates the buffer pooling threshold, for + // testing purposes. + SetBufferPoolingThresholdForTesting any // func(int) ) // HealthChecker defines the signature of the client-side LB channel health diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/dns/dns_resolver.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/dns/dns_resolver.go index 4552db16b02..e504955fb97 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/dns/dns_resolver.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/dns/dns_resolver.go @@ -237,7 +237,9 @@ func (d *dnsResolver) watcher() { } func (d *dnsResolver) lookupSRV(ctx context.Context) ([]resolver.Address, error) { - if !EnableSRVLookups { + // Skip this particular host to avoid timeouts with some versions of + // systemd-resolved. + if !EnableSRVLookups || d.host == "metadata.google.internal." { return nil, nil } var newAddrs []resolver.Address diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/passthrough/passthrough.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/passthrough/passthrough.go index afac56572ad..b901c7bace5 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/passthrough/passthrough.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/resolver/passthrough/passthrough.go @@ -55,7 +55,7 @@ func (r *passthroughResolver) start() { r.cc.UpdateState(resolver.State{Addresses: []resolver.Address{{Addr: r.target.Endpoint()}}}) } -func (*passthroughResolver) ResolveNow(o resolver.ResolveNowOptions) {} +func (*passthroughResolver) ResolveNow(resolver.ResolveNowOptions) {} func (*passthroughResolver) Close() {} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/labels.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/labels.go new file mode 100644 index 00000000000..fd33af51ae8 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/labels.go @@ -0,0 +1,42 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 stats provides internal stats related functionality. +package stats + +import "context" + +// Labels are the labels for metrics. +type Labels struct { + // TelemetryLabels are the telemetry labels to record. + TelemetryLabels map[string]string +} + +type labelsKey struct{} + +// GetLabels returns the Labels stored in the context, or nil if there is one. +func GetLabels(ctx context.Context) *Labels { + labels, _ := ctx.Value(labelsKey{}).(*Labels) + return labels +} + +// SetLabels sets the Labels in the context. +func SetLabels(ctx context.Context, labels *Labels) context.Context { + // could also append + return context.WithValue(ctx, labelsKey{}, labels) +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/metrics_recorder_list.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/metrics_recorder_list.go new file mode 100644 index 00000000000..be110d41f9a --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/stats/metrics_recorder_list.go @@ -0,0 +1,95 @@ +/* + * Copyright 2024 gRPC authors. + * + * 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 stats + +import ( + "fmt" + + estats "google.golang.org/grpc/experimental/stats" + "google.golang.org/grpc/stats" +) + +// MetricsRecorderList forwards Record calls to all of its metricsRecorders. +// +// It eats any record calls where the label values provided do not match the +// number of label keys. +type MetricsRecorderList struct { + // metricsRecorders are the metrics recorders this list will forward to. + metricsRecorders []estats.MetricsRecorder +} + +// NewMetricsRecorderList creates a new metric recorder list with all the stats +// handlers provided which implement the MetricsRecorder interface. +// If no stats handlers provided implement the MetricsRecorder interface, +// the MetricsRecorder list returned is a no-op. +func NewMetricsRecorderList(shs []stats.Handler) *MetricsRecorderList { + var mrs []estats.MetricsRecorder + for _, sh := range shs { + if mr, ok := sh.(estats.MetricsRecorder); ok { + mrs = append(mrs, mr) + } + } + return &MetricsRecorderList{ + metricsRecorders: mrs, + } +} + +func verifyLabels(desc *estats.MetricDescriptor, labelsRecv ...string) { + if got, want := len(labelsRecv), len(desc.Labels)+len(desc.OptionalLabels); got != want { + panic(fmt.Sprintf("Received %d labels in call to record metric %q, but expected %d.", got, desc.Name, want)) + } +} + +func (l *MetricsRecorderList) RecordInt64Count(handle *estats.Int64CountHandle, incr int64, labels ...string) { + verifyLabels(handle.Descriptor(), labels...) + + for _, metricRecorder := range l.metricsRecorders { + metricRecorder.RecordInt64Count(handle, incr, labels...) + } +} + +func (l *MetricsRecorderList) RecordFloat64Count(handle *estats.Float64CountHandle, incr float64, labels ...string) { + verifyLabels(handle.Descriptor(), labels...) + + for _, metricRecorder := range l.metricsRecorders { + metricRecorder.RecordFloat64Count(handle, incr, labels...) + } +} + +func (l *MetricsRecorderList) RecordInt64Histo(handle *estats.Int64HistoHandle, incr int64, labels ...string) { + verifyLabels(handle.Descriptor(), labels...) + + for _, metricRecorder := range l.metricsRecorders { + metricRecorder.RecordInt64Histo(handle, incr, labels...) + } +} + +func (l *MetricsRecorderList) RecordFloat64Histo(handle *estats.Float64HistoHandle, incr float64, labels ...string) { + verifyLabels(handle.Descriptor(), labels...) + + for _, metricRecorder := range l.metricsRecorders { + metricRecorder.RecordFloat64Histo(handle, incr, labels...) + } +} + +func (l *MetricsRecorderList) RecordInt64Gauge(handle *estats.Int64GaugeHandle, incr int64, labels ...string) { + verifyLabels(handle.Descriptor(), labels...) + + for _, metricRecorder := range l.metricsRecorders { + metricRecorder.RecordInt64Gauge(handle, incr, labels...) + } +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/status/status.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/status/status.go index c7dbc820595..757925381fe 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/status/status.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/status/status.go @@ -138,11 +138,11 @@ func (s *Status) WithDetails(details ...protoadapt.MessageV1) (*Status, error) { // s.Code() != OK implies that s.Proto() != nil. p := s.Proto() for _, detail := range details { - any, err := anypb.New(protoadapt.MessageV2Of(detail)) + m, err := anypb.New(protoadapt.MessageV2Of(detail)) if err != nil { return nil, err } - p.Details = append(p.Details, any) + p.Details = append(p.Details, m) } return &Status{s: p}, nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/syscall/syscall_nonlinux.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/syscall/syscall_nonlinux.go index 999f52cd75b..54c24c2ff38 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/syscall/syscall_nonlinux.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/syscall/syscall_nonlinux.go @@ -58,20 +58,20 @@ func GetRusage() *Rusage { // CPUTimeDiff returns the differences of user CPU time and system CPU time used // between two Rusage structs. It a no-op function for non-linux environments. -func CPUTimeDiff(first *Rusage, latest *Rusage) (float64, float64) { +func CPUTimeDiff(*Rusage, *Rusage) (float64, float64) { log() return 0, 0 } // SetTCPUserTimeout is a no-op function under non-linux environments. -func SetTCPUserTimeout(conn net.Conn, timeout time.Duration) error { +func SetTCPUserTimeout(net.Conn, time.Duration) error { log() return nil } // GetTCPUserTimeout is a no-op function under non-linux environments. // A negative return value indicates the operation is not supported -func GetTCPUserTimeout(conn net.Conn) (int, error) { +func GetTCPUserTimeout(net.Conn) (int, error) { log() return -1, nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_unix.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_unix.go index 078137b7fd7..7e7aaa54636 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_unix.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_unix.go @@ -44,7 +44,7 @@ func NetDialerWithTCPKeepalive() *net.Dialer { // combination of unconditionally enabling TCP keepalives here, and // disabling the overriding of TCP keepalive parameters by setting the // KeepAlive field to a negative value above, results in OS defaults for - // the TCP keealive interval and time parameters. + // the TCP keepalive interval and time parameters. Control: func(_, _ string, c syscall.RawConn) error { return c.Control(func(fd uintptr) { unix.SetsockoptInt(int(fd), unix.SOL_SOCKET, unix.SO_KEEPALIVE, 1) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_windows.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_windows.go index fd7d43a8907..d5c1085eeae 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_windows.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/tcp_keepalive_windows.go @@ -44,7 +44,7 @@ func NetDialerWithTCPKeepalive() *net.Dialer { // combination of unconditionally enabling TCP keepalives here, and // disabling the overriding of TCP keepalive parameters by setting the // KeepAlive field to a negative value above, results in OS defaults for - // the TCP keealive interval and time parameters. + // the TCP keepalive interval and time parameters. Control: func(_, _ string, c syscall.RawConn) error { return c.Control(func(fd uintptr) { windows.SetsockoptInt(windows.Handle(fd), windows.SOL_SOCKET, windows.SO_KEEPALIVE, 1) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/controlbuf.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/controlbuf.go index 3deadfb4a20..ef72fbb3a01 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/controlbuf.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/controlbuf.go @@ -32,6 +32,7 @@ import ( "golang.org/x/net/http2/hpack" "google.golang.org/grpc/internal/grpclog" "google.golang.org/grpc/internal/grpcutil" + "google.golang.org/grpc/mem" "google.golang.org/grpc/status" ) @@ -148,9 +149,9 @@ type dataFrame struct { streamID uint32 endStream bool h []byte - d []byte + reader mem.Reader // onEachWrite is called every time - // a part of d is written out. + // a part of data is written out. onEachWrite func() } @@ -289,18 +290,22 @@ func (l *outStreamList) dequeue() *outStream { } // controlBuffer is a way to pass information to loopy. -// Information is passed as specific struct types called control frames. -// A control frame not only represents data, messages or headers to be sent out -// but can also be used to instruct loopy to update its internal state. -// It shouldn't be confused with an HTTP2 frame, although some of the control frames -// like dataFrame and headerFrame do go out on wire as HTTP2 frames. +// +// Information is passed as specific struct types called control frames. A +// control frame not only represents data, messages or headers to be sent out +// but can also be used to instruct loopy to update its internal state. It +// shouldn't be confused with an HTTP2 frame, although some of the control +// frames like dataFrame and headerFrame do go out on wire as HTTP2 frames. type controlBuffer struct { - ch chan struct{} - done <-chan struct{} + wakeupCh chan struct{} // Unblocks readers waiting for something to read. + done <-chan struct{} // Closed when the transport is done. + + // Mutex guards all the fields below, except trfChan which can be read + // atomically without holding mu. mu sync.Mutex - consumerWaiting bool - list *itemList - err error + consumerWaiting bool // True when readers are blocked waiting for new data. + closed bool // True when the controlbuf is finished. + list *itemList // List of queued control frames. // transportResponseFrames counts the number of queued items that represent // the response of an action initiated by the peer. trfChan is created @@ -308,47 +313,59 @@ type controlBuffer struct { // closed and nilled when transportResponseFrames drops below the // threshold. Both fields are protected by mu. transportResponseFrames int - trfChan atomic.Value // chan struct{} + trfChan atomic.Pointer[chan struct{}] } func newControlBuffer(done <-chan struct{}) *controlBuffer { return &controlBuffer{ - ch: make(chan struct{}, 1), - list: &itemList{}, - done: done, + wakeupCh: make(chan struct{}, 1), + list: &itemList{}, + done: done, } } -// throttle blocks if there are too many incomingSettings/cleanupStreams in the -// controlbuf. +// throttle blocks if there are too many frames in the control buf that +// represent the response of an action initiated by the peer, like +// incomingSettings cleanupStreams etc. func (c *controlBuffer) throttle() { - ch, _ := c.trfChan.Load().(chan struct{}) - if ch != nil { + if ch := c.trfChan.Load(); ch != nil { select { - case <-ch: + case <-(*ch): case <-c.done: } } } +// put adds an item to the controlbuf. func (c *controlBuffer) put(it cbItem) error { _, err := c.executeAndPut(nil, it) return err } +// executeAndPut runs f, and if the return value is true, adds the given item to +// the controlbuf. The item could be nil, in which case, this method simply +// executes f and does not add the item to the controlbuf. +// +// The first return value indicates whether the item was successfully added to +// the control buffer. A non-nil error, specifically ErrConnClosing, is returned +// if the control buffer is already closed. func (c *controlBuffer) executeAndPut(f func() bool, it cbItem) (bool, error) { - var wakeUp bool c.mu.Lock() - if c.err != nil { - c.mu.Unlock() - return false, c.err + defer c.mu.Unlock() + + if c.closed { + return false, ErrConnClosing } if f != nil { if !f() { // f wasn't successful - c.mu.Unlock() return false, nil } } + if it == nil { + return true, nil + } + + var wakeUp bool if c.consumerWaiting { wakeUp = true c.consumerWaiting = false @@ -359,98 +376,102 @@ func (c *controlBuffer) executeAndPut(f func() bool, it cbItem) (bool, error) { if c.transportResponseFrames == maxQueuedTransportResponseFrames { // We are adding the frame that puts us over the threshold; create // a throttling channel. - c.trfChan.Store(make(chan struct{})) + ch := make(chan struct{}) + c.trfChan.Store(&ch) } } - c.mu.Unlock() if wakeUp { select { - case c.ch <- struct{}{}: + case c.wakeupCh <- struct{}{}: default: } } return true, nil } -// Note argument f should never be nil. -func (c *controlBuffer) execute(f func(it any) bool, it any) (bool, error) { - c.mu.Lock() - if c.err != nil { - c.mu.Unlock() - return false, c.err - } - if !f(it) { // f wasn't successful - c.mu.Unlock() - return false, nil - } - c.mu.Unlock() - return true, nil -} - +// get returns the next control frame from the control buffer. If block is true +// **and** there are no control frames in the control buffer, the call blocks +// until one of the conditions is met: there is a frame to return or the +// transport is closed. func (c *controlBuffer) get(block bool) (any, error) { for { c.mu.Lock() - if c.err != nil { + frame, err := c.getOnceLocked() + if frame != nil || err != nil || !block { + // If we read a frame or an error, we can return to the caller. The + // call to getOnceLocked() returns a nil frame and a nil error if + // there is nothing to read, and in that case, if the caller asked + // us not to block, we can return now as well. c.mu.Unlock() - return nil, c.err - } - if !c.list.isEmpty() { - h := c.list.dequeue().(cbItem) - if h.isTransportResponseFrame() { - if c.transportResponseFrames == maxQueuedTransportResponseFrames { - // We are removing the frame that put us over the - // threshold; close and clear the throttling channel. - ch := c.trfChan.Load().(chan struct{}) - close(ch) - c.trfChan.Store((chan struct{})(nil)) - } - c.transportResponseFrames-- - } - c.mu.Unlock() - return h, nil - } - if !block { - c.mu.Unlock() - return nil, nil + return frame, err } c.consumerWaiting = true c.mu.Unlock() + + // Release the lock above and wait to be woken up. select { - case <-c.ch: + case <-c.wakeupCh: case <-c.done: return nil, errors.New("transport closed by client") } } } +// Callers must not use this method, but should instead use get(). +// +// Caller must hold c.mu. +func (c *controlBuffer) getOnceLocked() (any, error) { + if c.closed { + return false, ErrConnClosing + } + if c.list.isEmpty() { + return nil, nil + } + h := c.list.dequeue().(cbItem) + if h.isTransportResponseFrame() { + if c.transportResponseFrames == maxQueuedTransportResponseFrames { + // We are removing the frame that put us over the + // threshold; close and clear the throttling channel. + ch := c.trfChan.Swap(nil) + close(*ch) + } + c.transportResponseFrames-- + } + return h, nil +} + +// finish closes the control buffer, cleaning up any streams that have queued +// header frames. Once this method returns, no more frames can be added to the +// control buffer, and attempts to do so will return ErrConnClosing. func (c *controlBuffer) finish() { c.mu.Lock() - if c.err != nil { - c.mu.Unlock() + defer c.mu.Unlock() + + if c.closed { return } - c.err = ErrConnClosing + c.closed = true // There may be headers for streams in the control buffer. // These streams need to be cleaned out since the transport // is still not aware of these yet. for head := c.list.dequeueAll(); head != nil; head = head.next { - hdr, ok := head.it.(*headerFrame) - if !ok { - continue - } - if hdr.onOrphaned != nil { // It will be nil on the server-side. - hdr.onOrphaned(ErrConnClosing) + switch v := head.it.(type) { + case *headerFrame: + if v.onOrphaned != nil { // It will be nil on the server-side. + v.onOrphaned(ErrConnClosing) + } + case *dataFrame: + _ = v.reader.Close() } } + // In case throttle() is currently in flight, it needs to be unblocked. // Otherwise, the transport may not close, since the transport is closed by // the reader encountering the connection error. - ch, _ := c.trfChan.Load().(chan struct{}) + ch := c.trfChan.Swap(nil) if ch != nil { - close(ch) + close(*ch) } - c.trfChan.Store((chan struct{})(nil)) - c.mu.Unlock() } type side int @@ -466,7 +487,7 @@ const ( // stream maintains a queue of data frames; as loopy receives data frames // it gets added to the queue of the relevant stream. // Loopy goes over this list of active streams by processing one node every iteration, -// thereby closely resemebling to a round-robin scheduling over all streams. While +// thereby closely resembling a round-robin scheduling over all streams. While // processing a stream, loopy writes out data bytes from this stream capped by the min // of http2MaxFrameLen, connection-level flow control and stream-level flow control. type loopyWriter struct { @@ -490,12 +511,13 @@ type loopyWriter struct { draining bool conn net.Conn logger *grpclog.PrefixLogger + bufferPool mem.BufferPool // Side-specific handlers ssGoAwayHandler func(*goAway) (bool, error) } -func newLoopyWriter(s side, fr *framer, cbuf *controlBuffer, bdpEst *bdpEstimator, conn net.Conn, logger *grpclog.PrefixLogger, goAwayHandler func(*goAway) (bool, error)) *loopyWriter { +func newLoopyWriter(s side, fr *framer, cbuf *controlBuffer, bdpEst *bdpEstimator, conn net.Conn, logger *grpclog.PrefixLogger, goAwayHandler func(*goAway) (bool, error), bufferPool mem.BufferPool) *loopyWriter { var buf bytes.Buffer l := &loopyWriter{ side: s, @@ -511,6 +533,7 @@ func newLoopyWriter(s side, fr *framer, cbuf *controlBuffer, bdpEst *bdpEstimato conn: conn, logger: logger, ssGoAwayHandler: goAwayHandler, + bufferPool: bufferPool, } return l } @@ -768,6 +791,11 @@ func (l *loopyWriter) cleanupStreamHandler(c *cleanupStream) error { // not be established yet. delete(l.estdStreams, c.streamID) str.deleteSelf() + for head := str.itl.dequeueAll(); head != nil; head = head.next { + if df, ok := head.it.(*dataFrame); ok { + _ = df.reader.Close() + } + } } if c.rst { // If RST_STREAM needs to be sent. if err := l.framer.fr.WriteRSTStream(c.streamID, c.rstCode); err != nil { @@ -903,16 +931,18 @@ func (l *loopyWriter) processData() (bool, error) { dataItem := str.itl.peek().(*dataFrame) // Peek at the first data item this stream. // A data item is represented by a dataFrame, since it later translates into // multiple HTTP2 data frames. - // Every dataFrame has two buffers; h that keeps grpc-message header and d that is actual data. - // As an optimization to keep wire traffic low, data from d is copied to h to make as big as the - // maximum possible HTTP2 frame size. + // Every dataFrame has two buffers; h that keeps grpc-message header and data + // that is the actual message. As an optimization to keep wire traffic low, data + // from data is copied to h to make as big as the maximum possible HTTP2 frame + // size. - if len(dataItem.h) == 0 && len(dataItem.d) == 0 { // Empty data frame + if len(dataItem.h) == 0 && dataItem.reader.Remaining() == 0 { // Empty data frame // Client sends out empty data frame with endStream = true if err := l.framer.fr.WriteData(dataItem.streamID, dataItem.endStream, nil); err != nil { return false, err } str.itl.dequeue() // remove the empty data item from stream + _ = dataItem.reader.Close() if str.itl.isEmpty() { str.state = empty } else if trailer, ok := str.itl.peek().(*headerFrame); ok { // the next item is trailers. @@ -927,9 +957,7 @@ func (l *loopyWriter) processData() (bool, error) { } return false, nil } - var ( - buf []byte - ) + // Figure out the maximum size we can send maxSize := http2MaxFrameLen if strQuota := int(l.oiws) - str.bytesOutStanding; strQuota <= 0 { // stream-level flow control. @@ -943,43 +971,50 @@ func (l *loopyWriter) processData() (bool, error) { } // Compute how much of the header and data we can send within quota and max frame length hSize := min(maxSize, len(dataItem.h)) - dSize := min(maxSize-hSize, len(dataItem.d)) - if hSize != 0 { - if dSize == 0 { - buf = dataItem.h - } else { - // We can add some data to grpc message header to distribute bytes more equally across frames. - // Copy on the stack to avoid generating garbage - var localBuf [http2MaxFrameLen]byte - copy(localBuf[:hSize], dataItem.h) - copy(localBuf[hSize:], dataItem.d[:dSize]) - buf = localBuf[:hSize+dSize] - } + dSize := min(maxSize-hSize, dataItem.reader.Remaining()) + remainingBytes := len(dataItem.h) + dataItem.reader.Remaining() - hSize - dSize + size := hSize + dSize + + var buf *[]byte + + if hSize != 0 && dSize == 0 { + buf = &dataItem.h } else { - buf = dataItem.d - } + // Note: this is only necessary because the http2.Framer does not support + // partially writing a frame, so the sequence must be materialized into a buffer. + // TODO: Revisit once https://github.com/golang/go/issues/66655 is addressed. + pool := l.bufferPool + if pool == nil { + // Note that this is only supposed to be nil in tests. Otherwise, stream is + // always initialized with a BufferPool. + pool = mem.DefaultBufferPool() + } + buf = pool.Get(size) + defer pool.Put(buf) - size := hSize + dSize + copy((*buf)[:hSize], dataItem.h) + _, _ = dataItem.reader.Read((*buf)[hSize:]) + } // Now that outgoing flow controls are checked we can replenish str's write quota str.wq.replenish(size) var endStream bool // If this is the last data message on this stream and all of it can be written in this iteration. - if dataItem.endStream && len(dataItem.h)+len(dataItem.d) <= size { + if dataItem.endStream && remainingBytes == 0 { endStream = true } if dataItem.onEachWrite != nil { dataItem.onEachWrite() } - if err := l.framer.fr.WriteData(dataItem.streamID, endStream, buf[:size]); err != nil { + if err := l.framer.fr.WriteData(dataItem.streamID, endStream, (*buf)[:size]); err != nil { return false, err } str.bytesOutStanding += size l.sendQuota -= uint32(size) dataItem.h = dataItem.h[hSize:] - dataItem.d = dataItem.d[dSize:] - if len(dataItem.h) == 0 && len(dataItem.d) == 0 { // All the data from that message was written out. + if remainingBytes == 0 { // All the data from that message was written out. + _ = dataItem.reader.Close() str.itl.dequeue() } if str.itl.isEmpty() { @@ -998,10 +1033,3 @@ func (l *loopyWriter) processData() (bool, error) { } return false, nil } - -func min(a, b int) int { - if a < b { - return a - } - return b -} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/handler_server.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/handler_server.go index 4a3ddce29a4..ce878693bd7 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/handler_server.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/handler_server.go @@ -24,7 +24,6 @@ package transport import ( - "bytes" "context" "errors" "fmt" @@ -40,6 +39,7 @@ import ( "google.golang.org/grpc/credentials" "google.golang.org/grpc/internal/grpclog" "google.golang.org/grpc/internal/grpcutil" + "google.golang.org/grpc/mem" "google.golang.org/grpc/metadata" "google.golang.org/grpc/peer" "google.golang.org/grpc/stats" @@ -50,7 +50,7 @@ import ( // NewServerHandlerTransport returns a ServerTransport handling gRPC from // inside an http.Handler, or writes an HTTP error to w and returns an error. // It requires that the http Server supports HTTP/2. -func NewServerHandlerTransport(w http.ResponseWriter, r *http.Request, stats []stats.Handler) (ServerTransport, error) { +func NewServerHandlerTransport(w http.ResponseWriter, r *http.Request, stats []stats.Handler, bufferPool mem.BufferPool) (ServerTransport, error) { if r.Method != http.MethodPost { w.Header().Set("Allow", http.MethodPost) msg := fmt.Sprintf("invalid gRPC request method %q", r.Method) @@ -98,6 +98,7 @@ func NewServerHandlerTransport(w http.ResponseWriter, r *http.Request, stats []s contentType: contentType, contentSubtype: contentSubtype, stats: stats, + bufferPool: bufferPool, } st.logger = prefixLoggerForServerHandlerTransport(st) @@ -171,6 +172,8 @@ type serverHandlerTransport struct { stats []stats.Handler logger *grpclog.PrefixLogger + + bufferPool mem.BufferPool } func (ht *serverHandlerTransport) Close(err error) { @@ -244,6 +247,7 @@ func (ht *serverHandlerTransport) WriteStatus(s *Stream, st *status.Status) erro } s.hdrMu.Lock() + defer s.hdrMu.Unlock() if p := st.Proto(); p != nil && len(p.Details) > 0 { delete(s.trailer, grpcStatusDetailsBinHeader) stBytes, err := proto.Marshal(p) @@ -268,7 +272,6 @@ func (ht *serverHandlerTransport) WriteStatus(s *Stream, st *status.Status) erro } } } - s.hdrMu.Unlock() }) if err == nil { // transport has not been closed @@ -330,16 +333,28 @@ func (ht *serverHandlerTransport) writeCustomHeaders(s *Stream) { s.hdrMu.Unlock() } -func (ht *serverHandlerTransport) Write(s *Stream, hdr []byte, data []byte, opts *Options) error { +func (ht *serverHandlerTransport) Write(s *Stream, hdr []byte, data mem.BufferSlice, _ *Options) error { + // Always take a reference because otherwise there is no guarantee the data will + // be available after this function returns. This is what callers to Write + // expect. + data.Ref() headersWritten := s.updateHeaderSent() - return ht.do(func() { + err := ht.do(func() { + defer data.Free() if !headersWritten { ht.writePendingHeaders(s) } ht.rw.Write(hdr) - ht.rw.Write(data) + for _, b := range data { + _, _ = ht.rw.Write(b.ReadOnlyData()) + } ht.rw.(http.Flusher).Flush() }) + if err != nil { + data.Free() + return err + } + return nil } func (ht *serverHandlerTransport) WriteHeader(s *Stream, md metadata.MD) error { @@ -406,7 +421,7 @@ func (ht *serverHandlerTransport) HandleStreams(ctx context.Context, startStream headerWireLength: 0, // won't have access to header wire length until golang/go#18997. } s.trReader = &transportReader{ - reader: &recvBufferReader{ctx: s.ctx, ctxDone: s.ctx.Done(), recv: s.buf, freeBuffer: func(*bytes.Buffer) {}}, + reader: &recvBufferReader{ctx: s.ctx, ctxDone: s.ctx.Done(), recv: s.buf}, windowHandler: func(int) {}, } @@ -415,21 +430,19 @@ func (ht *serverHandlerTransport) HandleStreams(ctx context.Context, startStream go func() { defer close(readerDone) - // TODO: minimize garbage, optimize recvBuffer code/ownership - const readSize = 8196 - for buf := make([]byte, readSize); ; { - n, err := req.Body.Read(buf) + for { + buf := ht.bufferPool.Get(http2MaxFrameLen) + n, err := req.Body.Read(*buf) if n > 0 { - s.buf.put(recvMsg{buffer: bytes.NewBuffer(buf[:n:n])}) - buf = buf[n:] + *buf = (*buf)[:n] + s.buf.put(recvMsg{buffer: mem.NewBuffer(buf, ht.bufferPool)}) + } else { + ht.bufferPool.Put(buf) } if err != nil { s.buf.put(recvMsg{err: mapRecvMsgError(err)}) return } - if len(buf) == 0 { - buf = make([]byte, readSize) - } } }() @@ -462,7 +475,7 @@ func (ht *serverHandlerTransport) IncrMsgSent() {} func (ht *serverHandlerTransport) IncrMsgRecv() {} -func (ht *serverHandlerTransport) Drain(debugData string) { +func (ht *serverHandlerTransport) Drain(string) { panic("Drain() is not implemented") } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_client.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_client.go index 3c63c706986..c769deab53c 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_client.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_client.go @@ -47,6 +47,7 @@ import ( isyscall "google.golang.org/grpc/internal/syscall" "google.golang.org/grpc/internal/transport/networktype" "google.golang.org/grpc/keepalive" + "google.golang.org/grpc/mem" "google.golang.org/grpc/metadata" "google.golang.org/grpc/peer" "google.golang.org/grpc/resolver" @@ -59,6 +60,8 @@ import ( // atomically. var clientConnectionCounter uint64 +var goAwayLoopyWriterTimeout = 5 * time.Second + var metadataFromOutgoingContextRaw = internal.FromOutgoingContextRaw.(func(context.Context) (metadata.MD, [][]string, bool)) // http2Client implements the ClientTransport interface with HTTP2. @@ -144,7 +147,7 @@ type http2Client struct { onClose func(GoAwayReason) - bufferPool *bufferPool + bufferPool mem.BufferPool connectionID uint64 logger *grpclog.PrefixLogger @@ -229,7 +232,7 @@ func newHTTP2Client(connectCtx, ctx context.Context, addr resolver.Address, opts } }(conn) - // The following defer and goroutine monitor the connectCtx for cancelation + // The following defer and goroutine monitor the connectCtx for cancellation // and deadline. On context expiration, the connection is hard closed and // this function will naturally fail as a result. Otherwise, the defer // waits for the goroutine to exit to prevent the context from being @@ -346,7 +349,7 @@ func newHTTP2Client(connectCtx, ctx context.Context, addr resolver.Address, opts streamQuota: defaultMaxStreamsClient, streamsQuotaAvailable: make(chan struct{}, 1), keepaliveEnabled: keepaliveEnabled, - bufferPool: newBufferPool(), + bufferPool: opts.BufferPool, onClose: onClose, } var czSecurity credentials.ChannelzSecurityValue @@ -463,7 +466,7 @@ func newHTTP2Client(connectCtx, ctx context.Context, addr resolver.Address, opts return nil, err } go func() { - t.loopy = newLoopyWriter(clientSide, t.framer, t.controlBuf, t.bdpEst, t.conn, t.logger, t.outgoingGoAwayHandler) + t.loopy = newLoopyWriter(clientSide, t.framer, t.controlBuf, t.bdpEst, t.conn, t.logger, t.outgoingGoAwayHandler, t.bufferPool) if err := t.loopy.run(); !isIOError(err) { // Immediately close the connection, as the loopy writer returns // when there are no more active streams and we were draining (the @@ -504,7 +507,6 @@ func (t *http2Client) newStream(ctx context.Context, callHdr *CallHdr) *Stream { closeStream: func(err error) { t.CloseStream(s, err) }, - freeBuffer: t.bufferPool.put, }, windowHandler: func(n int) { t.updateWindow(s, uint32(n)) @@ -770,7 +772,7 @@ func (t *http2Client) NewStream(ctx context.Context, callHdr *CallHdr) (*Stream, hdr := &headerFrame{ hf: headerFields, endStream: false, - initStream: func(id uint32) error { + initStream: func(uint32) error { t.mu.Lock() // TODO: handle transport closure in loopy instead and remove this // initStream is never called when transport is draining. @@ -983,6 +985,7 @@ func (t *http2Client) closeStream(s *Stream, err error, rst bool, rstCode http2. // only once on a transport. Once it is called, the transport should not be // accessed anymore. func (t *http2Client) Close(err error) { + t.conn.SetWriteDeadline(time.Now().Add(time.Second * 10)) t.mu.Lock() // Make sure we only close once. if t.state == closing { @@ -1006,10 +1009,20 @@ func (t *http2Client) Close(err error) { t.kpDormancyCond.Signal() } t.mu.Unlock() + // Per HTTP/2 spec, a GOAWAY frame must be sent before closing the - // connection. See https://httpwg.org/specs/rfc7540.html#GOAWAY. + // connection. See https://httpwg.org/specs/rfc7540.html#GOAWAY. It + // also waits for loopyWriter to be closed with a timer to avoid the + // long blocking in case the connection is blackholed, i.e. TCP is + // just stuck. t.controlBuf.put(&goAway{code: http2.ErrCodeNo, debugData: []byte("client transport shutdown"), closeConn: err}) - <-t.writerDone + timer := time.NewTimer(goAwayLoopyWriterTimeout) + defer timer.Stop() + select { + case <-t.writerDone: // success + case <-timer.C: + t.logger.Infof("Failed to write a GOAWAY frame as part of connection close after %s. Giving up and closing the transport.", goAwayLoopyWriterTimeout) + } t.cancel() t.conn.Close() channelz.RemoveEntry(t.channelz.ID) @@ -1065,27 +1078,36 @@ func (t *http2Client) GracefulClose() { // Write formats the data into HTTP2 data frame(s) and sends it out. The caller // should proceed only if Write returns nil. -func (t *http2Client) Write(s *Stream, hdr []byte, data []byte, opts *Options) error { +func (t *http2Client) Write(s *Stream, hdr []byte, data mem.BufferSlice, opts *Options) error { + reader := data.Reader() + if opts.Last { // If it's the last message, update stream state. if !s.compareAndSwapState(streamActive, streamWriteDone) { + _ = reader.Close() return errStreamDone } } else if s.getState() != streamActive { + _ = reader.Close() return errStreamDone } df := &dataFrame{ streamID: s.id, endStream: opts.Last, h: hdr, - d: data, + reader: reader, } - if hdr != nil || data != nil { // If it's not an empty data frame, check quota. - if err := s.wq.get(int32(len(hdr) + len(data))); err != nil { + if hdr != nil || df.reader.Remaining() != 0 { // If it's not an empty data frame, check quota. + if err := s.wq.get(int32(len(hdr) + df.reader.Remaining())); err != nil { + _ = reader.Close() return err } } - return t.controlBuf.put(df) + if err := t.controlBuf.put(df); err != nil { + _ = reader.Close() + return err + } + return nil } func (t *http2Client) getStream(f http2.Frame) *Stream { @@ -1190,10 +1212,13 @@ func (t *http2Client) handleData(f *http2.DataFrame) { // guarantee f.Data() is consumed before the arrival of next frame. // Can this copy be eliminated? if len(f.Data()) > 0 { - buffer := t.bufferPool.get() - buffer.Reset() - buffer.Write(f.Data()) - s.write(recvMsg{buffer: buffer}) + pool := t.bufferPool + if pool == nil { + // Note that this is only supposed to be nil in tests. Otherwise, stream is + // always initialized with a BufferPool. + pool = mem.DefaultBufferPool() + } + s.write(recvMsg{buffer: mem.Copy(f.Data(), pool)}) } } // The server has closed the stream without sending trailers. Record that @@ -1222,7 +1247,7 @@ func (t *http2Client) handleRSTStream(f *http2.RSTStreamFrame) { if statusCode == codes.Canceled { if d, ok := s.ctx.Deadline(); ok && !d.After(time.Now()) { // Our deadline was already exceeded, and that was likely the cause - // of this cancelation. Alter the status code accordingly. + // of this cancellation. Alter the status code accordingly. statusCode = codes.DeadlineExceeded } } @@ -1307,7 +1332,7 @@ func (t *http2Client) handleGoAway(f *http2.GoAwayFrame) { id := f.LastStreamID if id > 0 && id%2 == 0 { t.mu.Unlock() - t.Close(connectionErrorf(true, nil, "received goaway with non-zero even-numbered numbered stream id: %v", id)) + t.Close(connectionErrorf(true, nil, "received goaway with non-zero even-numbered stream id: %v", id)) return } // A client can receive multiple GoAways from the server (see @@ -1642,11 +1667,10 @@ func (t *http2Client) reader(errCh chan<- error) { t.closeStream(s, status.Error(code, msg), true, http2.ErrCodeProtocol, status.New(code, msg), nil, false) } continue - } else { - // Transport error. - t.Close(connectionErrorf(true, err, "error reading from server: %v", err)) - return } + // Transport error. + t.Close(connectionErrorf(true, err, "error reading from server: %v", err)) + return } switch frame := frame.(type) { case *http2.MetaHeadersFrame: @@ -1671,13 +1695,6 @@ func (t *http2Client) reader(errCh chan<- error) { } } -func minTime(a, b time.Duration) time.Duration { - if a < b { - return a - } - return b -} - // keepalive running in a separate goroutine makes sure the connection is alive by sending pings. func (t *http2Client) keepalive() { p := &ping{data: [8]byte{}} @@ -1745,7 +1762,7 @@ func (t *http2Client) keepalive() { // timeoutLeft. This will ensure that we wait only for kp.Time // before sending out the next ping (for cases where the ping is // acked). - sleepDuration := minTime(t.kp.Time, timeoutLeft) + sleepDuration := min(t.kp.Time, timeoutLeft) timeoutLeft -= sleepDuration timer.Reset(sleepDuration) case <-t.ctx.Done(): diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_server.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_server.go index b7091165b50..584b50fe553 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_server.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http2_server.go @@ -39,6 +39,7 @@ import ( "google.golang.org/grpc/internal/grpcutil" "google.golang.org/grpc/internal/pretty" "google.golang.org/grpc/internal/syscall" + "google.golang.org/grpc/mem" "google.golang.org/protobuf/proto" "google.golang.org/grpc/codes" @@ -119,7 +120,7 @@ type http2Server struct { // Fields below are for channelz metric collection. channelz *channelz.Socket - bufferPool *bufferPool + bufferPool mem.BufferPool connectionID uint64 @@ -261,7 +262,7 @@ func NewServerTransport(conn net.Conn, config *ServerConfig) (_ ServerTransport, idle: time.Now(), kep: kep, initialWindowSize: iwz, - bufferPool: newBufferPool(), + bufferPool: config.BufferPool, } var czSecurity credentials.ChannelzSecurityValue if au, ok := authInfo.(credentials.ChannelzSecurityInfo); ok { @@ -330,7 +331,7 @@ func NewServerTransport(conn net.Conn, config *ServerConfig) (_ ServerTransport, t.handleSettings(sf) go func() { - t.loopy = newLoopyWriter(serverSide, t.framer, t.controlBuf, t.bdpEst, t.conn, t.logger, t.outgoingGoAwayHandler) + t.loopy = newLoopyWriter(serverSide, t.framer, t.controlBuf, t.bdpEst, t.conn, t.logger, t.outgoingGoAwayHandler, t.bufferPool) err := t.loopy.run() close(t.loopyWriterDone) if !isIOError(err) { @@ -613,10 +614,9 @@ func (t *http2Server) operateHeaders(ctx context.Context, frame *http2.MetaHeade s.wq = newWriteQuota(defaultWriteQuota, s.ctxDone) s.trReader = &transportReader{ reader: &recvBufferReader{ - ctx: s.ctx, - ctxDone: s.ctxDone, - recv: s.buf, - freeBuffer: t.bufferPool.put, + ctx: s.ctx, + ctxDone: s.ctxDone, + recv: s.buf, }, windowHandler: func(n int) { t.updateWindow(s, uint32(n)) @@ -813,10 +813,13 @@ func (t *http2Server) handleData(f *http2.DataFrame) { // guarantee f.Data() is consumed before the arrival of next frame. // Can this copy be eliminated? if len(f.Data()) > 0 { - buffer := t.bufferPool.get() - buffer.Reset() - buffer.Write(f.Data()) - s.write(recvMsg{buffer: buffer}) + pool := t.bufferPool + if pool == nil { + // Note that this is only supposed to be nil in tests. Otherwise, stream is + // always initialized with a BufferPool. + pool = mem.DefaultBufferPool() + } + s.write(recvMsg{buffer: mem.Copy(f.Data(), pool)}) } } if f.StreamEnded() { @@ -1089,7 +1092,9 @@ func (t *http2Server) WriteStatus(s *Stream, st *status.Status) error { onWrite: t.setResetPingStrikes, } - success, err := t.controlBuf.execute(t.checkForHeaderListSize, trailingHeader) + success, err := t.controlBuf.executeAndPut(func() bool { + return t.checkForHeaderListSize(trailingHeader) + }, nil) if !success { if err != nil { return err @@ -1112,27 +1117,37 @@ func (t *http2Server) WriteStatus(s *Stream, st *status.Status) error { // Write converts the data into HTTP2 data frame and sends it out. Non-nil error // is returns if it fails (e.g., framing error, transport error). -func (t *http2Server) Write(s *Stream, hdr []byte, data []byte, opts *Options) error { +func (t *http2Server) Write(s *Stream, hdr []byte, data mem.BufferSlice, _ *Options) error { + reader := data.Reader() + if !s.isHeaderSent() { // Headers haven't been written yet. if err := t.WriteHeader(s, nil); err != nil { + _ = reader.Close() return err } } else { // Writing headers checks for this condition. if s.getState() == streamDone { + _ = reader.Close() return t.streamContextErr(s) } } + df := &dataFrame{ streamID: s.id, h: hdr, - d: data, + reader: reader, onEachWrite: t.setResetPingStrikes, } - if err := s.wq.get(int32(len(hdr) + len(data))); err != nil { + if err := s.wq.get(int32(len(hdr) + df.reader.Remaining())); err != nil { + _ = reader.Close() return t.streamContextErr(s) } - return t.controlBuf.put(df) + if err := t.controlBuf.put(df); err != nil { + _ = reader.Close() + return err + } + return nil } // keepalive running in a separate goroutine does the following: @@ -1223,7 +1238,7 @@ func (t *http2Server) keepalive() { // timeoutLeft. This will ensure that we wait only for kp.Time // before sending out the next ping (for cases where the ping is // acked). - sleepDuration := minTime(t.kp.Time, kpTimeoutLeft) + sleepDuration := min(t.kp.Time, kpTimeoutLeft) kpTimeoutLeft -= sleepDuration kpTimer.Reset(sleepDuration) case <-t.done: diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http_util.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http_util.go index 39cef3bd442..3613d7b6481 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http_util.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/http_util.go @@ -317,28 +317,32 @@ func newBufWriter(conn net.Conn, batchSize int, pool *sync.Pool) *bufWriter { return w } -func (w *bufWriter) Write(b []byte) (n int, err error) { +func (w *bufWriter) Write(b []byte) (int, error) { if w.err != nil { return 0, w.err } if w.batchSize == 0 { // Buffer has been disabled. - n, err = w.conn.Write(b) + n, err := w.conn.Write(b) return n, toIOError(err) } if w.buf == nil { b := w.pool.Get().(*[]byte) w.buf = *b } + written := 0 for len(b) > 0 { - nn := copy(w.buf[w.offset:], b) - b = b[nn:] - w.offset += nn - n += nn - if w.offset >= w.batchSize { - err = w.flushKeepBuffer() + copied := copy(w.buf[w.offset:], b) + b = b[copied:] + written += copied + w.offset += copied + if w.offset < w.batchSize { + continue + } + if err := w.flushKeepBuffer(); err != nil { + return written, err } } - return n, err + return written, nil } func (w *bufWriter) Flush() error { @@ -389,7 +393,7 @@ type framer struct { fr *http2.Framer } -var writeBufferPoolMap map[int]*sync.Pool = make(map[int]*sync.Pool) +var writeBufferPoolMap = make(map[int]*sync.Pool) var writeBufferMutex sync.Mutex func newFramer(conn net.Conn, writeBufferSize, readBufferSize int, sharedWriteBuffer bool, maxHeaderListSize uint32) *framer { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/proxy.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/proxy.go index 24fa1032574..54b22443654 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/proxy.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/proxy.go @@ -107,8 +107,14 @@ func doHTTPConnectHandshake(ctx context.Context, conn net.Conn, backendAddr stri } return nil, fmt.Errorf("failed to do connect handshake, response: %q", dump) } - - return &bufConn{Conn: conn, r: r}, nil + // The buffer could contain extra bytes from the target server, so we can't + // discard it. However, in many cases where the server waits for the client + // to send the first message (e.g. when TLS is being used), the buffer will + // be empty, so we can avoid the overhead of reading through this buffer. + if r.Buffered() != 0 { + return &bufConn{Conn: conn, r: r}, nil + } + return conn, nil } // proxyDial dials, connecting to a proxy first if necessary. Checks if a proxy diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/transport.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/transport.go index 4b39c0ade97..924ba4f3653 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/transport.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/internal/transport/transport.go @@ -22,7 +22,6 @@ package transport import ( - "bytes" "context" "errors" "fmt" @@ -37,6 +36,7 @@ import ( "google.golang.org/grpc/credentials" "google.golang.org/grpc/internal/channelz" "google.golang.org/grpc/keepalive" + "google.golang.org/grpc/mem" "google.golang.org/grpc/metadata" "google.golang.org/grpc/peer" "google.golang.org/grpc/resolver" @@ -47,32 +47,10 @@ import ( const logLevel = 2 -type bufferPool struct { - pool sync.Pool -} - -func newBufferPool() *bufferPool { - return &bufferPool{ - pool: sync.Pool{ - New: func() any { - return new(bytes.Buffer) - }, - }, - } -} - -func (p *bufferPool) get() *bytes.Buffer { - return p.pool.Get().(*bytes.Buffer) -} - -func (p *bufferPool) put(b *bytes.Buffer) { - p.pool.Put(b) -} - // recvMsg represents the received msg from the transport. All transport // protocol specific info has been removed. type recvMsg struct { - buffer *bytes.Buffer + buffer mem.Buffer // nil: received some data // io.EOF: stream is completed. data is nil. // other non-nil error: transport failure. data is nil. @@ -102,6 +80,9 @@ func newRecvBuffer() *recvBuffer { func (b *recvBuffer) put(r recvMsg) { b.mu.Lock() if b.err != nil { + // drop the buffer on the floor. Since b.err is not nil, any subsequent reads + // will always return an error, making this buffer inaccessible. + r.buffer.Free() b.mu.Unlock() // An error had occurred earlier, don't accept more // data or errors. @@ -148,45 +129,97 @@ type recvBufferReader struct { ctx context.Context ctxDone <-chan struct{} // cache of ctx.Done() (for performance). recv *recvBuffer - last *bytes.Buffer // Stores the remaining data in the previous calls. + last mem.Buffer // Stores the remaining data in the previous calls. err error - freeBuffer func(*bytes.Buffer) } -// Read reads the next len(p) bytes from last. If last is drained, it tries to -// read additional data from recv. It blocks if there no additional data available -// in recv. If Read returns any non-nil error, it will continue to return that error. -func (r *recvBufferReader) Read(p []byte) (n int, err error) { +func (r *recvBufferReader) ReadHeader(header []byte) (n int, err error) { if r.err != nil { return 0, r.err } if r.last != nil { - // Read remaining data left in last call. - copied, _ := r.last.Read(p) - if r.last.Len() == 0 { - r.freeBuffer(r.last) + n, r.last = mem.ReadUnsafe(header, r.last) + return n, nil + } + if r.closeStream != nil { + n, r.err = r.readHeaderClient(header) + } else { + n, r.err = r.readHeader(header) + } + return n, r.err +} + +// Read reads the next n bytes from last. If last is drained, it tries to read +// additional data from recv. It blocks if there no additional data available in +// recv. If Read returns any non-nil error, it will continue to return that +// error. +func (r *recvBufferReader) Read(n int) (buf mem.Buffer, err error) { + if r.err != nil { + return nil, r.err + } + if r.last != nil { + buf = r.last + if r.last.Len() > n { + buf, r.last = mem.SplitUnsafe(buf, n) + } else { r.last = nil } - return copied, nil + return buf, nil } if r.closeStream != nil { - n, r.err = r.readClient(p) + buf, r.err = r.readClient(n) } else { - n, r.err = r.read(p) + buf, r.err = r.read(n) } - return n, r.err + return buf, r.err } -func (r *recvBufferReader) read(p []byte) (n int, err error) { +func (r *recvBufferReader) readHeader(header []byte) (n int, err error) { select { case <-r.ctxDone: return 0, ContextErr(r.ctx.Err()) case m := <-r.recv.get(): - return r.readAdditional(m, p) + return r.readHeaderAdditional(m, header) + } +} + +func (r *recvBufferReader) read(n int) (buf mem.Buffer, err error) { + select { + case <-r.ctxDone: + return nil, ContextErr(r.ctx.Err()) + case m := <-r.recv.get(): + return r.readAdditional(m, n) + } +} + +func (r *recvBufferReader) readHeaderClient(header []byte) (n int, err error) { + // If the context is canceled, then closes the stream with nil metadata. + // closeStream writes its error parameter to r.recv as a recvMsg. + // r.readAdditional acts on that message and returns the necessary error. + select { + case <-r.ctxDone: + // Note that this adds the ctx error to the end of recv buffer, and + // reads from the head. This will delay the error until recv buffer is + // empty, thus will delay ctx cancellation in Recv(). + // + // It's done this way to fix a race between ctx cancel and trailer. The + // race was, stream.Recv() may return ctx error if ctxDone wins the + // race, but stream.Trailer() may return a non-nil md because the stream + // was not marked as done when trailer is received. This closeStream + // call will mark stream as done, thus fix the race. + // + // TODO: delaying ctx error seems like a unnecessary side effect. What + // we really want is to mark the stream as done, and return ctx error + // faster. + r.closeStream(ContextErr(r.ctx.Err())) + m := <-r.recv.get() + return r.readHeaderAdditional(m, header) + case m := <-r.recv.get(): + return r.readHeaderAdditional(m, header) } } -func (r *recvBufferReader) readClient(p []byte) (n int, err error) { +func (r *recvBufferReader) readClient(n int) (buf mem.Buffer, err error) { // If the context is canceled, then closes the stream with nil metadata. // closeStream writes its error parameter to r.recv as a recvMsg. // r.readAdditional acts on that message and returns the necessary error. @@ -207,25 +240,40 @@ func (r *recvBufferReader) readClient(p []byte) (n int, err error) { // faster. r.closeStream(ContextErr(r.ctx.Err())) m := <-r.recv.get() - return r.readAdditional(m, p) + return r.readAdditional(m, n) case m := <-r.recv.get(): - return r.readAdditional(m, p) + return r.readAdditional(m, n) } } -func (r *recvBufferReader) readAdditional(m recvMsg, p []byte) (n int, err error) { +func (r *recvBufferReader) readHeaderAdditional(m recvMsg, header []byte) (n int, err error) { r.recv.load() if m.err != nil { + if m.buffer != nil { + m.buffer.Free() + } return 0, m.err } - copied, _ := m.buffer.Read(p) - if m.buffer.Len() == 0 { - r.freeBuffer(m.buffer) - r.last = nil - } else { - r.last = m.buffer + + n, r.last = mem.ReadUnsafe(header, m.buffer) + + return n, nil +} + +func (r *recvBufferReader) readAdditional(m recvMsg, n int) (b mem.Buffer, err error) { + r.recv.load() + if m.err != nil { + if m.buffer != nil { + m.buffer.Free() + } + return nil, m.err + } + + if m.buffer.Len() > n { + m.buffer, r.last = mem.SplitUnsafe(m.buffer, n) } - return copied, nil + + return m.buffer, nil } type streamState uint32 @@ -241,7 +289,7 @@ const ( type Stream struct { id uint32 st ServerTransport // nil for client side Stream - ct *http2Client // nil for server side Stream + ct ClientTransport // nil for server side Stream ctx context.Context // the associated context of the stream cancel context.CancelFunc // always nil for client side Stream done chan struct{} // closed at the end of stream to unblock writers. On the client side. @@ -251,7 +299,7 @@ type Stream struct { recvCompress string sendCompress string buf *recvBuffer - trReader io.Reader + trReader *transportReader fc *inFlow wq *writeQuota @@ -408,7 +456,7 @@ func (s *Stream) TrailersOnly() bool { return s.noHeaders } -// Trailer returns the cached trailer metedata. Note that if it is not called +// Trailer returns the cached trailer metadata. Note that if it is not called // after the entire stream is done, it could return an empty MD. Client // side only. // It can be safely read only after stream has ended that is either read @@ -499,36 +547,87 @@ func (s *Stream) write(m recvMsg) { s.buf.put(m) } -// Read reads all p bytes from the wire for this stream. -func (s *Stream) Read(p []byte) (n int, err error) { +func (s *Stream) ReadHeader(header []byte) (err error) { + // Don't request a read if there was an error earlier + if er := s.trReader.er; er != nil { + return er + } + s.requestRead(len(header)) + for len(header) != 0 { + n, err := s.trReader.ReadHeader(header) + header = header[n:] + if len(header) == 0 { + err = nil + } + if err != nil { + if n > 0 && err == io.EOF { + err = io.ErrUnexpectedEOF + } + return err + } + } + return nil +} + +// Read reads n bytes from the wire for this stream. +func (s *Stream) Read(n int) (data mem.BufferSlice, err error) { // Don't request a read if there was an error earlier - if er := s.trReader.(*transportReader).er; er != nil { - return 0, er + if er := s.trReader.er; er != nil { + return nil, er } - s.requestRead(len(p)) - return io.ReadFull(s.trReader, p) + s.requestRead(n) + for n != 0 { + buf, err := s.trReader.Read(n) + var bufLen int + if buf != nil { + bufLen = buf.Len() + } + n -= bufLen + if n == 0 { + err = nil + } + if err != nil { + if bufLen > 0 && err == io.EOF { + err = io.ErrUnexpectedEOF + } + data.Free() + return nil, err + } + data = append(data, buf) + } + return data, nil } -// tranportReader reads all the data available for this Stream from the transport and +// transportReader reads all the data available for this Stream from the transport and // passes them into the decoder, which converts them into a gRPC message stream. // The error is io.EOF when the stream is done or another non-nil error if // the stream broke. type transportReader struct { - reader io.Reader + reader *recvBufferReader // The handler to control the window update procedure for both this // particular stream and the associated transport. windowHandler func(int) er error } -func (t *transportReader) Read(p []byte) (n int, err error) { - n, err = t.reader.Read(p) +func (t *transportReader) ReadHeader(header []byte) (int, error) { + n, err := t.reader.ReadHeader(header) if err != nil { t.er = err - return + return 0, err } t.windowHandler(n) - return + return n, nil +} + +func (t *transportReader) Read(n int) (mem.Buffer, error) { + buf, err := t.reader.Read(n) + if err != nil { + t.er = err + return buf, err + } + t.windowHandler(buf.Len()) + return buf, nil } // BytesReceived indicates whether any bytes have been received on this stream. @@ -574,6 +673,7 @@ type ServerConfig struct { ChannelzParent *channelz.Server MaxHeaderListSize *uint32 HeaderTableSize *uint32 + BufferPool mem.BufferPool } // ConnectOptions covers all relevant options for communicating with the server. @@ -612,6 +712,8 @@ type ConnectOptions struct { MaxHeaderListSize *uint32 // UseProxy specifies if a proxy should be used. UseProxy bool + // The mem.BufferPool to use when reading/writing to the wire. + BufferPool mem.BufferPool } // NewClientTransport establishes the transport with the required ConnectOptions @@ -673,7 +775,7 @@ type ClientTransport interface { // Write sends the data for the given stream. A nil stream indicates // the write is to be performed on the transport as a whole. - Write(s *Stream, hdr []byte, data []byte, opts *Options) error + Write(s *Stream, hdr []byte, data mem.BufferSlice, opts *Options) error // NewStream creates a Stream for an RPC. NewStream(ctx context.Context, callHdr *CallHdr) (*Stream, error) @@ -725,7 +827,7 @@ type ServerTransport interface { // Write sends the data for the given stream. // Write may not be called on all streams. - Write(s *Stream, hdr []byte, data []byte, opts *Options) error + Write(s *Stream, hdr []byte, data mem.BufferSlice, opts *Options) error // WriteStatus sends the status of a stream to the client. WriteStatus is // the final call made on a stream and always occurs. @@ -798,7 +900,7 @@ var ( // connection is draining. This could be caused by goaway or balancer // removing the address. errStreamDrain = status.Error(codes.Unavailable, "the connection is draining") - // errStreamDone is returned from write at the client side to indiacte application + // errStreamDone is returned from write at the client side to indicate application // layer of an error. errStreamDone = errors.New("the stream is done") // StatusGoAway indicates that the server sent a GOAWAY that included this diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/keepalive/keepalive.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/keepalive/keepalive.go index 34d31b5e7d3..eb42b19fb99 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/keepalive/keepalive.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/keepalive/keepalive.go @@ -34,15 +34,29 @@ type ClientParameters struct { // After a duration of this time if the client doesn't see any activity it // pings the server to see if the transport is still alive. // If set below 10s, a minimum value of 10s will be used instead. - Time time.Duration // The current default value is infinity. + // + // Note that gRPC servers have a default EnforcementPolicy.MinTime of 5 + // minutes (which means the client shouldn't ping more frequently than every + // 5 minutes). + // + // Though not ideal, it's not a strong requirement for Time to be less than + // EnforcementPolicy.MinTime. Time will automatically double if the server + // disconnects due to its enforcement policy. + // + // For more details, see + // https://github.com/grpc/proposal/blob/master/A8-client-side-keepalive.md + Time time.Duration // After having pinged for keepalive check, the client waits for a duration // of Timeout and if no activity is seen even after that the connection is // closed. - Timeout time.Duration // The current default value is 20 seconds. + // + // If keepalive is enabled, and this value is not explicitly set, the default + // is 20 seconds. + Timeout time.Duration // If true, client sends keepalive pings even with no active RPCs. If false, // when there are no active RPCs, Time and Timeout will be ignored and no // keepalive pings will be sent. - PermitWithoutStream bool // false by default. + PermitWithoutStream bool } // ServerParameters is used to set keepalive and max-age parameters on the diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_pool.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_pool.go new file mode 100644 index 00000000000..c37c58c0233 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_pool.go @@ -0,0 +1,194 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 mem + +import ( + "sort" + "sync" + + "google.golang.org/grpc/internal" +) + +// BufferPool is a pool of buffers that can be shared and reused, resulting in +// decreased memory allocation. +type BufferPool interface { + // Get returns a buffer with specified length from the pool. + Get(length int) *[]byte + + // Put returns a buffer to the pool. + Put(*[]byte) +} + +var defaultBufferPoolSizes = []int{ + 256, + 4 << 10, // 4KB (go page size) + 16 << 10, // 16KB (max HTTP/2 frame size used by gRPC) + 32 << 10, // 32KB (default buffer size for io.Copy) + 1 << 20, // 1MB +} + +var defaultBufferPool BufferPool + +func init() { + defaultBufferPool = NewTieredBufferPool(defaultBufferPoolSizes...) + + internal.SetDefaultBufferPoolForTesting = func(pool BufferPool) { + defaultBufferPool = pool + } + + internal.SetBufferPoolingThresholdForTesting = func(threshold int) { + bufferPoolingThreshold = threshold + } +} + +// DefaultBufferPool returns the current default buffer pool. It is a BufferPool +// created with NewBufferPool that uses a set of default sizes optimized for +// expected workflows. +func DefaultBufferPool() BufferPool { + return defaultBufferPool +} + +// NewTieredBufferPool returns a BufferPool implementation that uses multiple +// underlying pools of the given pool sizes. +func NewTieredBufferPool(poolSizes ...int) BufferPool { + sort.Ints(poolSizes) + pools := make([]*sizedBufferPool, len(poolSizes)) + for i, s := range poolSizes { + pools[i] = newSizedBufferPool(s) + } + return &tieredBufferPool{ + sizedPools: pools, + } +} + +// tieredBufferPool implements the BufferPool interface with multiple tiers of +// buffer pools for different sizes of buffers. +type tieredBufferPool struct { + sizedPools []*sizedBufferPool + fallbackPool simpleBufferPool +} + +func (p *tieredBufferPool) Get(size int) *[]byte { + return p.getPool(size).Get(size) +} + +func (p *tieredBufferPool) Put(buf *[]byte) { + p.getPool(cap(*buf)).Put(buf) +} + +func (p *tieredBufferPool) getPool(size int) BufferPool { + poolIdx := sort.Search(len(p.sizedPools), func(i int) bool { + return p.sizedPools[i].defaultSize >= size + }) + + if poolIdx == len(p.sizedPools) { + return &p.fallbackPool + } + + return p.sizedPools[poolIdx] +} + +// sizedBufferPool is a BufferPool implementation that is optimized for specific +// buffer sizes. For example, HTTP/2 frames within gRPC have a default max size +// of 16kb and a sizedBufferPool can be configured to only return buffers with a +// capacity of 16kb. Note that however it does not support returning larger +// buffers and in fact panics if such a buffer is requested. Because of this, +// this BufferPool implementation is not meant to be used on its own and rather +// is intended to be embedded in a tieredBufferPool such that Get is only +// invoked when the required size is smaller than or equal to defaultSize. +type sizedBufferPool struct { + pool sync.Pool + defaultSize int +} + +func (p *sizedBufferPool) Get(size int) *[]byte { + buf := p.pool.Get().(*[]byte) + b := *buf + clear(b[:cap(b)]) + *buf = b[:size] + return buf +} + +func (p *sizedBufferPool) Put(buf *[]byte) { + if cap(*buf) < p.defaultSize { + // Ignore buffers that are too small to fit in the pool. Otherwise, when + // Get is called it will panic as it tries to index outside the bounds + // of the buffer. + return + } + p.pool.Put(buf) +} + +func newSizedBufferPool(size int) *sizedBufferPool { + return &sizedBufferPool{ + pool: sync.Pool{ + New: func() any { + buf := make([]byte, size) + return &buf + }, + }, + defaultSize: size, + } +} + +var _ BufferPool = (*simpleBufferPool)(nil) + +// simpleBufferPool is an implementation of the BufferPool interface that +// attempts to pool buffers with a sync.Pool. When Get is invoked, it tries to +// acquire a buffer from the pool but if that buffer is too small, it returns it +// to the pool and creates a new one. +type simpleBufferPool struct { + pool sync.Pool +} + +func (p *simpleBufferPool) Get(size int) *[]byte { + bs, ok := p.pool.Get().(*[]byte) + if ok && cap(*bs) >= size { + *bs = (*bs)[:size] + return bs + } + + // A buffer was pulled from the pool, but it is too small. Put it back in + // the pool and create one large enough. + if ok { + p.pool.Put(bs) + } + + b := make([]byte, size) + return &b +} + +func (p *simpleBufferPool) Put(buf *[]byte) { + p.pool.Put(buf) +} + +var _ BufferPool = NopBufferPool{} + +// NopBufferPool is a buffer pool that returns new buffers without pooling. +type NopBufferPool struct{} + +// Get returns a buffer with specified length from the pool. +func (NopBufferPool) Get(length int) *[]byte { + b := make([]byte, length) + return &b +} + +// Put returns a buffer to the pool. +func (NopBufferPool) Put(*[]byte) { +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_slice.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_slice.go new file mode 100644 index 00000000000..228e9c2f20f --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffer_slice.go @@ -0,0 +1,226 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 mem + +import ( + "io" +) + +// BufferSlice offers a means to represent data that spans one or more Buffer +// instances. A BufferSlice is meant to be immutable after creation, and methods +// like Ref create and return copies of the slice. This is why all methods have +// value receivers rather than pointer receivers. +// +// Note that any of the methods that read the underlying buffers such as Ref, +// Len or CopyTo etc., will panic if any underlying buffers have already been +// freed. It is recommended to not directly interact with any of the underlying +// buffers directly, rather such interactions should be mediated through the +// various methods on this type. +// +// By convention, any APIs that return (mem.BufferSlice, error) should reduce +// the burden on the caller by never returning a mem.BufferSlice that needs to +// be freed if the error is non-nil, unless explicitly stated. +type BufferSlice []Buffer + +// Len returns the sum of the length of all the Buffers in this slice. +// +// # Warning +// +// Invoking the built-in len on a BufferSlice will return the number of buffers +// in the slice, and *not* the value returned by this function. +func (s BufferSlice) Len() int { + var length int + for _, b := range s { + length += b.Len() + } + return length +} + +// Ref invokes Ref on each buffer in the slice. +func (s BufferSlice) Ref() { + for _, b := range s { + b.Ref() + } +} + +// Free invokes Buffer.Free() on each Buffer in the slice. +func (s BufferSlice) Free() { + for _, b := range s { + b.Free() + } +} + +// CopyTo copies each of the underlying Buffer's data into the given buffer, +// returning the number of bytes copied. Has the same semantics as the copy +// builtin in that it will copy as many bytes as it can, stopping when either dst +// is full or s runs out of data, returning the minimum of s.Len() and len(dst). +func (s BufferSlice) CopyTo(dst []byte) int { + off := 0 + for _, b := range s { + off += copy(dst[off:], b.ReadOnlyData()) + } + return off +} + +// Materialize concatenates all the underlying Buffer's data into a single +// contiguous buffer using CopyTo. +func (s BufferSlice) Materialize() []byte { + l := s.Len() + if l == 0 { + return nil + } + out := make([]byte, l) + s.CopyTo(out) + return out +} + +// MaterializeToBuffer functions like Materialize except that it writes the data +// to a single Buffer pulled from the given BufferPool. +// +// As a special case, if the input BufferSlice only actually has one Buffer, this +// function simply increases the refcount before returning said Buffer. Freeing this +// buffer won't release it until the BufferSlice is itself released. +func (s BufferSlice) MaterializeToBuffer(pool BufferPool) Buffer { + if len(s) == 1 { + s[0].Ref() + return s[0] + } + sLen := s.Len() + if sLen == 0 { + return emptyBuffer{} + } + buf := pool.Get(sLen) + s.CopyTo(*buf) + return NewBuffer(buf, pool) +} + +// Reader returns a new Reader for the input slice after taking references to +// each underlying buffer. +func (s BufferSlice) Reader() Reader { + s.Ref() + return &sliceReader{ + data: s, + len: s.Len(), + } +} + +// Reader exposes a BufferSlice's data as an io.Reader, allowing it to interface +// with other parts systems. It also provides an additional convenience method +// Remaining(), which returns the number of unread bytes remaining in the slice. +// Buffers will be freed as they are read. +type Reader interface { + io.Reader + io.ByteReader + // Close frees the underlying BufferSlice and never returns an error. Subsequent + // calls to Read will return (0, io.EOF). + Close() error + // Remaining returns the number of unread bytes remaining in the slice. + Remaining() int +} + +type sliceReader struct { + data BufferSlice + len int + // The index into data[0].ReadOnlyData(). + bufferIdx int +} + +func (r *sliceReader) Remaining() int { + return r.len +} + +func (r *sliceReader) Close() error { + r.data.Free() + r.data = nil + r.len = 0 + return nil +} + +func (r *sliceReader) freeFirstBufferIfEmpty() bool { + if len(r.data) == 0 || r.bufferIdx != len(r.data[0].ReadOnlyData()) { + return false + } + + r.data[0].Free() + r.data = r.data[1:] + r.bufferIdx = 0 + return true +} + +func (r *sliceReader) Read(buf []byte) (n int, _ error) { + if r.len == 0 { + return 0, io.EOF + } + + for len(buf) != 0 && r.len != 0 { + // Copy as much as possible from the first Buffer in the slice into the + // given byte slice. + data := r.data[0].ReadOnlyData() + copied := copy(buf, data[r.bufferIdx:]) + r.len -= copied // Reduce len by the number of bytes copied. + r.bufferIdx += copied // Increment the buffer index. + n += copied // Increment the total number of bytes read. + buf = buf[copied:] // Shrink the given byte slice. + + // If we have copied all the data from the first Buffer, free it and advance to + // the next in the slice. + r.freeFirstBufferIfEmpty() + } + + return n, nil +} + +func (r *sliceReader) ReadByte() (byte, error) { + if r.len == 0 { + return 0, io.EOF + } + + // There may be any number of empty buffers in the slice, clear them all until a + // non-empty buffer is reached. This is guaranteed to exit since r.len is not 0. + for r.freeFirstBufferIfEmpty() { + } + + b := r.data[0].ReadOnlyData()[r.bufferIdx] + r.len-- + r.bufferIdx++ + // Free the first buffer in the slice if the last byte was read + r.freeFirstBufferIfEmpty() + return b, nil +} + +var _ io.Writer = (*writer)(nil) + +type writer struct { + buffers *BufferSlice + pool BufferPool +} + +func (w *writer) Write(p []byte) (n int, err error) { + b := Copy(p, w.pool) + *w.buffers = append(*w.buffers, b) + return b.Len(), nil +} + +// NewWriter wraps the given BufferSlice and BufferPool to implement the +// io.Writer interface. Every call to Write copies the contents of the given +// buffer into a new Buffer pulled from the given pool and the Buffer is added to +// the given BufferSlice. +func NewWriter(buffers *BufferSlice, pool BufferPool) io.Writer { + return &writer{buffers: buffers, pool: pool} +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffers.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffers.go new file mode 100644 index 00000000000..4d66b2ccc2b --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/mem/buffers.go @@ -0,0 +1,252 @@ +/* + * + * Copyright 2024 gRPC authors. + * + * 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 mem provides utilities that facilitate memory reuse in byte slices +// that are used as buffers. +// +// # Experimental +// +// Notice: All APIs in this package are EXPERIMENTAL and may be changed or +// removed in a later release. +package mem + +import ( + "fmt" + "sync" + "sync/atomic" +) + +// A Buffer represents a reference counted piece of data (in bytes) that can be +// acquired by a call to NewBuffer() or Copy(). A reference to a Buffer may be +// released by calling Free(), which invokes the free function given at creation +// only after all references are released. +// +// Note that a Buffer is not safe for concurrent access and instead each +// goroutine should use its own reference to the data, which can be acquired via +// a call to Ref(). +// +// Attempts to access the underlying data after releasing the reference to the +// Buffer will panic. +type Buffer interface { + // ReadOnlyData returns the underlying byte slice. Note that it is undefined + // behavior to modify the contents of this slice in any way. + ReadOnlyData() []byte + // Ref increases the reference counter for this Buffer. + Ref() + // Free decrements this Buffer's reference counter and frees the underlying + // byte slice if the counter reaches 0 as a result of this call. + Free() + // Len returns the Buffer's size. + Len() int + + split(n int) (left, right Buffer) + read(buf []byte) (int, Buffer) +} + +var ( + bufferPoolingThreshold = 1 << 10 + + bufferObjectPool = sync.Pool{New: func() any { return new(buffer) }} + refObjectPool = sync.Pool{New: func() any { return new(atomic.Int32) }} +) + +func IsBelowBufferPoolingThreshold(size int) bool { + return size <= bufferPoolingThreshold +} + +type buffer struct { + origData *[]byte + data []byte + refs *atomic.Int32 + pool BufferPool +} + +func newBuffer() *buffer { + return bufferObjectPool.Get().(*buffer) +} + +// NewBuffer creates a new Buffer from the given data, initializing the reference +// counter to 1. The data will then be returned to the given pool when all +// references to the returned Buffer are released. As a special case to avoid +// additional allocations, if the given buffer pool is nil, the returned buffer +// will be a "no-op" Buffer where invoking Buffer.Free() does nothing and the +// underlying data is never freed. +// +// Note that the backing array of the given data is not copied. +func NewBuffer(data *[]byte, pool BufferPool) Buffer { + if pool == nil || IsBelowBufferPoolingThreshold(len(*data)) { + return (SliceBuffer)(*data) + } + b := newBuffer() + b.origData = data + b.data = *data + b.pool = pool + b.refs = refObjectPool.Get().(*atomic.Int32) + b.refs.Add(1) + return b +} + +// Copy creates a new Buffer from the given data, initializing the reference +// counter to 1. +// +// It acquires a []byte from the given pool and copies over the backing array +// of the given data. The []byte acquired from the pool is returned to the +// pool when all references to the returned Buffer are released. +func Copy(data []byte, pool BufferPool) Buffer { + if IsBelowBufferPoolingThreshold(len(data)) { + buf := make(SliceBuffer, len(data)) + copy(buf, data) + return buf + } + + buf := pool.Get(len(data)) + copy(*buf, data) + return NewBuffer(buf, pool) +} + +func (b *buffer) ReadOnlyData() []byte { + if b.refs == nil { + panic("Cannot read freed buffer") + } + return b.data +} + +func (b *buffer) Ref() { + if b.refs == nil { + panic("Cannot ref freed buffer") + } + b.refs.Add(1) +} + +func (b *buffer) Free() { + if b.refs == nil { + panic("Cannot free freed buffer") + } + + refs := b.refs.Add(-1) + switch { + case refs > 0: + return + case refs == 0: + if b.pool != nil { + b.pool.Put(b.origData) + } + + refObjectPool.Put(b.refs) + b.origData = nil + b.data = nil + b.refs = nil + b.pool = nil + bufferObjectPool.Put(b) + default: + panic("Cannot free freed buffer") + } +} + +func (b *buffer) Len() int { + return len(b.ReadOnlyData()) +} + +func (b *buffer) split(n int) (Buffer, Buffer) { + if b.refs == nil { + panic("Cannot split freed buffer") + } + + b.refs.Add(1) + split := newBuffer() + split.origData = b.origData + split.data = b.data[n:] + split.refs = b.refs + split.pool = b.pool + + b.data = b.data[:n] + + return b, split +} + +func (b *buffer) read(buf []byte) (int, Buffer) { + if b.refs == nil { + panic("Cannot read freed buffer") + } + + n := copy(buf, b.data) + if n == len(b.data) { + b.Free() + return n, nil + } + + b.data = b.data[n:] + return n, b +} + +// String returns a string representation of the buffer. May be used for +// debugging purposes. +func (b *buffer) String() string { + return fmt.Sprintf("mem.Buffer(%p, data: %p, length: %d)", b, b.ReadOnlyData(), len(b.ReadOnlyData())) +} + +func ReadUnsafe(dst []byte, buf Buffer) (int, Buffer) { + return buf.read(dst) +} + +// SplitUnsafe modifies the receiver to point to the first n bytes while it +// returns a new reference to the remaining bytes. The returned Buffer functions +// just like a normal reference acquired using Ref(). +func SplitUnsafe(buf Buffer, n int) (left, right Buffer) { + return buf.split(n) +} + +type emptyBuffer struct{} + +func (e emptyBuffer) ReadOnlyData() []byte { + return nil +} + +func (e emptyBuffer) Ref() {} +func (e emptyBuffer) Free() {} + +func (e emptyBuffer) Len() int { + return 0 +} + +func (e emptyBuffer) split(int) (left, right Buffer) { + return e, e +} + +func (e emptyBuffer) read([]byte) (int, Buffer) { + return 0, e +} + +type SliceBuffer []byte + +func (s SliceBuffer) ReadOnlyData() []byte { return s } +func (s SliceBuffer) Ref() {} +func (s SliceBuffer) Free() {} +func (s SliceBuffer) Len() int { return len(s) } + +func (s SliceBuffer) split(n int) (left, right Buffer) { + return s[:n], s[n:] +} + +func (s SliceBuffer) read(buf []byte) (int, Buffer) { + n := copy(buf, s) + if n == len(s) { + return n, nil + } + return n, s[n:] +} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/metadata/metadata.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/metadata/metadata.go index 1e9485fd6e2..d2e15253bbf 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/metadata/metadata.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/metadata/metadata.go @@ -213,11 +213,6 @@ func FromIncomingContext(ctx context.Context) (MD, bool) { // ValueFromIncomingContext returns the metadata value corresponding to the metadata // key from the incoming metadata if it exists. Keys are matched in a case insensitive // manner. -// -// # Experimental -// -// Notice: This API is EXPERIMENTAL and may be changed or removed in a -// later release. func ValueFromIncomingContext(ctx context.Context, key string) []string { md, ok := ctx.Value(mdIncomingKey{}).(MD) if !ok { @@ -228,7 +223,7 @@ func ValueFromIncomingContext(ctx context.Context, key string) []string { return copyOf(v) } for k, v := range md { - // Case insenitive comparison: MD is a map, and there's no guarantee + // Case insensitive comparison: MD is a map, and there's no guarantee // that the MD attached to the context is created using our helper // functions. if strings.EqualFold(k, key) { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/preloader.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/preloader.go index 73bd6336433..e87a17f36a5 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/preloader.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/preloader.go @@ -20,6 +20,7 @@ package grpc import ( "google.golang.org/grpc/codes" + "google.golang.org/grpc/mem" "google.golang.org/grpc/status" ) @@ -31,9 +32,10 @@ import ( // later release. type PreparedMsg struct { // Struct for preparing msg before sending them - encodedData []byte + encodedData mem.BufferSlice hdr []byte - payload []byte + payload mem.BufferSlice + pf payloadFormat } // Encode marshalls and compresses the message using the codec and compressor for the stream. @@ -57,11 +59,27 @@ func (p *PreparedMsg) Encode(s Stream, msg any) error { if err != nil { return err } - p.encodedData = data - compData, err := compress(data, rpcInfo.preloaderInfo.cp, rpcInfo.preloaderInfo.comp) + + materializedData := data.Materialize() + data.Free() + p.encodedData = mem.BufferSlice{mem.NewBuffer(&materializedData, nil)} + + // TODO: it should be possible to grab the bufferPool from the underlying + // stream implementation with a type cast to its actual type (such as + // addrConnStream) and accessing the buffer pool directly. + var compData mem.BufferSlice + compData, p.pf, err = compress(p.encodedData, rpcInfo.preloaderInfo.cp, rpcInfo.preloaderInfo.comp, mem.DefaultBufferPool()) if err != nil { return err } - p.hdr, p.payload = msgHeader(data, compData) + + if p.pf.isCompressed() { + materializedCompData := compData.Materialize() + compData.Free() + compData = mem.BufferSlice{mem.NewBuffer(&materializedCompData, nil)} + } + + p.hdr, p.payload = msgHeader(p.encodedData, compData, p.pf) + return nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/regenerate.sh b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/regenerate.sh deleted file mode 100644 index 3edca296c22..00000000000 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/regenerate.sh +++ /dev/null @@ -1,123 +0,0 @@ -#!/bin/bash -# Copyright 2020 gRPC authors. -# -# 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. - -set -eu -o pipefail - -WORKDIR=$(mktemp -d) - -function finish { - rm -rf "$WORKDIR" -} -trap finish EXIT - -export GOBIN=${WORKDIR}/bin -export PATH=${GOBIN}:${PATH} -mkdir -p ${GOBIN} - -echo "remove existing generated files" -# grpc_testing_not_regenerate/*.pb.go is not re-generated, -# see grpc_testing_not_regenerate/README.md for details. -rm -f $(find . -name '*.pb.go' | grep -v 'grpc_testing_not_regenerate') - -echo "go install google.golang.org/protobuf/cmd/protoc-gen-go" -(cd test/tools && go install google.golang.org/protobuf/cmd/protoc-gen-go) - -echo "go install cmd/protoc-gen-go-grpc" -(cd cmd/protoc-gen-go-grpc && go install .) - -echo "git clone https://github.com/grpc/grpc-proto" -git clone --quiet https://github.com/grpc/grpc-proto ${WORKDIR}/grpc-proto - -echo "git clone https://github.com/protocolbuffers/protobuf" -git clone --quiet https://github.com/protocolbuffers/protobuf ${WORKDIR}/protobuf - -# Pull in code.proto as a proto dependency -mkdir -p ${WORKDIR}/googleapis/google/rpc -echo "curl https://raw.githubusercontent.com/googleapis/googleapis/master/google/rpc/code.proto" -curl --silent https://raw.githubusercontent.com/googleapis/googleapis/master/google/rpc/code.proto > ${WORKDIR}/googleapis/google/rpc/code.proto - -mkdir -p ${WORKDIR}/out - -# Generates sources without the embed requirement -LEGACY_SOURCES=( - ${WORKDIR}/grpc-proto/grpc/binlog/v1/binarylog.proto - ${WORKDIR}/grpc-proto/grpc/channelz/v1/channelz.proto - ${WORKDIR}/grpc-proto/grpc/health/v1/health.proto - ${WORKDIR}/grpc-proto/grpc/lb/v1/load_balancer.proto - profiling/proto/service.proto - ${WORKDIR}/grpc-proto/grpc/reflection/v1alpha/reflection.proto - ${WORKDIR}/grpc-proto/grpc/reflection/v1/reflection.proto -) - -# Generates only the new gRPC Service symbols -SOURCES=( - $(git ls-files --exclude-standard --cached --others "*.proto" | grep -v '^profiling/proto/service.proto$') - ${WORKDIR}/grpc-proto/grpc/gcp/altscontext.proto - ${WORKDIR}/grpc-proto/grpc/gcp/handshaker.proto - ${WORKDIR}/grpc-proto/grpc/gcp/transport_security_common.proto - ${WORKDIR}/grpc-proto/grpc/lookup/v1/rls.proto - ${WORKDIR}/grpc-proto/grpc/lookup/v1/rls_config.proto - ${WORKDIR}/grpc-proto/grpc/testing/*.proto - ${WORKDIR}/grpc-proto/grpc/core/*.proto -) - -# These options of the form 'Mfoo.proto=bar' instruct the codegen to use an -# import path of 'bar' in the generated code when 'foo.proto' is imported in -# one of the sources. -# -# Note that the protos listed here are all for testing purposes. All protos to -# be used externally should have a go_package option (and they don't need to be -# listed here). -OPTS=Mgrpc/core/stats.proto=google.golang.org/grpc/interop/grpc_testing/core,\ -Mgrpc/testing/benchmark_service.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/stats.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/report_qps_scenario_service.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/messages.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/worker_service.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/control.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/test.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/payloads.proto=google.golang.org/grpc/interop/grpc_testing,\ -Mgrpc/testing/empty.proto=google.golang.org/grpc/interop/grpc_testing - -for src in ${SOURCES[@]}; do - echo "protoc ${src}" - protoc --go_out=${OPTS}:${WORKDIR}/out --go-grpc_out=${OPTS},use_generic_streams_experimental=true:${WORKDIR}/out \ - -I"." \ - -I${WORKDIR}/grpc-proto \ - -I${WORKDIR}/googleapis \ - -I${WORKDIR}/protobuf/src \ - ${src} -done - -for src in ${LEGACY_SOURCES[@]}; do - echo "protoc ${src}" - protoc --go_out=${OPTS}:${WORKDIR}/out --go-grpc_out=${OPTS},require_unimplemented_servers=false:${WORKDIR}/out \ - -I"." \ - -I${WORKDIR}/grpc-proto \ - -I${WORKDIR}/googleapis \ - -I${WORKDIR}/protobuf/src \ - ${src} -done - -# The go_package option in grpc/lookup/v1/rls.proto doesn't match the -# current location. Move it into the right place. -mkdir -p ${WORKDIR}/out/google.golang.org/grpc/internal/proto/grpc_lookup_v1 -mv ${WORKDIR}/out/google.golang.org/grpc/lookup/grpc_lookup_v1/* ${WORKDIR}/out/google.golang.org/grpc/internal/proto/grpc_lookup_v1 - -# grpc_testing_not_regenerate/*.pb.go are not re-generated, -# see grpc_testing_not_regenerate/README.md for details. -rm ${WORKDIR}/out/google.golang.org/grpc/reflection/test/grpc_testing_not_regenerate/*.pb.go - -cp -R ${WORKDIR}/out/google.golang.org/grpc/* . diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/resolver_wrapper.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/resolver_wrapper.go index c5fb45236fa..23bb3fb2582 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/resolver_wrapper.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/resolver_wrapper.go @@ -66,7 +66,7 @@ func newCCResolverWrapper(cc *ClientConn) *ccResolverWrapper { // any newly created ccResolverWrapper, except that close may be called instead. func (ccr *ccResolverWrapper) start() error { errCh := make(chan error) - ccr.serializer.Schedule(func(ctx context.Context) { + ccr.serializer.TrySchedule(func(ctx context.Context) { if ctx.Err() != nil { return } @@ -85,7 +85,7 @@ func (ccr *ccResolverWrapper) start() error { } func (ccr *ccResolverWrapper) resolveNow(o resolver.ResolveNowOptions) { - ccr.serializer.Schedule(func(ctx context.Context) { + ccr.serializer.TrySchedule(func(ctx context.Context) { if ctx.Err() != nil || ccr.resolver == nil { return } @@ -102,7 +102,7 @@ func (ccr *ccResolverWrapper) close() { ccr.closed = true ccr.mu.Unlock() - ccr.serializer.Schedule(func(context.Context) { + ccr.serializer.TrySchedule(func(context.Context) { if ccr.resolver == nil { return } @@ -177,6 +177,9 @@ func (ccr *ccResolverWrapper) ParseServiceConfig(scJSON string) *serviceconfig.P // addChannelzTraceEvent adds a channelz trace event containing the new // state received from resolver implementations. func (ccr *ccResolverWrapper) addChannelzTraceEvent(s resolver.State) { + if !logger.V(0) && !channelz.IsOn() { + return + } var updates []string var oldSC, newSC *ServiceConfig var oldOK, newOK bool diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/rpc_util.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/rpc_util.go index fdd49e6e915..2d96f1405e8 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/rpc_util.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/rpc_util.go @@ -19,7 +19,6 @@ package grpc import ( - "bytes" "compress/gzip" "context" "encoding/binary" @@ -35,6 +34,7 @@ import ( "google.golang.org/grpc/encoding" "google.golang.org/grpc/encoding/proto" "google.golang.org/grpc/internal/transport" + "google.golang.org/grpc/mem" "google.golang.org/grpc/metadata" "google.golang.org/grpc/peer" "google.golang.org/grpc/stats" @@ -220,8 +220,8 @@ type HeaderCallOption struct { HeaderAddr *metadata.MD } -func (o HeaderCallOption) before(c *callInfo) error { return nil } -func (o HeaderCallOption) after(c *callInfo, attempt *csAttempt) { +func (o HeaderCallOption) before(*callInfo) error { return nil } +func (o HeaderCallOption) after(_ *callInfo, attempt *csAttempt) { *o.HeaderAddr, _ = attempt.s.Header() } @@ -242,8 +242,8 @@ type TrailerCallOption struct { TrailerAddr *metadata.MD } -func (o TrailerCallOption) before(c *callInfo) error { return nil } -func (o TrailerCallOption) after(c *callInfo, attempt *csAttempt) { +func (o TrailerCallOption) before(*callInfo) error { return nil } +func (o TrailerCallOption) after(_ *callInfo, attempt *csAttempt) { *o.TrailerAddr = attempt.s.Trailer() } @@ -264,24 +264,20 @@ type PeerCallOption struct { PeerAddr *peer.Peer } -func (o PeerCallOption) before(c *callInfo) error { return nil } -func (o PeerCallOption) after(c *callInfo, attempt *csAttempt) { +func (o PeerCallOption) before(*callInfo) error { return nil } +func (o PeerCallOption) after(_ *callInfo, attempt *csAttempt) { if x, ok := peer.FromContext(attempt.s.Context()); ok { *o.PeerAddr = *x } } -// WaitForReady configures the action to take when an RPC is attempted on broken -// connections or unreachable servers. If waitForReady is false and the -// connection is in the TRANSIENT_FAILURE state, the RPC will fail -// immediately. Otherwise, the RPC client will block the call until a -// connection is available (or the call is canceled or times out) and will -// retry the call if it fails due to a transient error. gRPC will not retry if -// data was written to the wire unless the server indicates it did not process -// the data. Please refer to -// https://github.com/grpc/grpc/blob/master/doc/wait-for-ready.md. +// WaitForReady configures the RPC's behavior when the client is in +// TRANSIENT_FAILURE, which occurs when all addresses fail to connect. If +// waitForReady is false, the RPC will fail immediately. Otherwise, the client +// will wait until a connection becomes available or the RPC's deadline is +// reached. // -// By default, RPCs don't "wait for ready". +// By default, RPCs do not "wait for ready". func WaitForReady(waitForReady bool) CallOption { return FailFastCallOption{FailFast: !waitForReady} } @@ -308,7 +304,7 @@ func (o FailFastCallOption) before(c *callInfo) error { c.failFast = o.FailFast return nil } -func (o FailFastCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o FailFastCallOption) after(*callInfo, *csAttempt) {} // OnFinish returns a CallOption that configures a callback to be called when // the call completes. The error passed to the callback is the status of the @@ -343,7 +339,7 @@ func (o OnFinishCallOption) before(c *callInfo) error { return nil } -func (o OnFinishCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o OnFinishCallOption) after(*callInfo, *csAttempt) {} // MaxCallRecvMsgSize returns a CallOption which sets the maximum message size // in bytes the client can receive. If this is not set, gRPC uses the default @@ -367,7 +363,7 @@ func (o MaxRecvMsgSizeCallOption) before(c *callInfo) error { c.maxReceiveMessageSize = &o.MaxRecvMsgSize return nil } -func (o MaxRecvMsgSizeCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o MaxRecvMsgSizeCallOption) after(*callInfo, *csAttempt) {} // MaxCallSendMsgSize returns a CallOption which sets the maximum message size // in bytes the client can send. If this is not set, gRPC uses the default @@ -391,7 +387,7 @@ func (o MaxSendMsgSizeCallOption) before(c *callInfo) error { c.maxSendMessageSize = &o.MaxSendMsgSize return nil } -func (o MaxSendMsgSizeCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o MaxSendMsgSizeCallOption) after(*callInfo, *csAttempt) {} // PerRPCCredentials returns a CallOption that sets credentials.PerRPCCredentials // for a call. @@ -414,7 +410,7 @@ func (o PerRPCCredsCallOption) before(c *callInfo) error { c.creds = o.Creds return nil } -func (o PerRPCCredsCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o PerRPCCredsCallOption) after(*callInfo, *csAttempt) {} // UseCompressor returns a CallOption which sets the compressor used when // sending the request. If WithCompressor is also set, UseCompressor has @@ -442,7 +438,7 @@ func (o CompressorCallOption) before(c *callInfo) error { c.compressorType = o.CompressorType return nil } -func (o CompressorCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o CompressorCallOption) after(*callInfo, *csAttempt) {} // CallContentSubtype returns a CallOption that will set the content-subtype // for a call. For example, if content-subtype is "json", the Content-Type over @@ -479,7 +475,7 @@ func (o ContentSubtypeCallOption) before(c *callInfo) error { c.contentSubtype = o.ContentSubtype return nil } -func (o ContentSubtypeCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o ContentSubtypeCallOption) after(*callInfo, *csAttempt) {} // ForceCodec returns a CallOption that will set codec to be used for all // request and response messages for a call. The result of calling Name() will @@ -515,10 +511,50 @@ type ForceCodecCallOption struct { } func (o ForceCodecCallOption) before(c *callInfo) error { - c.codec = o.Codec + c.codec = newCodecV1Bridge(o.Codec) return nil } -func (o ForceCodecCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o ForceCodecCallOption) after(*callInfo, *csAttempt) {} + +// ForceCodecV2 returns a CallOption that will set codec to be used for all +// request and response messages for a call. The result of calling Name() will +// be used as the content-subtype after converting to lowercase, unless +// CallContentSubtype is also used. +// +// See Content-Type on +// https://github.com/grpc/grpc/blob/master/doc/PROTOCOL-HTTP2.md#requests for +// more details. Also see the documentation on RegisterCodec and +// CallContentSubtype for more details on the interaction between Codec and +// content-subtype. +// +// This function is provided for advanced users; prefer to use only +// CallContentSubtype to select a registered codec instead. +// +// # Experimental +// +// Notice: This API is EXPERIMENTAL and may be changed or removed in a +// later release. +func ForceCodecV2(codec encoding.CodecV2) CallOption { + return ForceCodecV2CallOption{CodecV2: codec} +} + +// ForceCodecV2CallOption is a CallOption that indicates the codec used for +// marshaling messages. +// +// # Experimental +// +// Notice: This type is EXPERIMENTAL and may be changed or removed in a +// later release. +type ForceCodecV2CallOption struct { + CodecV2 encoding.CodecV2 +} + +func (o ForceCodecV2CallOption) before(c *callInfo) error { + c.codec = o.CodecV2 + return nil +} + +func (o ForceCodecV2CallOption) after(*callInfo, *csAttempt) {} // CallCustomCodec behaves like ForceCodec, but accepts a grpc.Codec instead of // an encoding.Codec. @@ -540,10 +576,10 @@ type CustomCodecCallOption struct { } func (o CustomCodecCallOption) before(c *callInfo) error { - c.codec = o.Codec + c.codec = newCodecV0Bridge(o.Codec) return nil } -func (o CustomCodecCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o CustomCodecCallOption) after(*callInfo, *csAttempt) {} // MaxRetryRPCBufferSize returns a CallOption that limits the amount of memory // used for buffering this RPC's requests for retry purposes. @@ -571,7 +607,7 @@ func (o MaxRetryRPCBufferSizeCallOption) before(c *callInfo) error { c.maxRetryRPCBufferSize = o.MaxRetryRPCBufferSize return nil } -func (o MaxRetryRPCBufferSizeCallOption) after(c *callInfo, attempt *csAttempt) {} +func (o MaxRetryRPCBufferSizeCallOption) after(*callInfo, *csAttempt) {} // The format of the payload: compressed or not? type payloadFormat uint8 @@ -581,19 +617,28 @@ const ( compressionMade payloadFormat = 1 // compressed ) +func (pf payloadFormat) isCompressed() bool { + return pf == compressionMade +} + +type streamReader interface { + ReadHeader(header []byte) error + Read(n int) (mem.BufferSlice, error) +} + // parser reads complete gRPC messages from the underlying reader. type parser struct { // r is the underlying reader. // See the comment on recvMsg for the permissible // error types. - r io.Reader + r streamReader // The header of a gRPC message. Find more detail at // https://github.com/grpc/grpc/blob/master/doc/PROTOCOL-HTTP2.md header [5]byte - // recvBufferPool is the pool of shared receive buffers. - recvBufferPool SharedBufferPool + // bufferPool is the pool of shared receive buffers. + bufferPool mem.BufferPool } // recvMsg reads a complete gRPC message from the stream. @@ -608,14 +653,15 @@ type parser struct { // - an error from the status package // // No other error values or types must be returned, which also means -// that the underlying io.Reader must not return an incompatible +// that the underlying streamReader must not return an incompatible // error. -func (p *parser) recvMsg(maxReceiveMessageSize int) (pf payloadFormat, msg []byte, err error) { - if _, err := p.r.Read(p.header[:]); err != nil { +func (p *parser) recvMsg(maxReceiveMessageSize int) (payloadFormat, mem.BufferSlice, error) { + err := p.r.ReadHeader(p.header[:]) + if err != nil { return 0, nil, err } - pf = payloadFormat(p.header[0]) + pf := payloadFormat(p.header[0]) length := binary.BigEndian.Uint32(p.header[1:]) if length == 0 { @@ -627,20 +673,21 @@ func (p *parser) recvMsg(maxReceiveMessageSize int) (pf payloadFormat, msg []byt if int(length) > maxReceiveMessageSize { return 0, nil, status.Errorf(codes.ResourceExhausted, "grpc: received message larger than max (%d vs. %d)", length, maxReceiveMessageSize) } - msg = p.recvBufferPool.Get(int(length)) - if _, err := p.r.Read(msg); err != nil { + + data, err := p.r.Read(int(length)) + if err != nil { if err == io.EOF { err = io.ErrUnexpectedEOF } return 0, nil, err } - return pf, msg, nil + return pf, data, nil } // encode serializes msg and returns a buffer containing the message, or an // error if it is too large to be transmitted by grpc. If msg is nil, it // generates an empty message. -func encode(c baseCodec, msg any) ([]byte, error) { +func encode(c baseCodec, msg any) (mem.BufferSlice, error) { if msg == nil { // NOTE: typed nils will not be caught by this check return nil, nil } @@ -648,7 +695,8 @@ func encode(c baseCodec, msg any) ([]byte, error) { if err != nil { return nil, status.Errorf(codes.Internal, "grpc: error while marshaling: %v", err.Error()) } - if uint(len(b)) > math.MaxUint32 { + if uint(b.Len()) > math.MaxUint32 { + b.Free() return nil, status.Errorf(codes.ResourceExhausted, "grpc: message too large (%d bytes)", len(b)) } return b, nil @@ -659,34 +707,41 @@ func encode(c baseCodec, msg any) ([]byte, error) { // indicating no compression was done. // // TODO(dfawley): eliminate cp parameter by wrapping Compressor in an encoding.Compressor. -func compress(in []byte, cp Compressor, compressor encoding.Compressor) ([]byte, error) { - if compressor == nil && cp == nil { - return nil, nil - } - if len(in) == 0 { - return nil, nil +func compress(in mem.BufferSlice, cp Compressor, compressor encoding.Compressor, pool mem.BufferPool) (mem.BufferSlice, payloadFormat, error) { + if (compressor == nil && cp == nil) || in.Len() == 0 { + return nil, compressionNone, nil } + var out mem.BufferSlice + w := mem.NewWriter(&out, pool) wrapErr := func(err error) error { + out.Free() return status.Errorf(codes.Internal, "grpc: error while compressing: %v", err.Error()) } - cbuf := &bytes.Buffer{} if compressor != nil { - z, err := compressor.Compress(cbuf) + z, err := compressor.Compress(w) if err != nil { - return nil, wrapErr(err) + return nil, 0, wrapErr(err) } - if _, err := z.Write(in); err != nil { - return nil, wrapErr(err) + for _, b := range in { + if _, err := z.Write(b.ReadOnlyData()); err != nil { + return nil, 0, wrapErr(err) + } } if err := z.Close(); err != nil { - return nil, wrapErr(err) + return nil, 0, wrapErr(err) } } else { - if err := cp.Do(cbuf, in); err != nil { - return nil, wrapErr(err) + // This is obviously really inefficient since it fully materializes the data, but + // there is no way around this with the old Compressor API. At least it attempts + // to return the buffer to the provider, in the hopes it can be reused (maybe + // even by a subsequent call to this very function). + buf := in.MaterializeToBuffer(pool) + defer buf.Free() + if err := cp.Do(w, buf.ReadOnlyData()); err != nil { + return nil, 0, wrapErr(err) } } - return cbuf.Bytes(), nil + return out, compressionMade, nil } const ( @@ -697,33 +752,36 @@ const ( // msgHeader returns a 5-byte header for the message being transmitted and the // payload, which is compData if non-nil or data otherwise. -func msgHeader(data, compData []byte) (hdr []byte, payload []byte) { +func msgHeader(data, compData mem.BufferSlice, pf payloadFormat) (hdr []byte, payload mem.BufferSlice) { hdr = make([]byte, headerLen) - if compData != nil { - hdr[0] = byte(compressionMade) - data = compData + hdr[0] = byte(pf) + + var length uint32 + if pf.isCompressed() { + length = uint32(compData.Len()) + payload = compData } else { - hdr[0] = byte(compressionNone) + length = uint32(data.Len()) + payload = data } // Write length of payload into buf - binary.BigEndian.PutUint32(hdr[payloadLen:], uint32(len(data))) - return hdr, data + binary.BigEndian.PutUint32(hdr[payloadLen:], length) + return hdr, payload } -func outPayload(client bool, msg any, data, payload []byte, t time.Time) *stats.OutPayload { +func outPayload(client bool, msg any, dataLength, payloadLength int, t time.Time) *stats.OutPayload { return &stats.OutPayload{ Client: client, Payload: msg, - Data: data, - Length: len(data), - WireLength: len(payload) + headerLen, - CompressedLength: len(payload), + Length: dataLength, + WireLength: payloadLength + headerLen, + CompressedLength: payloadLength, SentTime: t, } } -func checkRecvPayload(pf payloadFormat, recvCompress string, haveCompressor bool) *status.Status { +func checkRecvPayload(pf payloadFormat, recvCompress string, haveCompressor bool, isServer bool) *status.Status { switch pf { case compressionNone: case compressionMade: @@ -731,7 +789,11 @@ func checkRecvPayload(pf payloadFormat, recvCompress string, haveCompressor bool return status.New(codes.Internal, "grpc: compressed flag set with identity or empty encoding") } if !haveCompressor { - return status.Newf(codes.Unimplemented, "grpc: Decompressor is not installed for grpc-encoding %q", recvCompress) + if isServer { + return status.Newf(codes.Unimplemented, "grpc: Decompressor is not installed for grpc-encoding %q", recvCompress) + } else { + return status.Newf(codes.Internal, "grpc: Decompressor is not installed for grpc-encoding %q", recvCompress) + } } default: return status.Newf(codes.Internal, "grpc: received unexpected payload format %d", pf) @@ -741,104 +803,129 @@ func checkRecvPayload(pf payloadFormat, recvCompress string, haveCompressor bool type payloadInfo struct { compressedLength int // The compressed length got from wire. - uncompressedBytes []byte + uncompressedBytes mem.BufferSlice +} + +func (p *payloadInfo) free() { + if p != nil && p.uncompressedBytes != nil { + p.uncompressedBytes.Free() + } } // recvAndDecompress reads a message from the stream, decompressing it if necessary. // // Cancelling the returned cancel function releases the buffer back to the pool. So the caller should cancel as soon as // the buffer is no longer needed. -func recvAndDecompress(p *parser, s *transport.Stream, dc Decompressor, maxReceiveMessageSize int, payInfo *payloadInfo, compressor encoding.Compressor, -) (uncompressedBuf []byte, cancel func(), err error) { - pf, compressedBuf, err := p.recvMsg(maxReceiveMessageSize) +// TODO: Refactor this function to reduce the number of arguments. +// See: https://google.github.io/styleguide/go/best-practices.html#function-argument-lists +func recvAndDecompress(p *parser, s *transport.Stream, dc Decompressor, maxReceiveMessageSize int, payInfo *payloadInfo, compressor encoding.Compressor, isServer bool, +) (out mem.BufferSlice, err error) { + pf, compressed, err := p.recvMsg(maxReceiveMessageSize) if err != nil { - return nil, nil, err + return nil, err } - if st := checkRecvPayload(pf, s.RecvCompress(), compressor != nil || dc != nil); st != nil { - return nil, nil, st.Err() + compressedLength := compressed.Len() + + if st := checkRecvPayload(pf, s.RecvCompress(), compressor != nil || dc != nil, isServer); st != nil { + compressed.Free() + return nil, st.Err() } var size int - if pf == compressionMade { + if pf.isCompressed() { + defer compressed.Free() + // To match legacy behavior, if the decompressor is set by WithDecompressor or RPCDecompressor, // use this decompressor as the default. if dc != nil { - uncompressedBuf, err = dc.Do(bytes.NewReader(compressedBuf)) + var uncompressedBuf []byte + uncompressedBuf, err = dc.Do(compressed.Reader()) + if err == nil { + out = mem.BufferSlice{mem.NewBuffer(&uncompressedBuf, nil)} + } size = len(uncompressedBuf) } else { - uncompressedBuf, size, err = decompress(compressor, compressedBuf, maxReceiveMessageSize) + out, size, err = decompress(compressor, compressed, maxReceiveMessageSize, p.bufferPool) } if err != nil { - return nil, nil, status.Errorf(codes.Internal, "grpc: failed to decompress the received message: %v", err) + return nil, status.Errorf(codes.Internal, "grpc: failed to decompress the received message: %v", err) } if size > maxReceiveMessageSize { + out.Free() // TODO: Revisit the error code. Currently keep it consistent with java // implementation. - return nil, nil, status.Errorf(codes.ResourceExhausted, "grpc: received message after decompression larger than max (%d vs. %d)", size, maxReceiveMessageSize) + return nil, status.Errorf(codes.ResourceExhausted, "grpc: received message after decompression larger than max (%d vs. %d)", size, maxReceiveMessageSize) } } else { - uncompressedBuf = compressedBuf + out = compressed } if payInfo != nil { - payInfo.compressedLength = len(compressedBuf) - payInfo.uncompressedBytes = uncompressedBuf - - cancel = func() {} - } else { - cancel = func() { - p.recvBufferPool.Put(&compressedBuf) - } + payInfo.compressedLength = compressedLength + out.Ref() + payInfo.uncompressedBytes = out } - return uncompressedBuf, cancel, nil + return out, nil } // Using compressor, decompress d, returning data and size. // Optionally, if data will be over maxReceiveMessageSize, just return the size. -func decompress(compressor encoding.Compressor, d []byte, maxReceiveMessageSize int) ([]byte, int, error) { - dcReader, err := compressor.Decompress(bytes.NewReader(d)) +func decompress(compressor encoding.Compressor, d mem.BufferSlice, maxReceiveMessageSize int, pool mem.BufferPool) (mem.BufferSlice, int, error) { + dcReader, err := compressor.Decompress(d.Reader()) if err != nil { return nil, 0, err } - if sizer, ok := compressor.(interface { - DecompressedSize(compressedBytes []byte) int - }); ok { - if size := sizer.DecompressedSize(d); size >= 0 { - if size > maxReceiveMessageSize { - return nil, size, nil - } - // size is used as an estimate to size the buffer, but we - // will read more data if available. - // +MinRead so ReadFrom will not reallocate if size is correct. - // - // TODO: If we ensure that the buffer size is the same as the DecompressedSize, - // we can also utilize the recv buffer pool here. - buf := bytes.NewBuffer(make([]byte, 0, size+bytes.MinRead)) - bytesRead, err := buf.ReadFrom(io.LimitReader(dcReader, int64(maxReceiveMessageSize)+1)) - return buf.Bytes(), int(bytesRead), err - } + + // TODO: Can/should this still be preserved with the new BufferSlice API? Are + // there any actual benefits to allocating a single large buffer instead of + // multiple smaller ones? + //if sizer, ok := compressor.(interface { + // DecompressedSize(compressedBytes []byte) int + //}); ok { + // if size := sizer.DecompressedSize(d); size >= 0 { + // if size > maxReceiveMessageSize { + // return nil, size, nil + // } + // // size is used as an estimate to size the buffer, but we + // // will read more data if available. + // // +MinRead so ReadFrom will not reallocate if size is correct. + // // + // // TODO: If we ensure that the buffer size is the same as the DecompressedSize, + // // we can also utilize the recv buffer pool here. + // buf := bytes.NewBuffer(make([]byte, 0, size+bytes.MinRead)) + // bytesRead, err := buf.ReadFrom(io.LimitReader(dcReader, int64(maxReceiveMessageSize)+1)) + // return buf.Bytes(), int(bytesRead), err + // } + //} + + var out mem.BufferSlice + _, err = io.Copy(mem.NewWriter(&out, pool), io.LimitReader(dcReader, int64(maxReceiveMessageSize)+1)) + if err != nil { + out.Free() + return nil, 0, err } - // Read from LimitReader with limit max+1. So if the underlying - // reader is over limit, the result will be bigger than max. - d, err = io.ReadAll(io.LimitReader(dcReader, int64(maxReceiveMessageSize)+1)) - return d, len(d), err + return out, out.Len(), nil } // For the two compressor parameters, both should not be set, but if they are, // dc takes precedence over compressor. // TODO(dfawley): wrap the old compressor/decompressor using the new API? -func recv(p *parser, c baseCodec, s *transport.Stream, dc Decompressor, m any, maxReceiveMessageSize int, payInfo *payloadInfo, compressor encoding.Compressor) error { - buf, cancel, err := recvAndDecompress(p, s, dc, maxReceiveMessageSize, payInfo, compressor) +func recv(p *parser, c baseCodec, s *transport.Stream, dc Decompressor, m any, maxReceiveMessageSize int, payInfo *payloadInfo, compressor encoding.Compressor, isServer bool) error { + data, err := recvAndDecompress(p, s, dc, maxReceiveMessageSize, payInfo, compressor, isServer) if err != nil { return err } - defer cancel() - if err := c.Unmarshal(buf, m); err != nil { + // If the codec wants its own reference to the data, it can get it. Otherwise, always + // free the buffers. + defer data.Free() + + if err := c.Unmarshal(data, m); err != nil { return status.Errorf(codes.Internal, "grpc: failed to unmarshal the received message: %v", err) } + return nil } @@ -941,7 +1028,7 @@ func setCallInfoCodec(c *callInfo) error { // encoding.Codec (Name vs. String method name). We only support // setting content subtype from encoding.Codec to avoid a behavior // change with the deprecated version. - if ec, ok := c.codec.(encoding.Codec); ok { + if ec, ok := c.codec.(encoding.CodecV2); ok { c.contentSubtype = strings.ToLower(ec.Name()) } } @@ -950,12 +1037,12 @@ func setCallInfoCodec(c *callInfo) error { if c.contentSubtype == "" { // No codec specified in CallOptions; use proto by default. - c.codec = encoding.GetCodec(proto.Name) + c.codec = getCodec(proto.Name) return nil } // c.contentSubtype is already lowercased in CallContentSubtype - c.codec = encoding.GetCodec(c.contentSubtype) + c.codec = getCodec(c.contentSubtype) if c.codec == nil { return status.Errorf(codes.Internal, "no codec registered for content-subtype %s", c.contentSubtype) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/server.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/server.go index 89f8e4792bf..d1e1415a40f 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/server.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/server.go @@ -45,6 +45,7 @@ import ( "google.golang.org/grpc/internal/grpcutil" "google.golang.org/grpc/internal/transport" "google.golang.org/grpc/keepalive" + "google.golang.org/grpc/mem" "google.golang.org/grpc/metadata" "google.golang.org/grpc/peer" "google.golang.org/grpc/stats" @@ -80,7 +81,7 @@ func init() { } internal.BinaryLogger = binaryLogger internal.JoinServerOptions = newJoinServerOption - internal.RecvBufferPool = recvBufferPool + internal.BufferPool = bufferPool } var statusOK = status.New(codes.OK, "") @@ -170,7 +171,7 @@ type serverOptions struct { maxHeaderListSize *uint32 headerTableSize *uint32 numServerWorkers uint32 - recvBufferPool SharedBufferPool + bufferPool mem.BufferPool waitForHandlers bool } @@ -181,7 +182,7 @@ var defaultServerOptions = serverOptions{ connectionTimeout: 120 * time.Second, writeBufferSize: defaultWriteBufSize, readBufferSize: defaultReadBufSize, - recvBufferPool: nopBufferPool{}, + bufferPool: mem.DefaultBufferPool(), } var globalServerOptions []ServerOption @@ -313,7 +314,7 @@ func KeepaliveEnforcementPolicy(kep keepalive.EnforcementPolicy) ServerOption { // Will be supported throughout 1.x. func CustomCodec(codec Codec) ServerOption { return newFuncServerOption(func(o *serverOptions) { - o.codec = codec + o.codec = newCodecV0Bridge(codec) }) } @@ -342,7 +343,22 @@ func CustomCodec(codec Codec) ServerOption { // later release. func ForceServerCodec(codec encoding.Codec) ServerOption { return newFuncServerOption(func(o *serverOptions) { - o.codec = codec + o.codec = newCodecV1Bridge(codec) + }) +} + +// ForceServerCodecV2 is the equivalent of ForceServerCodec, but for the new +// CodecV2 interface. +// +// Will be supported throughout 1.x. +// +// # Experimental +// +// Notice: This API is EXPERIMENTAL and may be changed or removed in a +// later release. +func ForceServerCodecV2(codecV2 encoding.CodecV2) ServerOption { + return newFuncServerOption(func(o *serverOptions) { + o.codec = codecV2 }) } @@ -592,26 +608,9 @@ func WaitForHandlers(w bool) ServerOption { }) } -// RecvBufferPool returns a ServerOption that configures the server -// to use the provided shared buffer pool for parsing incoming messages. Depending -// on the application's workload, this could result in reduced memory allocation. -// -// If you are unsure about how to implement a memory pool but want to utilize one, -// begin with grpc.NewSharedBufferPool. -// -// Note: The shared buffer pool feature will not be active if any of the following -// options are used: StatsHandler, EnableTracing, or binary logging. In such -// cases, the shared buffer pool will be ignored. -// -// Deprecated: use experimental.WithRecvBufferPool instead. Will be deleted in -// v1.60.0 or later. -func RecvBufferPool(bufferPool SharedBufferPool) ServerOption { - return recvBufferPool(bufferPool) -} - -func recvBufferPool(bufferPool SharedBufferPool) ServerOption { +func bufferPool(bufferPool mem.BufferPool) ServerOption { return newFuncServerOption(func(o *serverOptions) { - o.recvBufferPool = bufferPool + o.bufferPool = bufferPool }) } @@ -622,7 +621,7 @@ func recvBufferPool(bufferPool SharedBufferPool) ServerOption { // workload (assuming a QPS of a few thousand requests/sec). const serverWorkerResetThreshold = 1 << 16 -// serverWorkers blocks on a *transport.Stream channel forever and waits for +// serverWorker blocks on a *transport.Stream channel forever and waits for // data to be fed by serveStreams. This allows multiple requests to be // processed by the same goroutine, removing the need for expensive stack // re-allocations (see the runtime.morestack problem [1]). @@ -980,6 +979,7 @@ func (s *Server) newHTTP2Transport(c net.Conn) transport.ServerTransport { ChannelzParent: s.channelz, MaxHeaderListSize: s.opts.maxHeaderListSize, HeaderTableSize: s.opts.headerTableSize, + BufferPool: s.opts.bufferPool, } st, err := transport.NewServerTransport(c, config) if err != nil { @@ -1072,7 +1072,7 @@ var _ http.Handler = (*Server)(nil) // Notice: This API is EXPERIMENTAL and may be changed or removed in a // later release. func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) { - st, err := transport.NewServerHandlerTransport(w, r, s.opts.statsHandlers) + st, err := transport.NewServerHandlerTransport(w, r, s.opts.statsHandlers, s.opts.bufferPool) if err != nil { // Errors returned from transport.NewServerHandlerTransport have // already been written to w. @@ -1142,20 +1142,35 @@ func (s *Server) sendResponse(ctx context.Context, t transport.ServerTransport, channelz.Error(logger, s.channelz, "grpc: server failed to encode response: ", err) return err } - compData, err := compress(data, cp, comp) + + compData, pf, err := compress(data, cp, comp, s.opts.bufferPool) if err != nil { + data.Free() channelz.Error(logger, s.channelz, "grpc: server failed to compress response: ", err) return err } - hdr, payload := msgHeader(data, compData) + + hdr, payload := msgHeader(data, compData, pf) + + defer func() { + compData.Free() + data.Free() + // payload does not need to be freed here, it is either data or compData, both of + // which are already freed. + }() + + dataLen := data.Len() + payloadLen := payload.Len() // TODO(dfawley): should we be checking len(data) instead? - if len(payload) > s.opts.maxSendMessageSize { - return status.Errorf(codes.ResourceExhausted, "grpc: trying to send message larger than max (%d vs. %d)", len(payload), s.opts.maxSendMessageSize) + if payloadLen > s.opts.maxSendMessageSize { + return status.Errorf(codes.ResourceExhausted, "grpc: trying to send message larger than max (%d vs. %d)", payloadLen, s.opts.maxSendMessageSize) } err = t.Write(stream, hdr, payload, opts) if err == nil { - for _, sh := range s.opts.statsHandlers { - sh.HandleRPC(ctx, outPayload(false, msg, data, payload, time.Now())) + if len(s.opts.statsHandlers) != 0 { + for _, sh := range s.opts.statsHandlers { + sh.HandleRPC(ctx, outPayload(false, msg, dataLen, payloadLen, time.Now())) + } } } return err @@ -1334,37 +1349,37 @@ func (s *Server) processUnaryRPC(ctx context.Context, t transport.ServerTranspor var payInfo *payloadInfo if len(shs) != 0 || len(binlogs) != 0 { payInfo = &payloadInfo{} + defer payInfo.free() } - d, cancel, err := recvAndDecompress(&parser{r: stream, recvBufferPool: s.opts.recvBufferPool}, stream, dc, s.opts.maxReceiveMessageSize, payInfo, decomp) + d, err := recvAndDecompress(&parser{r: stream, bufferPool: s.opts.bufferPool}, stream, dc, s.opts.maxReceiveMessageSize, payInfo, decomp, true) if err != nil { if e := t.WriteStatus(stream, status.Convert(err)); e != nil { channelz.Warningf(logger, s.channelz, "grpc: Server.processUnaryRPC failed to write status: %v", e) } return err } + defer d.Free() if channelz.IsOn() { t.IncrMsgRecv() } df := func(v any) error { - defer cancel() - if err := s.getCodec(stream.ContentSubtype()).Unmarshal(d, v); err != nil { return status.Errorf(codes.Internal, "grpc: error unmarshalling request: %v", err) } + for _, sh := range shs { sh.HandleRPC(ctx, &stats.InPayload{ RecvTime: time.Now(), Payload: v, - Length: len(d), + Length: d.Len(), WireLength: payInfo.compressedLength + headerLen, CompressedLength: payInfo.compressedLength, - Data: d, }) } if len(binlogs) != 0 { cm := &binarylog.ClientMessage{ - Message: d, + Message: d.Materialize(), } for _, binlog := range binlogs { binlog.Log(ctx, cm) @@ -1548,7 +1563,7 @@ func (s *Server) processStreamingRPC(ctx context.Context, t transport.ServerTran ctx: ctx, t: t, s: stream, - p: &parser{r: stream, recvBufferPool: s.opts.recvBufferPool}, + p: &parser{r: stream, bufferPool: s.opts.bufferPool}, codec: s.getCodec(stream.ContentSubtype()), maxReceiveMessageSize: s.opts.maxReceiveMessageSize, maxSendMessageSize: s.opts.maxSendMessageSize, @@ -1963,12 +1978,12 @@ func (s *Server) getCodec(contentSubtype string) baseCodec { return s.opts.codec } if contentSubtype == "" { - return encoding.GetCodec(proto.Name) + return getCodec(proto.Name) } - codec := encoding.GetCodec(contentSubtype) + codec := getCodec(contentSubtype) if codec == nil { logger.Warningf("Unsupported codec %q. Defaulting to %q for now. This will start to fail in future releases.", contentSubtype, proto.Name) - return encoding.GetCodec(proto.Name) + return getCodec(proto.Name) } return codec } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/shared_buffer_pool.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/shared_buffer_pool.go deleted file mode 100644 index 48a64cfe8e2..00000000000 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/shared_buffer_pool.go +++ /dev/null @@ -1,154 +0,0 @@ -/* - * - * Copyright 2023 gRPC authors. - * - * 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 grpc - -import "sync" - -// SharedBufferPool is a pool of buffers that can be shared, resulting in -// decreased memory allocation. Currently, in gRPC-go, it is only utilized -// for parsing incoming messages. -// -// # Experimental -// -// Notice: This API is EXPERIMENTAL and may be changed or removed in a -// later release. -type SharedBufferPool interface { - // Get returns a buffer with specified length from the pool. - // - // The returned byte slice may be not zero initialized. - Get(length int) []byte - - // Put returns a buffer to the pool. - Put(*[]byte) -} - -// NewSharedBufferPool creates a simple SharedBufferPool with buckets -// of different sizes to optimize memory usage. This prevents the pool from -// wasting large amounts of memory, even when handling messages of varying sizes. -// -// # Experimental -// -// Notice: This API is EXPERIMENTAL and may be changed or removed in a -// later release. -func NewSharedBufferPool() SharedBufferPool { - return &simpleSharedBufferPool{ - pools: [poolArraySize]simpleSharedBufferChildPool{ - newBytesPool(level0PoolMaxSize), - newBytesPool(level1PoolMaxSize), - newBytesPool(level2PoolMaxSize), - newBytesPool(level3PoolMaxSize), - newBytesPool(level4PoolMaxSize), - newBytesPool(0), - }, - } -} - -// simpleSharedBufferPool is a simple implementation of SharedBufferPool. -type simpleSharedBufferPool struct { - pools [poolArraySize]simpleSharedBufferChildPool -} - -func (p *simpleSharedBufferPool) Get(size int) []byte { - return p.pools[p.poolIdx(size)].Get(size) -} - -func (p *simpleSharedBufferPool) Put(bs *[]byte) { - p.pools[p.poolIdx(cap(*bs))].Put(bs) -} - -func (p *simpleSharedBufferPool) poolIdx(size int) int { - switch { - case size <= level0PoolMaxSize: - return level0PoolIdx - case size <= level1PoolMaxSize: - return level1PoolIdx - case size <= level2PoolMaxSize: - return level2PoolIdx - case size <= level3PoolMaxSize: - return level3PoolIdx - case size <= level4PoolMaxSize: - return level4PoolIdx - default: - return levelMaxPoolIdx - } -} - -const ( - level0PoolMaxSize = 16 // 16 B - level1PoolMaxSize = level0PoolMaxSize * 16 // 256 B - level2PoolMaxSize = level1PoolMaxSize * 16 // 4 KB - level3PoolMaxSize = level2PoolMaxSize * 16 // 64 KB - level4PoolMaxSize = level3PoolMaxSize * 16 // 1 MB -) - -const ( - level0PoolIdx = iota - level1PoolIdx - level2PoolIdx - level3PoolIdx - level4PoolIdx - levelMaxPoolIdx - poolArraySize -) - -type simpleSharedBufferChildPool interface { - Get(size int) []byte - Put(any) -} - -type bufferPool struct { - sync.Pool - - defaultSize int -} - -func (p *bufferPool) Get(size int) []byte { - bs := p.Pool.Get().(*[]byte) - - if cap(*bs) < size { - p.Pool.Put(bs) - - return make([]byte, size) - } - - return (*bs)[:size] -} - -func newBytesPool(size int) simpleSharedBufferChildPool { - return &bufferPool{ - Pool: sync.Pool{ - New: func() any { - bs := make([]byte, size) - return &bs - }, - }, - defaultSize: size, - } -} - -// nopBufferPool is a buffer pool just makes new buffer without pooling. -type nopBufferPool struct { -} - -func (nopBufferPool) Get(length int) []byte { - return make([]byte, length) -} - -func (nopBufferPool) Put(*[]byte) { -} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stats/stats.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stats/stats.go index fdb0bd65182..71195c4943d 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stats/stats.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stats/stats.go @@ -77,9 +77,6 @@ type InPayload struct { // the call to HandleRPC which provides the InPayload returns and must be // copied if needed later. Payload any - // Data is the serialized message payload. - // Deprecated: Data will be removed in the next release. - Data []byte // Length is the size of the uncompressed payload data. Does not include any // framing (gRPC or HTTP/2). @@ -150,9 +147,6 @@ type OutPayload struct { // the call to HandleRPC which provides the OutPayload returns and must be // copied if needed later. Payload any - // Data is the serialized message payload. - // Deprecated: Data will be removed in the next release. - Data []byte // Length is the size of the uncompressed payload data. Does not include any // framing (gRPC or HTTP/2). Length int diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream.go index 8051ef5b514..bb2b2a216ce 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream.go @@ -41,6 +41,7 @@ import ( "google.golang.org/grpc/internal/serviceconfig" istatus "google.golang.org/grpc/internal/status" "google.golang.org/grpc/internal/transport" + "google.golang.org/grpc/mem" "google.golang.org/grpc/metadata" "google.golang.org/grpc/peer" "google.golang.org/grpc/stats" @@ -359,7 +360,7 @@ func newClientStreamWithParams(ctx context.Context, desc *StreamDesc, cc *Client cs.attempt = a return nil } - if err := cs.withRetry(op, func() { cs.bufferForRetryLocked(0, op) }); err != nil { + if err := cs.withRetry(op, func() { cs.bufferForRetryLocked(0, op, nil) }); err != nil { return nil, err } @@ -517,7 +518,7 @@ func (a *csAttempt) newStream() error { } a.s = s a.ctx = s.Context() - a.p = &parser{r: s, recvBufferPool: a.cs.cc.dopts.recvBufferPool} + a.p = &parser{r: s, bufferPool: a.cs.cc.dopts.copts.BufferPool} return nil } @@ -566,10 +567,15 @@ type clientStream struct { // place where we need to check if the attempt is nil. attempt *csAttempt // TODO(hedging): hedging will have multiple attempts simultaneously. - committed bool // active attempt committed for retry? - onCommit func() - buffer []func(a *csAttempt) error // operations to replay on retry - bufferSize int // current size of buffer + committed bool // active attempt committed for retry? + onCommit func() + replayBuffer []replayOp // operations to replay on retry + replayBufferSize int // current size of replayBuffer +} + +type replayOp struct { + op func(a *csAttempt) error + cleanup func() } // csAttempt implements a single transport stream attempt within a @@ -607,7 +613,12 @@ func (cs *clientStream) commitAttemptLocked() { cs.onCommit() } cs.committed = true - cs.buffer = nil + for _, op := range cs.replayBuffer { + if op.cleanup != nil { + op.cleanup() + } + } + cs.replayBuffer = nil } func (cs *clientStream) commitAttempt() { @@ -732,7 +743,7 @@ func (cs *clientStream) retryLocked(attempt *csAttempt, lastErr error) error { // the stream is canceled. return err } - // Note that the first op in the replay buffer always sets cs.attempt + // Note that the first op in replayBuffer always sets cs.attempt // if it is able to pick a transport and create a stream. if lastErr = cs.replayBufferLocked(attempt); lastErr == nil { return nil @@ -761,7 +772,7 @@ func (cs *clientStream) withRetry(op func(a *csAttempt) error, onSuccess func()) // already be status errors. return toRPCErr(op(cs.attempt)) } - if len(cs.buffer) == 0 { + if len(cs.replayBuffer) == 0 { // For the first op, which controls creation of the stream and // assigns cs.attempt, we need to create a new attempt inline // before executing the first op. On subsequent ops, the attempt @@ -851,25 +862,26 @@ func (cs *clientStream) Trailer() metadata.MD { } func (cs *clientStream) replayBufferLocked(attempt *csAttempt) error { - for _, f := range cs.buffer { - if err := f(attempt); err != nil { + for _, f := range cs.replayBuffer { + if err := f.op(attempt); err != nil { return err } } return nil } -func (cs *clientStream) bufferForRetryLocked(sz int, op func(a *csAttempt) error) { +func (cs *clientStream) bufferForRetryLocked(sz int, op func(a *csAttempt) error, cleanup func()) { // Note: we still will buffer if retry is disabled (for transparent retries). if cs.committed { return } - cs.bufferSize += sz - if cs.bufferSize > cs.callInfo.maxRetryRPCBufferSize { + cs.replayBufferSize += sz + if cs.replayBufferSize > cs.callInfo.maxRetryRPCBufferSize { cs.commitAttemptLocked() + cleanup() return } - cs.buffer = append(cs.buffer, op) + cs.replayBuffer = append(cs.replayBuffer, replayOp{op: op, cleanup: cleanup}) } func (cs *clientStream) SendMsg(m any) (err error) { @@ -891,23 +903,50 @@ func (cs *clientStream) SendMsg(m any) (err error) { } // load hdr, payload, data - hdr, payload, data, err := prepareMsg(m, cs.codec, cs.cp, cs.comp) + hdr, data, payload, pf, err := prepareMsg(m, cs.codec, cs.cp, cs.comp, cs.cc.dopts.copts.BufferPool) if err != nil { return err } + defer func() { + data.Free() + // only free payload if compression was made, and therefore it is a different set + // of buffers from data. + if pf.isCompressed() { + payload.Free() + } + }() + + dataLen := data.Len() + payloadLen := payload.Len() // TODO(dfawley): should we be checking len(data) instead? - if len(payload) > *cs.callInfo.maxSendMessageSize { - return status.Errorf(codes.ResourceExhausted, "trying to send message larger than max (%d vs. %d)", len(payload), *cs.callInfo.maxSendMessageSize) + if payloadLen > *cs.callInfo.maxSendMessageSize { + return status.Errorf(codes.ResourceExhausted, "trying to send message larger than max (%d vs. %d)", payloadLen, *cs.callInfo.maxSendMessageSize) } + + // always take an extra ref in case data == payload (i.e. when the data isn't + // compressed). The original ref will always be freed by the deferred free above. + payload.Ref() op := func(a *csAttempt) error { - return a.sendMsg(m, hdr, payload, data) + return a.sendMsg(m, hdr, payload, dataLen, payloadLen) + } + + // onSuccess is invoked when the op is captured for a subsequent retry. If the + // stream was established by a previous message and therefore retries are + // disabled, onSuccess will not be invoked, and payloadRef can be freed + // immediately. + onSuccessCalled := false + err = cs.withRetry(op, func() { + cs.bufferForRetryLocked(len(hdr)+payloadLen, op, payload.Free) + onSuccessCalled = true + }) + if !onSuccessCalled { + payload.Free() } - err = cs.withRetry(op, func() { cs.bufferForRetryLocked(len(hdr)+len(payload), op) }) if len(cs.binlogs) != 0 && err == nil { cm := &binarylog.ClientMessage{ OnClientSide: true, - Message: data, + Message: data.Materialize(), } for _, binlog := range cs.binlogs { binlog.Log(cs.ctx, cm) @@ -924,6 +963,7 @@ func (cs *clientStream) RecvMsg(m any) error { var recvInfo *payloadInfo if len(cs.binlogs) != 0 { recvInfo = &payloadInfo{} + defer recvInfo.free() } err := cs.withRetry(func(a *csAttempt) error { return a.recvMsg(m, recvInfo) @@ -931,7 +971,7 @@ func (cs *clientStream) RecvMsg(m any) error { if len(cs.binlogs) != 0 && err == nil { sm := &binarylog.ServerMessage{ OnClientSide: true, - Message: recvInfo.uncompressedBytes, + Message: recvInfo.uncompressedBytes.Materialize(), } for _, binlog := range cs.binlogs { binlog.Log(cs.ctx, sm) @@ -958,7 +998,7 @@ func (cs *clientStream) CloseSend() error { // RecvMsg. This also matches historical behavior. return nil } - cs.withRetry(op, func() { cs.bufferForRetryLocked(0, op) }) + cs.withRetry(op, func() { cs.bufferForRetryLocked(0, op, nil) }) if len(cs.binlogs) != 0 { chc := &binarylog.ClientHalfClose{ OnClientSide: true, @@ -1034,7 +1074,7 @@ func (cs *clientStream) finish(err error) { cs.cancel() } -func (a *csAttempt) sendMsg(m any, hdr, payld, data []byte) error { +func (a *csAttempt) sendMsg(m any, hdr []byte, payld mem.BufferSlice, dataLength, payloadLength int) error { cs := a.cs if a.trInfo != nil { a.mu.Lock() @@ -1052,8 +1092,10 @@ func (a *csAttempt) sendMsg(m any, hdr, payld, data []byte) error { } return io.EOF } - for _, sh := range a.statsHandlers { - sh.HandleRPC(a.ctx, outPayload(true, m, data, payld, time.Now())) + if len(a.statsHandlers) != 0 { + for _, sh := range a.statsHandlers { + sh.HandleRPC(a.ctx, outPayload(true, m, dataLength, payloadLength, time.Now())) + } } if channelz.IsOn() { a.t.IncrMsgSent() @@ -1065,6 +1107,7 @@ func (a *csAttempt) recvMsg(m any, payInfo *payloadInfo) (err error) { cs := a.cs if len(a.statsHandlers) != 0 && payInfo == nil { payInfo = &payloadInfo{} + defer payInfo.free() } if !a.decompSet { @@ -1083,8 +1126,7 @@ func (a *csAttempt) recvMsg(m any, payInfo *payloadInfo) (err error) { // Only initialize this state once per stream. a.decompSet = true } - err = recv(a.p, cs.codec, a.s, a.dc, m, *cs.callInfo.maxReceiveMessageSize, payInfo, a.decomp) - if err != nil { + if err := recv(a.p, cs.codec, a.s, a.dc, m, *cs.callInfo.maxReceiveMessageSize, payInfo, a.decomp, false); err != nil { if err == io.EOF { if statusErr := a.s.Status().Err(); statusErr != nil { return statusErr @@ -1103,14 +1145,12 @@ func (a *csAttempt) recvMsg(m any, payInfo *payloadInfo) (err error) { } for _, sh := range a.statsHandlers { sh.HandleRPC(a.ctx, &stats.InPayload{ - Client: true, - RecvTime: time.Now(), - Payload: m, - // TODO truncate large payload. - Data: payInfo.uncompressedBytes, + Client: true, + RecvTime: time.Now(), + Payload: m, WireLength: payInfo.compressedLength + headerLen, CompressedLength: payInfo.compressedLength, - Length: len(payInfo.uncompressedBytes), + Length: payInfo.uncompressedBytes.Len(), }) } if channelz.IsOn() { @@ -1122,14 +1162,12 @@ func (a *csAttempt) recvMsg(m any, payInfo *payloadInfo) (err error) { } // Special handling for non-server-stream rpcs. // This recv expects EOF or errors, so we don't collect inPayload. - err = recv(a.p, cs.codec, a.s, a.dc, m, *cs.callInfo.maxReceiveMessageSize, nil, a.decomp) - if err == nil { - return toRPCErr(errors.New("grpc: client streaming protocol violation: get , want ")) - } - if err == io.EOF { + if err := recv(a.p, cs.codec, a.s, a.dc, m, *cs.callInfo.maxReceiveMessageSize, nil, a.decomp, false); err == io.EOF { return a.s.Status().Err() // non-server streaming Recv returns nil on success + } else if err != nil { + return toRPCErr(err) } - return toRPCErr(err) + return toRPCErr(errors.New("grpc: client streaming protocol violation: get , want ")) } func (a *csAttempt) finish(err error) { @@ -1185,12 +1223,12 @@ func (a *csAttempt) finish(err error) { a.mu.Unlock() } -// newClientStream creates a ClientStream with the specified transport, on the +// newNonRetryClientStream creates a ClientStream with the specified transport, on the // given addrConn. // // It's expected that the given transport is either the same one in addrConn, or // is already closed. To avoid race, transport is specified separately, instead -// of using ac.transpot. +// of using ac.transport. // // Main difference between this and ClientConn.NewStream: // - no retry @@ -1276,7 +1314,7 @@ func newNonRetryClientStream(ctx context.Context, desc *StreamDesc, method strin return nil, err } as.s = s - as.p = &parser{r: s, recvBufferPool: ac.dopts.recvBufferPool} + as.p = &parser{r: s, bufferPool: ac.dopts.copts.BufferPool} ac.incrCallsStarted() if desc != unaryStreamDesc { // Listen on stream context to cleanup when the stream context is @@ -1373,17 +1411,26 @@ func (as *addrConnStream) SendMsg(m any) (err error) { } // load hdr, payload, data - hdr, payld, _, err := prepareMsg(m, as.codec, as.cp, as.comp) + hdr, data, payload, pf, err := prepareMsg(m, as.codec, as.cp, as.comp, as.ac.dopts.copts.BufferPool) if err != nil { return err } + defer func() { + data.Free() + // only free payload if compression was made, and therefore it is a different set + // of buffers from data. + if pf.isCompressed() { + payload.Free() + } + }() + // TODO(dfawley): should we be checking len(data) instead? - if len(payld) > *as.callInfo.maxSendMessageSize { - return status.Errorf(codes.ResourceExhausted, "trying to send message larger than max (%d vs. %d)", len(payld), *as.callInfo.maxSendMessageSize) + if payload.Len() > *as.callInfo.maxSendMessageSize { + return status.Errorf(codes.ResourceExhausted, "trying to send message larger than max (%d vs. %d)", payload.Len(), *as.callInfo.maxSendMessageSize) } - if err := as.t.Write(as.s, hdr, payld, &transport.Options{Last: !as.desc.ClientStreams}); err != nil { + if err := as.t.Write(as.s, hdr, payload, &transport.Options{Last: !as.desc.ClientStreams}); err != nil { if !as.desc.ClientStreams { // For non-client-streaming RPCs, we return nil instead of EOF on error // because the generated code requires it. finish is not called; RecvMsg() @@ -1423,8 +1470,7 @@ func (as *addrConnStream) RecvMsg(m any) (err error) { // Only initialize this state once per stream. as.decompSet = true } - err = recv(as.p, as.codec, as.s, as.dc, m, *as.callInfo.maxReceiveMessageSize, nil, as.decomp) - if err != nil { + if err := recv(as.p, as.codec, as.s, as.dc, m, *as.callInfo.maxReceiveMessageSize, nil, as.decomp, false); err != nil { if err == io.EOF { if statusErr := as.s.Status().Err(); statusErr != nil { return statusErr @@ -1444,14 +1490,12 @@ func (as *addrConnStream) RecvMsg(m any) (err error) { // Special handling for non-server-stream rpcs. // This recv expects EOF or errors, so we don't collect inPayload. - err = recv(as.p, as.codec, as.s, as.dc, m, *as.callInfo.maxReceiveMessageSize, nil, as.decomp) - if err == nil { - return toRPCErr(errors.New("grpc: client streaming protocol violation: get , want ")) - } - if err == io.EOF { + if err := recv(as.p, as.codec, as.s, as.dc, m, *as.callInfo.maxReceiveMessageSize, nil, as.decomp, false); err == io.EOF { return as.s.Status().Err() // non-server streaming Recv returns nil on success + } else if err != nil { + return toRPCErr(err) } - return toRPCErr(err) + return toRPCErr(errors.New("grpc: client streaming protocol violation: get , want ")) } func (as *addrConnStream) finish(err error) { @@ -1645,18 +1689,31 @@ func (ss *serverStream) SendMsg(m any) (err error) { } // load hdr, payload, data - hdr, payload, data, err := prepareMsg(m, ss.codec, ss.cp, ss.comp) + hdr, data, payload, pf, err := prepareMsg(m, ss.codec, ss.cp, ss.comp, ss.p.bufferPool) if err != nil { return err } + defer func() { + data.Free() + // only free payload if compression was made, and therefore it is a different set + // of buffers from data. + if pf.isCompressed() { + payload.Free() + } + }() + + dataLen := data.Len() + payloadLen := payload.Len() + // TODO(dfawley): should we be checking len(data) instead? - if len(payload) > ss.maxSendMessageSize { - return status.Errorf(codes.ResourceExhausted, "trying to send message larger than max (%d vs. %d)", len(payload), ss.maxSendMessageSize) + if payloadLen > ss.maxSendMessageSize { + return status.Errorf(codes.ResourceExhausted, "trying to send message larger than max (%d vs. %d)", payloadLen, ss.maxSendMessageSize) } if err := ss.t.Write(ss.s, hdr, payload, &transport.Options{Last: false}); err != nil { return toRPCErr(err) } + if len(ss.binlogs) != 0 { if !ss.serverHeaderBinlogged { h, _ := ss.s.Header() @@ -1669,7 +1726,7 @@ func (ss *serverStream) SendMsg(m any) (err error) { } } sm := &binarylog.ServerMessage{ - Message: data, + Message: data.Materialize(), } for _, binlog := range ss.binlogs { binlog.Log(ss.ctx, sm) @@ -1677,7 +1734,7 @@ func (ss *serverStream) SendMsg(m any) (err error) { } if len(ss.statsHandler) != 0 { for _, sh := range ss.statsHandler { - sh.HandleRPC(ss.s.Context(), outPayload(false, m, data, payload, time.Now())) + sh.HandleRPC(ss.s.Context(), outPayload(false, m, dataLen, payloadLen, time.Now())) } } return nil @@ -1714,8 +1771,9 @@ func (ss *serverStream) RecvMsg(m any) (err error) { var payInfo *payloadInfo if len(ss.statsHandler) != 0 || len(ss.binlogs) != 0 { payInfo = &payloadInfo{} + defer payInfo.free() } - if err := recv(ss.p, ss.codec, ss.s, ss.dc, m, ss.maxReceiveMessageSize, payInfo, ss.decomp); err != nil { + if err := recv(ss.p, ss.codec, ss.s, ss.dc, m, ss.maxReceiveMessageSize, payInfo, ss.decomp, true); err != nil { if err == io.EOF { if len(ss.binlogs) != 0 { chc := &binarylog.ClientHalfClose{} @@ -1733,11 +1791,9 @@ func (ss *serverStream) RecvMsg(m any) (err error) { if len(ss.statsHandler) != 0 { for _, sh := range ss.statsHandler { sh.HandleRPC(ss.s.Context(), &stats.InPayload{ - RecvTime: time.Now(), - Payload: m, - // TODO truncate large payload. - Data: payInfo.uncompressedBytes, - Length: len(payInfo.uncompressedBytes), + RecvTime: time.Now(), + Payload: m, + Length: payInfo.uncompressedBytes.Len(), WireLength: payInfo.compressedLength + headerLen, CompressedLength: payInfo.compressedLength, }) @@ -1745,7 +1801,7 @@ func (ss *serverStream) RecvMsg(m any) (err error) { } if len(ss.binlogs) != 0 { cm := &binarylog.ClientMessage{ - Message: payInfo.uncompressedBytes, + Message: payInfo.uncompressedBytes.Materialize(), } for _, binlog := range ss.binlogs { binlog.Log(ss.ctx, cm) @@ -1760,23 +1816,26 @@ func MethodFromServerStream(stream ServerStream) (string, bool) { return Method(stream.Context()) } -// prepareMsg returns the hdr, payload and data -// using the compressors passed or using the -// passed preparedmsg -func prepareMsg(m any, codec baseCodec, cp Compressor, comp encoding.Compressor) (hdr, payload, data []byte, err error) { +// prepareMsg returns the hdr, payload and data using the compressors passed or +// using the passed preparedmsg. The returned boolean indicates whether +// compression was made and therefore whether the payload needs to be freed in +// addition to the returned data. Freeing the payload if the returned boolean is +// false can lead to undefined behavior. +func prepareMsg(m any, codec baseCodec, cp Compressor, comp encoding.Compressor, pool mem.BufferPool) (hdr []byte, data, payload mem.BufferSlice, pf payloadFormat, err error) { if preparedMsg, ok := m.(*PreparedMsg); ok { - return preparedMsg.hdr, preparedMsg.payload, preparedMsg.encodedData, nil + return preparedMsg.hdr, preparedMsg.encodedData, preparedMsg.payload, preparedMsg.pf, nil } // The input interface is not a prepared msg. // Marshal and Compress the data at this point data, err = encode(codec, m) if err != nil { - return nil, nil, nil, err + return nil, nil, nil, 0, err } - compData, err := compress(data, cp, comp) + compData, pf, err := compress(data, cp, comp, pool) if err != nil { - return nil, nil, nil, err + data.Free() + return nil, nil, nil, 0, err } - hdr, payload = msgHeader(data, compData) - return hdr, payload, data, nil + hdr, payload = msgHeader(data, compData, pf) + return hdr, data, payload, pf, nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream_interfaces.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream_interfaces.go index 8b813529c0c..0037fee0bd7 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream_interfaces.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/stream_interfaces.go @@ -22,15 +22,35 @@ package grpc // request, many responses) RPC. It is generic over the type of the response // message. It is used in generated code. type ServerStreamingClient[Res any] interface { + // Recv receives the next response message from the server. The client may + // repeatedly call Recv to read messages from the response stream. If + // io.EOF is returned, the stream has terminated with an OK status. Any + // other error is compatible with the status package and indicates the + // RPC's status code and message. Recv() (*Res, error) + + // ClientStream is embedded to provide Context, Header, and Trailer + // functionality. No other methods in the ClientStream should be called + // directly. ClientStream } // ServerStreamingServer represents the server side of a server-streaming (one // request, many responses) RPC. It is generic over the type of the response // message. It is used in generated code. +// +// To terminate the response stream, return from the handler method and return +// an error from the status package, or use nil to indicate an OK status code. type ServerStreamingServer[Res any] interface { + // Send sends a response message to the client. The server handler may + // call Send multiple times to send multiple messages to the client. An + // error is returned if the stream was terminated unexpectedly, and the + // handler method should return, as the stream is no longer usable. Send(*Res) error + + // ServerStream is embedded to provide Context, SetHeader, SendHeader, and + // SetTrailer functionality. No other methods in the ServerStream should + // be called directly. ServerStream } @@ -39,8 +59,22 @@ type ServerStreamingServer[Res any] interface { // message stream and the type of the unary response message. It is used in // generated code. type ClientStreamingClient[Req any, Res any] interface { + // Send sends a request message to the server. The client may call Send + // multiple times to send multiple messages to the server. On error, Send + // aborts the stream. If the error was generated by the client, the status + // is returned directly. Otherwise, io.EOF is returned, and the status of + // the stream may be discovered using CloseAndRecv(). Send(*Req) error + + // CloseAndRecv closes the request stream and waits for the server's + // response. This method must be called once and only once after sending + // all request messages. Any error returned is implemented by the status + // package. CloseAndRecv() (*Res, error) + + // ClientStream is embedded to provide Context, Header, and Trailer + // functionality. No other methods in the ClientStream should be called + // directly. ClientStream } @@ -48,9 +82,28 @@ type ClientStreamingClient[Req any, Res any] interface { // requests, one response) RPC. It is generic over both the type of the request // message stream and the type of the unary response message. It is used in // generated code. +// +// To terminate the RPC, call SendAndClose and return nil from the method +// handler or do not call SendAndClose and return an error from the status +// package. type ClientStreamingServer[Req any, Res any] interface { + // Recv receives the next request message from the client. The server may + // repeatedly call Recv to read messages from the request stream. If + // io.EOF is returned, it indicates the client called CloseAndRecv on its + // ClientStreamingClient. Any other error indicates the stream was + // terminated unexpectedly, and the handler method should return, as the + // stream is no longer usable. Recv() (*Req, error) + + // SendAndClose sends a single response message to the client and closes + // the stream. This method must be called once and only once after all + // request messages have been processed. Recv should not be called after + // calling SendAndClose. SendAndClose(*Res) error + + // ServerStream is embedded to provide Context, SetHeader, SendHeader, and + // SetTrailer functionality. No other methods in the ServerStream should + // be called directly. ServerStream } @@ -59,8 +112,23 @@ type ClientStreamingServer[Req any, Res any] interface { // request message stream and the type of the response message stream. It is // used in generated code. type BidiStreamingClient[Req any, Res any] interface { + // Send sends a request message to the server. The client may call Send + // multiple times to send multiple messages to the server. On error, Send + // aborts the stream. If the error was generated by the client, the status + // is returned directly. Otherwise, io.EOF is returned, and the status of + // the stream may be discovered using Recv(). Send(*Req) error + + // Recv receives the next response message from the server. The client may + // repeatedly call Recv to read messages from the response stream. If + // io.EOF is returned, the stream has terminated with an OK status. Any + // other error is compatible with the status package and indicates the + // RPC's status code and message. Recv() (*Res, error) + + // ClientStream is embedded to provide Context, Header, Trailer, and + // CloseSend functionality. No other methods in the ClientStream should be + // called directly. ClientStream } @@ -68,9 +136,27 @@ type BidiStreamingClient[Req any, Res any] interface { // (many requests, many responses) RPC. It is generic over both the type of the // request message stream and the type of the response message stream. It is // used in generated code. +// +// To terminate the stream, return from the handler method and return +// an error from the status package, or use nil to indicate an OK status code. type BidiStreamingServer[Req any, Res any] interface { + // Recv receives the next request message from the client. The server may + // repeatedly call Recv to read messages from the request stream. If + // io.EOF is returned, it indicates the client called CloseSend on its + // BidiStreamingClient. Any other error indicates the stream was + // terminated unexpectedly, and the handler method should return, as the + // stream is no longer usable. Recv() (*Req, error) + + // Send sends a response message to the client. The server handler may + // call Send multiple times to send multiple messages to the client. An + // error is returned if the stream was terminated unexpectedly, and the + // handler method should return, as the stream is no longer usable. Send(*Res) error + + // ServerStream is embedded to provide Context, SetHeader, SendHeader, and + // SetTrailer functionality. No other methods in the ServerStream should + // be called directly. ServerStream } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/version.go b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/version.go index 4209a0a2dfe..35728c2d383 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/version.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/grpc/version.go @@ -19,4 +19,4 @@ package grpc // Version is the current grpc version. -const Version = "1.65.1" +const Version = "1.67.3" diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/protojson/decode.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/protojson/decode.go index 8f9e592f870..737d6876d5e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/protojson/decode.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/protojson/decode.go @@ -192,11 +192,6 @@ func (d decoder) unmarshalMessage(m protoreflect.Message, skipTypeURL bool) erro fd = fieldDescs.ByTextName(name) } } - if flags.ProtoLegacy { - if fd != nil && fd.IsWeak() && fd.Message().IsPlaceholder() { - fd = nil // reset since the weak reference is not linked in - } - } if fd == nil { // Field is unknown. diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/prototext/decode.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/prototext/decode.go index 24bc98ac422..b53805056a9 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/prototext/decode.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/encoding/prototext/decode.go @@ -185,11 +185,6 @@ func (d decoder) unmarshalMessage(m protoreflect.Message, checkDelims bool) erro } else if xtErr != nil && xtErr != protoregistry.NotFound { return d.newError(tok.Pos(), "unable to resolve [%s]: %v", tok.RawString(), xtErr) } - if flags.ProtoLegacy { - if fd != nil && fd.IsWeak() && fd.Message().IsPlaceholder() { - fd = nil // reset since the weak reference is not linked in - } - } // Handle unknown fields. if fd == nil { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/encoding/tag/tag.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/encoding/tag/tag.go index 7e87c760443..669133d04dc 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/encoding/tag/tag.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/encoding/tag/tag.go @@ -26,7 +26,7 @@ var byteType = reflect.TypeOf(byte(0)) // The type is the underlying field type (e.g., a repeated field may be // represented by []T, but the Go type passed in is just T). // A list of enum value descriptors must be provided for enum fields. -// This does not populate the Enum or Message (except for weak message). +// This does not populate the Enum or Message. // // This function is a best effort attempt; parsing errors are ignored. func Unmarshal(tag string, goType reflect.Type, evs protoreflect.EnumValueDescriptors) protoreflect.FieldDescriptor { @@ -109,9 +109,6 @@ func Unmarshal(tag string, goType reflect.Type, evs protoreflect.EnumValueDescri } case s == "packed": f.L1.EditionFeatures.IsPacked = true - case strings.HasPrefix(s, "weak="): - f.L1.IsWeak = true - f.L1.Message = filedesc.PlaceholderMessage(protoreflect.FullName(s[len("weak="):])) case strings.HasPrefix(s, "def="): // The default tag is special in that everything afterwards is the // default regardless of the presence of commas. @@ -183,9 +180,6 @@ func Marshal(fd protoreflect.FieldDescriptor, enumName string) string { // the exact same semantics from the previous generator. tag = append(tag, "json="+jsonName) } - if fd.IsWeak() { - tag = append(tag, "weak="+string(fd.Message().FullName())) - } // The previous implementation does not tag extension fields as proto3, // even when the field is defined in a proto3 file. Match that behavior // for consistency. diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc.go index 378b826faa6..688aabe434e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc.go @@ -19,7 +19,6 @@ import ( "google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/internal/strs" "google.golang.org/protobuf/reflect/protoreflect" - "google.golang.org/protobuf/reflect/protoregistry" ) // Edition is an Enum for proto2.Edition @@ -275,7 +274,6 @@ type ( Kind protoreflect.Kind StringName stringName IsProto3Optional bool // promoted from google.protobuf.FieldDescriptorProto - IsWeak bool // promoted from google.protobuf.FieldOptions IsLazy bool // promoted from google.protobuf.FieldOptions Default defaultValue ContainingOneof protoreflect.OneofDescriptor // must be consistent with Message.Oneofs.Fields @@ -369,7 +367,7 @@ func (fd *Field) IsPacked() bool { return fd.L1.EditionFeatures.IsPacked } func (fd *Field) IsExtension() bool { return false } -func (fd *Field) IsWeak() bool { return fd.L1.IsWeak } +func (fd *Field) IsWeak() bool { return false } func (fd *Field) IsLazy() bool { return fd.L1.IsLazy } func (fd *Field) IsList() bool { return fd.Cardinality() == protoreflect.Repeated && !fd.IsMap() } func (fd *Field) IsMap() bool { return fd.Message() != nil && fd.Message().IsMapEntry() } @@ -396,11 +394,6 @@ func (fd *Field) Enum() protoreflect.EnumDescriptor { return fd.L1.Enum } func (fd *Field) Message() protoreflect.MessageDescriptor { - if fd.L1.IsWeak { - if d, _ := protoregistry.GlobalFiles.FindDescriptorByName(fd.L1.Message.FullName()); d != nil { - return d.(protoreflect.MessageDescriptor) - } - } return fd.L1.Message } func (fd *Field) IsMapEntry() bool { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc_lazy.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc_lazy.go index 67a51b327c5..d4c94458bd9 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc_lazy.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filedesc/desc_lazy.go @@ -32,11 +32,6 @@ func (file *File) resolveMessages() { for j := range md.L2.Fields.List { fd := &md.L2.Fields.List[j] - // Weak fields are resolved upon actual use. - if fd.L1.IsWeak { - continue - } - // Resolve message field dependency. switch fd.L1.Kind { case protoreflect.EnumKind: @@ -150,8 +145,6 @@ func (fd *File) unmarshalFull(b []byte) { switch num { case genid.FileDescriptorProto_PublicDependency_field_number: fd.L2.Imports[v].IsPublic = true - case genid.FileDescriptorProto_WeakDependency_field_number: - fd.L2.Imports[v].IsWeak = true } case protowire.BytesType: v, m := protowire.ConsumeBytes(b) @@ -502,8 +495,6 @@ func (fd *Field) unmarshalOptions(b []byte) { switch num { case genid.FieldOptions_Packed_field_number: fd.L1.EditionFeatures.IsPacked = protowire.DecodeBool(v) - case genid.FieldOptions_Weak_field_number: - fd.L1.IsWeak = protowire.DecodeBool(v) case genid.FieldOptions_Lazy_field_number: fd.L1.IsLazy = protowire.DecodeBool(v) case FieldOptions_EnforceUTF8: diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filetype/build.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filetype/build.go index ba83fea44c3..e1b4130bd28 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filetype/build.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/filetype/build.go @@ -63,7 +63,7 @@ type Builder struct { // message declarations in "flattened ordering". // // Dependencies are Go types for enums or messages referenced by - // message fields (excluding weak fields), for parent extended messages of + // message fields, for parent extended messages of // extension fields, for enums or messages referenced by extension fields, // and for input and output messages referenced by service methods. // Dependencies must come after declarations, but the ordering of diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/flags/flags.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/flags/flags.go index 58372dd3485..a06ccabc2fa 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/flags/flags.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/flags/flags.go @@ -6,7 +6,7 @@ package flags // ProtoLegacy specifies whether to enable support for legacy functionality -// such as MessageSets, weak fields, and various other obscure behavior +// such as MessageSets, and various other obscure behavior // that is necessary to maintain backwards compatibility with proto1 or // the pre-release variants of proto2 and proto3. // diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/genid/goname.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/genid/goname.go index 693d2e9e1fe..99bb95bafd5 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/genid/goname.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/genid/goname.go @@ -11,15 +11,10 @@ const ( SizeCache_goname = "sizeCache" SizeCacheA_goname = "XXX_sizecache" - WeakFields_goname = "weakFields" - WeakFieldsA_goname = "XXX_weak" - UnknownFields_goname = "unknownFields" UnknownFieldsA_goname = "XXX_unrecognized" ExtensionFields_goname = "extensionFields" ExtensionFieldsA_goname = "XXX_InternalExtensions" ExtensionFieldsB_goname = "XXX_extensions" - - WeakFieldPrefix_goname = "XXX_weak_" ) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_field.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_field.go index 7c1f66c8c19..d14d7d93cca 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_field.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_field.go @@ -5,15 +5,12 @@ package impl import ( - "fmt" "reflect" - "sync" "google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/internal/errors" "google.golang.org/protobuf/proto" "google.golang.org/protobuf/reflect/protoreflect" - "google.golang.org/protobuf/reflect/protoregistry" "google.golang.org/protobuf/runtime/protoiface" ) @@ -121,78 +118,6 @@ func (mi *MessageInfo) initOneofFieldCoders(od protoreflect.OneofDescriptor, si } } -func makeWeakMessageFieldCoder(fd protoreflect.FieldDescriptor) pointerCoderFuncs { - var once sync.Once - var messageType protoreflect.MessageType - lazyInit := func() { - once.Do(func() { - messageName := fd.Message().FullName() - messageType, _ = protoregistry.GlobalTypes.FindMessageByName(messageName) - }) - } - - return pointerCoderFuncs{ - size: func(p pointer, f *coderFieldInfo, opts marshalOptions) int { - m, ok := p.WeakFields().get(f.num) - if !ok { - return 0 - } - lazyInit() - if messageType == nil { - panic(fmt.Sprintf("weak message %v is not linked in", fd.Message().FullName())) - } - return sizeMessage(m, f.tagsize, opts) - }, - marshal: func(b []byte, p pointer, f *coderFieldInfo, opts marshalOptions) ([]byte, error) { - m, ok := p.WeakFields().get(f.num) - if !ok { - return b, nil - } - lazyInit() - if messageType == nil { - panic(fmt.Sprintf("weak message %v is not linked in", fd.Message().FullName())) - } - return appendMessage(b, m, f.wiretag, opts) - }, - unmarshal: func(b []byte, p pointer, wtyp protowire.Type, f *coderFieldInfo, opts unmarshalOptions) (unmarshalOutput, error) { - fs := p.WeakFields() - m, ok := fs.get(f.num) - if !ok { - lazyInit() - if messageType == nil { - return unmarshalOutput{}, errUnknown - } - m = messageType.New().Interface() - fs.set(f.num, m) - } - return consumeMessage(b, m, wtyp, opts) - }, - isInit: func(p pointer, f *coderFieldInfo) error { - m, ok := p.WeakFields().get(f.num) - if !ok { - return nil - } - return proto.CheckInitialized(m) - }, - merge: func(dst, src pointer, f *coderFieldInfo, opts mergeOptions) { - sm, ok := src.WeakFields().get(f.num) - if !ok { - return - } - dm, ok := dst.WeakFields().get(f.num) - if !ok { - lazyInit() - if messageType == nil { - panic(fmt.Sprintf("weak message %v is not linked in", fd.Message().FullName())) - } - dm = messageType.New().Interface() - dst.WeakFields().set(f.num, dm) - } - opts.Merge(dm, sm) - }, - } -} - func makeMessageFieldCoder(fd protoreflect.FieldDescriptor, ft reflect.Type) pointerCoderFuncs { if mi := getMessageInfo(ft); mi != nil { funcs := pointerCoderFuncs{ diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map.go index fb35f0bae9c..229c6980138 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map.go @@ -94,7 +94,7 @@ func sizeMap(mapv reflect.Value, mapi *mapInfo, f *coderFieldInfo, opts marshalO return 0 } n := 0 - iter := mapRange(mapv) + iter := mapv.MapRange() for iter.Next() { key := mapi.conv.keyConv.PBValueOf(iter.Key()).MapKey() keySize := mapi.keyFuncs.size(key.Value(), mapKeyTagSize, opts) @@ -281,7 +281,7 @@ func appendMap(b []byte, mapv reflect.Value, mapi *mapInfo, f *coderFieldInfo, o if opts.Deterministic() { return appendMapDeterministic(b, mapv, mapi, f, opts) } - iter := mapRange(mapv) + iter := mapv.MapRange() for iter.Next() { var err error b = protowire.AppendVarint(b, f.wiretag) @@ -328,7 +328,7 @@ func isInitMap(mapv reflect.Value, mapi *mapInfo, f *coderFieldInfo) error { if !mi.needsInitCheck { return nil } - iter := mapRange(mapv) + iter := mapv.MapRange() for iter.Next() { val := pointerOfValue(iter.Value()) if err := mi.checkInitializedPointer(val); err != nil { @@ -336,7 +336,7 @@ func isInitMap(mapv reflect.Value, mapi *mapInfo, f *coderFieldInfo) error { } } } else { - iter := mapRange(mapv) + iter := mapv.MapRange() for iter.Next() { val := mapi.conv.valConv.PBValueOf(iter.Value()) if err := mapi.valFuncs.isInit(val); err != nil { @@ -356,7 +356,7 @@ func mergeMap(dst, src pointer, f *coderFieldInfo, opts mergeOptions) { if dstm.IsNil() { dstm.Set(reflect.MakeMap(f.ft)) } - iter := mapRange(srcm) + iter := srcm.MapRange() for iter.Next() { dstm.SetMapIndex(iter.Key(), iter.Value()) } @@ -371,7 +371,7 @@ func mergeMapOfBytes(dst, src pointer, f *coderFieldInfo, opts mergeOptions) { if dstm.IsNil() { dstm.Set(reflect.MakeMap(f.ft)) } - iter := mapRange(srcm) + iter := srcm.MapRange() for iter.Next() { dstm.SetMapIndex(iter.Key(), reflect.ValueOf(append(emptyBuf[:], iter.Value().Bytes()...))) } @@ -386,7 +386,7 @@ func mergeMapOfMessage(dst, src pointer, f *coderFieldInfo, opts mergeOptions) { if dstm.IsNil() { dstm.Set(reflect.MakeMap(f.ft)) } - iter := mapRange(srcm) + iter := srcm.MapRange() for iter.Next() { val := reflect.New(f.ft.Elem().Elem()) if f.mi != nil { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go111.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go111.go deleted file mode 100644 index 4b15493f2f4..00000000000 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go111.go +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright 2019 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -//go:build !go1.12 -// +build !go1.12 - -package impl - -import "reflect" - -type mapIter struct { - v reflect.Value - keys []reflect.Value -} - -// mapRange provides a less-efficient equivalent to -// the Go 1.12 reflect.Value.MapRange method. -func mapRange(v reflect.Value) *mapIter { - return &mapIter{v: v} -} - -func (i *mapIter) Next() bool { - if i.keys == nil { - i.keys = i.v.MapKeys() - } else { - i.keys = i.keys[1:] - } - return len(i.keys) > 0 -} - -func (i *mapIter) Key() reflect.Value { - return i.keys[0] -} - -func (i *mapIter) Value() reflect.Value { - return i.v.MapIndex(i.keys[0]) -} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go112.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go112.go deleted file mode 100644 index 0b31b66eaf8..00000000000 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_map_go112.go +++ /dev/null @@ -1,12 +0,0 @@ -// Copyright 2019 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -//go:build go1.12 -// +build go1.12 - -package impl - -import "reflect" - -func mapRange(v reflect.Value) *reflect.MapIter { return v.MapRange() } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message.go index 2f7b363ec4a..f78b57b0467 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message.go @@ -118,12 +118,9 @@ func (mi *MessageInfo) makeCoderMethods(t reflect.Type, si structInfo) { }, } case isOneof: - fieldOffset = offsetOf(fs, mi.Exporter) - case fd.IsWeak(): - fieldOffset = si.weakOffset - funcs = makeWeakMessageFieldCoder(fd) + fieldOffset = offsetOf(fs) default: - fieldOffset = offsetOf(fs, mi.Exporter) + fieldOffset = offsetOf(fs) childMessage, funcs = fieldCoder(fd, ft) } cf := &preallocFields[i] diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message_opaque.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message_opaque.go index 88c16ae5b7c..41c1f74ef81 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message_opaque.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/codec_message_opaque.go @@ -45,19 +45,16 @@ func (mi *MessageInfo) makeOpaqueCoderMethods(t reflect.Type, si opaqueStructInf var childMessage *MessageInfo switch { case fd.ContainingOneof() != nil && !fd.ContainingOneof().IsSynthetic(): - fieldOffset = offsetOf(fs, mi.Exporter) - case fd.IsWeak(): - fieldOffset = si.weakOffset - funcs = makeWeakMessageFieldCoder(fd) + fieldOffset = offsetOf(fs) case fd.Message() != nil && !fd.IsMap(): - fieldOffset = offsetOf(fs, mi.Exporter) + fieldOffset = offsetOf(fs) if fd.IsList() { childMessage, funcs = makeOpaqueRepeatedMessageFieldCoder(fd, ft) } else { childMessage, funcs = makeOpaqueMessageFieldCoder(fd, ft) } default: - fieldOffset = offsetOf(fs, mi.Exporter) + fieldOffset = offsetOf(fs) childMessage, funcs = fieldCoder(fd, ft) } cf := &coderFieldInfo{ diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/convert_map.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/convert_map.go index 304244a651d..e4580b3ac2e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/convert_map.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/convert_map.go @@ -101,7 +101,7 @@ func (ms *mapReflect) Mutable(k protoreflect.MapKey) protoreflect.Value { return v } func (ms *mapReflect) Range(f func(protoreflect.MapKey, protoreflect.Value) bool) { - iter := mapRange(ms.v) + iter := ms.v.MapRange() for iter.Next() { k := ms.keyConv.PBValueOf(iter.Key()).MapKey() v := ms.valConv.PBValueOf(iter.Value()) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/lazy.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/lazy.go index e8fb6c35b4a..c7de31e243e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/lazy.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/lazy.go @@ -131,7 +131,7 @@ func (mi *MessageInfo) skipField(b []byte, f *coderFieldInfo, wtyp protowire.Typ fmi := f.validation.mi if fmi == nil { fd := mi.Desc.Fields().ByNumber(f.num) - if fd == nil || !fd.IsWeak() { + if fd == nil { return out, ValidationUnknown } messageName := fd.Message().FullName() diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/legacy_message.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/legacy_message.go index bf0b6049b46..a51dffbe294 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/legacy_message.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/legacy_message.go @@ -310,12 +310,9 @@ func aberrantAppendField(md *filedesc.Message, goType reflect.Type, tag, tagKey, fd.L0.Parent = md fd.L0.Index = n - if fd.L1.IsWeak || fd.L1.EditionFeatures.IsPacked { + if fd.L1.EditionFeatures.IsPacked { fd.L1.Options = func() protoreflect.ProtoMessage { opts := descopts.Field.ProtoReflect().New() - if fd.L1.IsWeak { - opts.Set(opts.Descriptor().Fields().ByName("weak"), protoreflect.ValueOfBool(true)) - } if fd.L1.EditionFeatures.IsPacked { opts.Set(opts.Descriptor().Fields().ByName("packed"), protoreflect.ValueOfBool(fd.L1.EditionFeatures.IsPacked)) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message.go index fa10a0f5cc9..d50423dcb77 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message.go @@ -14,7 +14,6 @@ import ( "google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/reflect/protoreflect" - "google.golang.org/protobuf/reflect/protoregistry" ) // MessageInfo provides protobuf related functionality for a given Go type @@ -120,7 +119,6 @@ type ( var ( sizecacheType = reflect.TypeOf(SizeCache(0)) - weakFieldsType = reflect.TypeOf(WeakFields(nil)) unknownFieldsAType = reflect.TypeOf(unknownFieldsA(nil)) unknownFieldsBType = reflect.TypeOf(unknownFieldsB(nil)) extensionFieldsType = reflect.TypeOf(ExtensionFields(nil)) @@ -129,8 +127,6 @@ var ( type structInfo struct { sizecacheOffset offset sizecacheType reflect.Type - weakOffset offset - weakType reflect.Type unknownOffset offset unknownType reflect.Type extensionOffset offset @@ -148,7 +144,6 @@ type structInfo struct { func (mi *MessageInfo) makeStructInfo(t reflect.Type) structInfo { si := structInfo{ sizecacheOffset: invalidOffset, - weakOffset: invalidOffset, unknownOffset: invalidOffset, extensionOffset: invalidOffset, lazyOffset: invalidOffset, @@ -165,28 +160,23 @@ fieldLoop: switch f := t.Field(i); f.Name { case genid.SizeCache_goname, genid.SizeCacheA_goname: if f.Type == sizecacheType { - si.sizecacheOffset = offsetOf(f, mi.Exporter) + si.sizecacheOffset = offsetOf(f) si.sizecacheType = f.Type } - case genid.WeakFields_goname, genid.WeakFieldsA_goname: - if f.Type == weakFieldsType { - si.weakOffset = offsetOf(f, mi.Exporter) - si.weakType = f.Type - } case genid.UnknownFields_goname, genid.UnknownFieldsA_goname: if f.Type == unknownFieldsAType || f.Type == unknownFieldsBType { - si.unknownOffset = offsetOf(f, mi.Exporter) + si.unknownOffset = offsetOf(f) si.unknownType = f.Type } case genid.ExtensionFields_goname, genid.ExtensionFieldsA_goname, genid.ExtensionFieldsB_goname: if f.Type == extensionFieldsType { - si.extensionOffset = offsetOf(f, mi.Exporter) + si.extensionOffset = offsetOf(f) si.extensionType = f.Type } case "lazyFields", "XXX_lazyUnmarshalInfo": - si.lazyOffset = offsetOf(f, mi.Exporter) + si.lazyOffset = offsetOf(f) case "XXX_presence": - si.presenceOffset = offsetOf(f, mi.Exporter) + si.presenceOffset = offsetOf(f) default: for _, s := range strings.Split(f.Tag.Get("protobuf"), ",") { if len(s) > 0 && strings.Trim(s, "0123456789") == "" { @@ -256,9 +246,6 @@ func (mi *MessageInfo) Message(i int) protoreflect.MessageType { mi.init() fd := mi.Desc.Fields().Get(i) switch { - case fd.IsWeak(): - mt, _ := protoregistry.GlobalTypes.FindMessageByName(fd.Message().FullName()) - return mt case fd.IsMap(): return mapEntryType{fd.Message(), mi.fieldTypes[fd.Number()]} default: diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_opaque.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_opaque.go index d407dd791e8..dd55e8e009c 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_opaque.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_opaque.go @@ -56,9 +56,6 @@ func opaqueInitHook(mi *MessageInfo) bool { usePresence, _ := usePresenceForField(si, fd) switch { - case fd.IsWeak(): - // Weak fields are no different for opaque. - fi = fieldInfoForWeakMessage(fd, si.weakOffset) case fd.ContainingOneof() != nil && !fd.ContainingOneof().IsSynthetic(): // Oneofs are no different for opaque. fi = fieldInfoForOneof(fd, si.oneofsByName[fd.ContainingOneof().Name()], mi.Exporter, si.oneofWrappersByNumber[fd.Number()]) @@ -88,9 +85,7 @@ func opaqueInitHook(mi *MessageInfo) bool { mi.oneofs = map[protoreflect.Name]*oneofInfo{} for i := 0; i < mi.Desc.Oneofs().Len(); i++ { od := mi.Desc.Oneofs().Get(i) - if !od.IsSynthetic() { - mi.oneofs[od.Name()] = makeOneofInfo(od, si.structInfo, mi.Exporter) - } + mi.oneofs[od.Name()] = makeOneofInfoOpaque(mi, od, si.structInfo, mi.Exporter) } mi.denseFields = make([]*fieldInfo, fds.Len()*2) @@ -119,12 +114,32 @@ func opaqueInitHook(mi *MessageInfo) bool { return true } +func makeOneofInfoOpaque(mi *MessageInfo, od protoreflect.OneofDescriptor, si structInfo, x exporter) *oneofInfo { + oi := &oneofInfo{oneofDesc: od} + if od.IsSynthetic() { + fd := od.Fields().Get(0) + index, _ := presenceIndex(mi.Desc, fd) + oi.which = func(p pointer) protoreflect.FieldNumber { + if p.IsNil() { + return 0 + } + if !mi.present(p, index) { + return 0 + } + return od.Fields().Get(0).Number() + } + return oi + } + // Dispatch to non-opaque oneof implementation for non-synthetic oneofs. + return makeOneofInfo(od, si, x) +} + func (mi *MessageInfo) fieldInfoForMapOpaque(si opaqueStructInfo, fd protoreflect.FieldDescriptor, fs reflect.StructField) fieldInfo { ft := fs.Type if ft.Kind() != reflect.Map { panic(fmt.Sprintf("invalid type: got %v, want map kind", ft)) } - fieldOffset := offsetOf(fs, mi.Exporter) + fieldOffset := offsetOf(fs) conv := NewConverter(ft, fd) return fieldInfo{ fieldDesc: fd, @@ -178,7 +193,7 @@ func (mi *MessageInfo) fieldInfoForScalarListOpaque(si opaqueStructInfo, fd prot panic(fmt.Sprintf("invalid type: got %v, want slice kind", ft)) } conv := NewConverter(reflect.PtrTo(ft), fd) - fieldOffset := offsetOf(fs, mi.Exporter) + fieldOffset := offsetOf(fs) index, _ := presenceIndex(mi.Desc, fd) return fieldInfo{ fieldDesc: fd, @@ -228,7 +243,7 @@ func (mi *MessageInfo) fieldInfoForMessageListOpaque(si opaqueStructInfo, fd pro panic(fmt.Sprintf("invalid type: got %v, want slice kind", ft)) } conv := NewConverter(ft, fd) - fieldOffset := offsetOf(fs, mi.Exporter) + fieldOffset := offsetOf(fs) index, _ := presenceIndex(mi.Desc, fd) fieldNumber := fd.Number() return fieldInfo{ @@ -321,7 +336,7 @@ func (mi *MessageInfo) fieldInfoForMessageListOpaqueNoPresence(si opaqueStructIn panic(fmt.Sprintf("invalid type: got %v, want slice kind", ft)) } conv := NewConverter(ft, fd) - fieldOffset := offsetOf(fs, mi.Exporter) + fieldOffset := offsetOf(fs) return fieldInfo{ fieldDesc: fd, has: func(p pointer) bool { @@ -393,7 +408,7 @@ func (mi *MessageInfo) fieldInfoForScalarOpaque(si opaqueStructInfo, fd protoref deref = true } conv := NewConverter(ft, fd) - fieldOffset := offsetOf(fs, mi.Exporter) + fieldOffset := offsetOf(fs) index, _ := presenceIndex(mi.Desc, fd) var getter func(p pointer) protoreflect.Value if !nullable { @@ -462,7 +477,7 @@ func (mi *MessageInfo) fieldInfoForScalarOpaque(si opaqueStructInfo, fd protoref func (mi *MessageInfo) fieldInfoForMessageOpaque(si opaqueStructInfo, fd protoreflect.FieldDescriptor, fs reflect.StructField) fieldInfo { ft := fs.Type conv := NewConverter(ft, fd) - fieldOffset := offsetOf(fs, mi.Exporter) + fieldOffset := offsetOf(fs) index, _ := presenceIndex(mi.Desc, fd) fieldNumber := fd.Number() elemType := fs.Type.Elem() @@ -602,8 +617,6 @@ func usePresenceForField(si opaqueStructInfo, fd protoreflect.FieldDescriptor) ( switch { case fd.ContainingOneof() != nil && !fd.ContainingOneof().IsSynthetic(): return false, false - case fd.IsWeak(): - return false, false case fd.IsMap(): return false, false case fd.Kind() == protoreflect.MessageKind || fd.Kind() == protoreflect.GroupKind: diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect.go index 31c19b54f8d..0d20132fa24 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect.go @@ -72,8 +72,6 @@ func (mi *MessageInfo) makeKnownFieldsFunc(si structInfo) { fi = fieldInfoForMap(fd, fs, mi.Exporter) case fd.IsList(): fi = fieldInfoForList(fd, fs, mi.Exporter) - case fd.IsWeak(): - fi = fieldInfoForWeakMessage(fd, si.weakOffset) case fd.Message() != nil: fi = fieldInfoForMessage(fd, fs, mi.Exporter) default: @@ -219,9 +217,6 @@ func (mi *MessageInfo) makeFieldTypes(si structInfo) { } case fd.Message() != nil: ft = fs.Type - if fd.IsWeak() { - ft = nil - } isMessage = true } if isMessage && ft != nil && ft.Kind() != reflect.Ptr { diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect_field.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect_field.go index a740646205c..68d4ae32ec9 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect_field.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/message_reflect_field.go @@ -8,11 +8,8 @@ import ( "fmt" "math" "reflect" - "sync" - "google.golang.org/protobuf/internal/flags" "google.golang.org/protobuf/reflect/protoreflect" - "google.golang.org/protobuf/reflect/protoregistry" ) type fieldInfo struct { @@ -76,7 +73,7 @@ func fieldInfoForOneof(fd protoreflect.FieldDescriptor, fs reflect.StructField, isMessage := fd.Message() != nil // TODO: Implement unsafe fast path? - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) return fieldInfo{ // NOTE: The logic below intentionally assumes that oneof fields are // well-formatted. That is, the oneof interface never contains a @@ -152,7 +149,7 @@ func fieldInfoForMap(fd protoreflect.FieldDescriptor, fs reflect.StructField, x conv := NewConverter(ft, fd) // TODO: Implement unsafe fast path? - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) return fieldInfo{ fieldDesc: fd, has: func(p pointer) bool { @@ -205,7 +202,7 @@ func fieldInfoForList(fd protoreflect.FieldDescriptor, fs reflect.StructField, x conv := NewConverter(reflect.PtrTo(ft), fd) // TODO: Implement unsafe fast path? - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) return fieldInfo{ fieldDesc: fd, has: func(p pointer) bool { @@ -269,7 +266,7 @@ func fieldInfoForScalar(fd protoreflect.FieldDescriptor, fs reflect.StructField, } } conv := NewConverter(ft, fd) - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) // Generate specialized getter functions to avoid going through reflect.Value if nullable { @@ -332,85 +329,12 @@ func fieldInfoForScalar(fd protoreflect.FieldDescriptor, fs reflect.StructField, } } -func fieldInfoForWeakMessage(fd protoreflect.FieldDescriptor, weakOffset offset) fieldInfo { - if !flags.ProtoLegacy { - panic("no support for proto1 weak fields") - } - - var once sync.Once - var messageType protoreflect.MessageType - lazyInit := func() { - once.Do(func() { - messageName := fd.Message().FullName() - messageType, _ = protoregistry.GlobalTypes.FindMessageByName(messageName) - if messageType == nil { - panic(fmt.Sprintf("weak message %v for field %v is not linked in", messageName, fd.FullName())) - } - }) - } - - num := fd.Number() - return fieldInfo{ - fieldDesc: fd, - has: func(p pointer) bool { - if p.IsNil() { - return false - } - _, ok := p.Apply(weakOffset).WeakFields().get(num) - return ok - }, - clear: func(p pointer) { - p.Apply(weakOffset).WeakFields().clear(num) - }, - get: func(p pointer) protoreflect.Value { - lazyInit() - if p.IsNil() { - return protoreflect.ValueOfMessage(messageType.Zero()) - } - m, ok := p.Apply(weakOffset).WeakFields().get(num) - if !ok { - return protoreflect.ValueOfMessage(messageType.Zero()) - } - return protoreflect.ValueOfMessage(m.ProtoReflect()) - }, - set: func(p pointer, v protoreflect.Value) { - lazyInit() - m := v.Message() - if m.Descriptor() != messageType.Descriptor() { - if got, want := m.Descriptor().FullName(), messageType.Descriptor().FullName(); got != want { - panic(fmt.Sprintf("field %v has mismatching message descriptor: got %v, want %v", fd.FullName(), got, want)) - } - panic(fmt.Sprintf("field %v has mismatching message descriptor: %v", fd.FullName(), m.Descriptor().FullName())) - } - p.Apply(weakOffset).WeakFields().set(num, m.Interface()) - }, - mutable: func(p pointer) protoreflect.Value { - lazyInit() - fs := p.Apply(weakOffset).WeakFields() - m, ok := fs.get(num) - if !ok { - m = messageType.New().Interface() - fs.set(num, m) - } - return protoreflect.ValueOfMessage(m.ProtoReflect()) - }, - newMessage: func() protoreflect.Message { - lazyInit() - return messageType.New() - }, - newField: func() protoreflect.Value { - lazyInit() - return protoreflect.ValueOfMessage(messageType.New()) - }, - } -} - func fieldInfoForMessage(fd protoreflect.FieldDescriptor, fs reflect.StructField, x exporter) fieldInfo { ft := fs.Type conv := NewConverter(ft, fd) // TODO: Implement unsafe fast path? - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) return fieldInfo{ fieldDesc: fd, has: func(p pointer) bool { @@ -419,7 +343,7 @@ func fieldInfoForMessage(fd protoreflect.FieldDescriptor, fs reflect.StructField } rv := p.Apply(fieldOffset).AsValueOf(fs.Type).Elem() if fs.Type.Kind() != reflect.Ptr { - return !isZero(rv) + return !rv.IsZero() } return !rv.IsNil() }, @@ -466,7 +390,7 @@ func makeOneofInfo(od protoreflect.OneofDescriptor, si structInfo, x exporter) * oi := &oneofInfo{oneofDesc: od} if od.IsSynthetic() { fs := si.fieldsByNumber[od.Fields().Get(0).Number()] - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) oi.which = func(p pointer) protoreflect.FieldNumber { if p.IsNil() { return 0 @@ -479,7 +403,7 @@ func makeOneofInfo(od protoreflect.OneofDescriptor, si structInfo, x exporter) * } } else { fs := si.oneofsByName[od.Name()] - fieldOffset := offsetOf(fs, x) + fieldOffset := offsetOf(fs) oi.which = func(p pointer) protoreflect.FieldNumber { if p.IsNil() { return 0 @@ -497,41 +421,3 @@ func makeOneofInfo(od protoreflect.OneofDescriptor, si structInfo, x exporter) * } return oi } - -// isZero is identical to reflect.Value.IsZero. -// TODO: Remove this when Go1.13 is the minimally supported Go version. -func isZero(v reflect.Value) bool { - switch v.Kind() { - case reflect.Bool: - return !v.Bool() - case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: - return v.Int() == 0 - case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr: - return v.Uint() == 0 - case reflect.Float32, reflect.Float64: - return math.Float64bits(v.Float()) == 0 - case reflect.Complex64, reflect.Complex128: - c := v.Complex() - return math.Float64bits(real(c)) == 0 && math.Float64bits(imag(c)) == 0 - case reflect.Array: - for i := 0; i < v.Len(); i++ { - if !isZero(v.Index(i)) { - return false - } - } - return true - case reflect.Chan, reflect.Func, reflect.Interface, reflect.Map, reflect.Ptr, reflect.Slice, reflect.UnsafePointer: - return v.IsNil() - case reflect.String: - return v.Len() == 0 - case reflect.Struct: - for i := 0; i < v.NumField(); i++ { - if !isZero(v.Field(i)) { - return false - } - } - return true - default: - panic(&reflect.ValueError{Method: "reflect.Value.IsZero", Kind: v.Kind()}) - } -} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/pointer_unsafe.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/pointer_unsafe.go index 041ebde2de6..62f8bf663ea 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/pointer_unsafe.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/pointer_unsafe.go @@ -22,7 +22,7 @@ type Pointer unsafe.Pointer type offset uintptr // offsetOf returns a field offset for the struct field. -func offsetOf(f reflect.StructField, x exporter) offset { +func offsetOf(f reflect.StructField) offset { return offset(f.Offset) } @@ -111,7 +111,6 @@ func (p pointer) StringSlice() *[]string { return (*[]string)(p.p func (p pointer) Bytes() *[]byte { return (*[]byte)(p.p) } func (p pointer) BytesPtr() **[]byte { return (**[]byte)(p.p) } func (p pointer) BytesSlice() *[][]byte { return (*[][]byte)(p.p) } -func (p pointer) WeakFields() *weakFields { return (*weakFields)(p.p) } func (p pointer) Extensions() *map[int32]ExtensionField { return (*map[int32]ExtensionField)(p.p) } func (p pointer) LazyInfoPtr() **protolazy.XXX_lazyUnmarshalInfo { return (**protolazy.XXX_lazyUnmarshalInfo)(p.p) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/validate.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/validate.go index b534a3d6dbb..7b2995dde5e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/validate.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/validate.go @@ -211,9 +211,7 @@ func newValidationInfo(fd protoreflect.FieldDescriptor, ft reflect.Type) validat switch fd.Kind() { case protoreflect.MessageKind: vi.typ = validationTypeMessage - if !fd.IsWeak() { - vi.mi = getMessageInfo(ft) - } + vi.mi = getMessageInfo(ft) case protoreflect.GroupKind: vi.typ = validationTypeGroup vi.mi = getMessageInfo(ft) @@ -320,26 +318,6 @@ State: } if f != nil { vi = f.validation - if vi.typ == validationTypeMessage && vi.mi == nil { - // Probable weak field. - // - // TODO: Consider storing the results of this lookup somewhere - // rather than recomputing it on every validation. - fd := st.mi.Desc.Fields().ByNumber(num) - if fd == nil || !fd.IsWeak() { - break - } - messageName := fd.Message().FullName() - messageType, err := protoregistry.GlobalTypes.FindMessageByName(messageName) - switch err { - case nil: - vi.mi, _ = messageType.(*MessageInfo) - case protoregistry.NotFound: - vi.typ = validationTypeBytes - default: - return out, ValidationUnknown - } - } break } // Possible extension field. diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/weak.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/weak.go deleted file mode 100644 index eb79a7ba94c..00000000000 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/impl/weak.go +++ /dev/null @@ -1,74 +0,0 @@ -// Copyright 2019 The Go Authors. All rights reserved. -// Use of this source code is governed by a BSD-style -// license that can be found in the LICENSE file. - -package impl - -import ( - "fmt" - - "google.golang.org/protobuf/reflect/protoreflect" - "google.golang.org/protobuf/reflect/protoregistry" -) - -// weakFields adds methods to the exported WeakFields type for internal use. -// -// The exported type is an alias to an unnamed type, so methods can't be -// defined directly on it. -type weakFields WeakFields - -func (w weakFields) get(num protoreflect.FieldNumber) (protoreflect.ProtoMessage, bool) { - m, ok := w[int32(num)] - return m, ok -} - -func (w *weakFields) set(num protoreflect.FieldNumber, m protoreflect.ProtoMessage) { - if *w == nil { - *w = make(weakFields) - } - (*w)[int32(num)] = m -} - -func (w *weakFields) clear(num protoreflect.FieldNumber) { - delete(*w, int32(num)) -} - -func (Export) HasWeak(w WeakFields, num protoreflect.FieldNumber) bool { - _, ok := w[int32(num)] - return ok -} - -func (Export) ClearWeak(w *WeakFields, num protoreflect.FieldNumber) { - delete(*w, int32(num)) -} - -func (Export) GetWeak(w WeakFields, num protoreflect.FieldNumber, name protoreflect.FullName) protoreflect.ProtoMessage { - if m, ok := w[int32(num)]; ok { - return m - } - mt, _ := protoregistry.GlobalTypes.FindMessageByName(name) - if mt == nil { - panic(fmt.Sprintf("message %v for weak field is not linked in", name)) - } - return mt.Zero().Interface() -} - -func (Export) SetWeak(w *WeakFields, num protoreflect.FieldNumber, name protoreflect.FullName, m protoreflect.ProtoMessage) { - if m != nil { - mt, _ := protoregistry.GlobalTypes.FindMessageByName(name) - if mt == nil { - panic(fmt.Sprintf("message %v for weak field is not linked in", name)) - } - if mt != m.ProtoReflect().Type() { - panic(fmt.Sprintf("invalid message type for weak field: got %T, want %T", m, mt.Zero().Interface())) - } - } - if m == nil || !m.ProtoReflect().IsValid() { - delete(*w, int32(num)) - return - } - if *w == nil { - *w = make(weakFields) - } - (*w)[int32(num)] = m -} diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/version/version.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/version/version.go index 3018450df79..01efc33030d 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/version/version.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/internal/version/version.go @@ -52,7 +52,7 @@ import ( const ( Major = 1 Minor = 36 - Patch = 1 + Patch = 5 PreRelease = "" ) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/proto/decode.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/proto/decode.go index a3b5e142d24..4cbf1aeaf79 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/proto/decode.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/proto/decode.go @@ -8,7 +8,6 @@ import ( "google.golang.org/protobuf/encoding/protowire" "google.golang.org/protobuf/internal/encoding/messageset" "google.golang.org/protobuf/internal/errors" - "google.golang.org/protobuf/internal/flags" "google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/internal/pragma" "google.golang.org/protobuf/reflect/protoreflect" @@ -172,10 +171,6 @@ func (o UnmarshalOptions) unmarshalMessageSlow(b []byte, m protoreflect.Message) var err error if fd == nil { err = errUnknown - } else if flags.ProtoLegacy { - if fd.IsWeak() && fd.Message().IsPlaceholder() { - err = errUnknown // weak referent is not linked in - } } // Parse the field value. diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc.go index 69a05050917..823dbf3ba6c 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc.go @@ -132,17 +132,11 @@ func (o FileOptions) New(fd *descriptorpb.FileDescriptorProto, r Resolver) (prot } f.L2.Imports[i].IsPublic = true } - for _, i := range fd.GetWeakDependency() { - if !(0 <= i && int(i) < len(f.L2.Imports)) || f.L2.Imports[i].IsWeak { - return nil, errors.New("invalid or duplicate weak import index: %d", i) - } - f.L2.Imports[i].IsWeak = true - } imps := importSet{f.Path(): true} for i, path := range fd.GetDependency() { imp := &f.L2.Imports[i] f, err := r.FindFileByPath(path) - if err == protoregistry.NotFound && (o.AllowUnresolvable || imp.IsWeak) { + if err == protoregistry.NotFound && o.AllowUnresolvable { f = filedesc.PlaceholderFile(path) } else if err != nil { return nil, errors.New("could not resolve import %q: %v", path, err) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_init.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_init.go index ebcb4a8ab13..9da34998b17 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_init.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_init.go @@ -149,7 +149,6 @@ func (r descsByName) initFieldsFromDescriptorProto(fds []*descriptorpb.FieldDesc if opts := fd.GetOptions(); opts != nil { opts = proto.Clone(opts).(*descriptorpb.FieldOptions) f.L1.Options = func() protoreflect.ProtoMessage { return opts } - f.L1.IsWeak = opts.GetWeak() f.L1.IsLazy = opts.GetLazy() if opts.Packed != nil { f.L1.EditionFeatures.IsPacked = opts.GetPacked() diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_resolve.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_resolve.go index f3cebab29c8..ff692436e9f 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_resolve.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_resolve.go @@ -43,7 +43,7 @@ func (r *resolver) resolveMessageDependencies(ms []filedesc.Message, mds []*desc o.L1.Fields.List = append(o.L1.Fields.List, f) } - if f.L1.Kind, f.L1.Enum, f.L1.Message, err = r.findTarget(f.Kind(), f.Parent().FullName(), partialName(fd.GetTypeName()), f.IsWeak()); err != nil { + if f.L1.Kind, f.L1.Enum, f.L1.Message, err = r.findTarget(f.Kind(), f.Parent().FullName(), partialName(fd.GetTypeName())); err != nil { return errors.New("message field %q cannot resolve type: %v", f.FullName(), err) } if f.L1.Kind == protoreflect.GroupKind && (f.IsMap() || f.IsMapEntry()) { @@ -73,10 +73,10 @@ func (r *resolver) resolveMessageDependencies(ms []filedesc.Message, mds []*desc func (r *resolver) resolveExtensionDependencies(xs []filedesc.Extension, xds []*descriptorpb.FieldDescriptorProto) (err error) { for i, xd := range xds { x := &xs[i] - if x.L1.Extendee, err = r.findMessageDescriptor(x.Parent().FullName(), partialName(xd.GetExtendee()), false); err != nil { + if x.L1.Extendee, err = r.findMessageDescriptor(x.Parent().FullName(), partialName(xd.GetExtendee())); err != nil { return errors.New("extension field %q cannot resolve extendee: %v", x.FullName(), err) } - if x.L1.Kind, x.L2.Enum, x.L2.Message, err = r.findTarget(x.Kind(), x.Parent().FullName(), partialName(xd.GetTypeName()), false); err != nil { + if x.L1.Kind, x.L2.Enum, x.L2.Message, err = r.findTarget(x.Kind(), x.Parent().FullName(), partialName(xd.GetTypeName())); err != nil { return errors.New("extension field %q cannot resolve type: %v", x.FullName(), err) } if xd.DefaultValue != nil { @@ -95,11 +95,11 @@ func (r *resolver) resolveServiceDependencies(ss []filedesc.Service, sds []*desc s := &ss[i] for j, md := range sd.GetMethod() { m := &s.L2.Methods.List[j] - m.L1.Input, err = r.findMessageDescriptor(m.Parent().FullName(), partialName(md.GetInputType()), false) + m.L1.Input, err = r.findMessageDescriptor(m.Parent().FullName(), partialName(md.GetInputType())) if err != nil { return errors.New("service method %q cannot resolve input: %v", m.FullName(), err) } - m.L1.Output, err = r.findMessageDescriptor(s.FullName(), partialName(md.GetOutputType()), false) + m.L1.Output, err = r.findMessageDescriptor(s.FullName(), partialName(md.GetOutputType())) if err != nil { return errors.New("service method %q cannot resolve output: %v", m.FullName(), err) } @@ -111,16 +111,16 @@ func (r *resolver) resolveServiceDependencies(ss []filedesc.Service, sds []*desc // findTarget finds an enum or message descriptor if k is an enum, message, // group, or unknown. If unknown, and the name could be resolved, the kind // returned kind is set based on the type of the resolved descriptor. -func (r *resolver) findTarget(k protoreflect.Kind, scope protoreflect.FullName, ref partialName, isWeak bool) (protoreflect.Kind, protoreflect.EnumDescriptor, protoreflect.MessageDescriptor, error) { +func (r *resolver) findTarget(k protoreflect.Kind, scope protoreflect.FullName, ref partialName) (protoreflect.Kind, protoreflect.EnumDescriptor, protoreflect.MessageDescriptor, error) { switch k { case protoreflect.EnumKind: - ed, err := r.findEnumDescriptor(scope, ref, isWeak) + ed, err := r.findEnumDescriptor(scope, ref) if err != nil { return 0, nil, nil, err } return k, ed, nil, nil case protoreflect.MessageKind, protoreflect.GroupKind: - md, err := r.findMessageDescriptor(scope, ref, isWeak) + md, err := r.findMessageDescriptor(scope, ref) if err != nil { return 0, nil, nil, err } @@ -129,7 +129,7 @@ func (r *resolver) findTarget(k protoreflect.Kind, scope protoreflect.FullName, // Handle unspecified kinds (possible with parsers that operate // on a per-file basis without knowledge of dependencies). d, err := r.findDescriptor(scope, ref) - if err == protoregistry.NotFound && (r.allowUnresolvable || isWeak) { + if err == protoregistry.NotFound && r.allowUnresolvable { return k, filedesc.PlaceholderEnum(ref.FullName()), filedesc.PlaceholderMessage(ref.FullName()), nil } else if err == protoregistry.NotFound { return 0, nil, nil, errors.New("%q not found", ref.FullName()) @@ -206,9 +206,9 @@ func (r *resolver) findDescriptor(scope protoreflect.FullName, ref partialName) } } -func (r *resolver) findEnumDescriptor(scope protoreflect.FullName, ref partialName, isWeak bool) (protoreflect.EnumDescriptor, error) { +func (r *resolver) findEnumDescriptor(scope protoreflect.FullName, ref partialName) (protoreflect.EnumDescriptor, error) { d, err := r.findDescriptor(scope, ref) - if err == protoregistry.NotFound && (r.allowUnresolvable || isWeak) { + if err == protoregistry.NotFound && r.allowUnresolvable { return filedesc.PlaceholderEnum(ref.FullName()), nil } else if err == protoregistry.NotFound { return nil, errors.New("%q not found", ref.FullName()) @@ -222,9 +222,9 @@ func (r *resolver) findEnumDescriptor(scope protoreflect.FullName, ref partialNa return ed, nil } -func (r *resolver) findMessageDescriptor(scope protoreflect.FullName, ref partialName, isWeak bool) (protoreflect.MessageDescriptor, error) { +func (r *resolver) findMessageDescriptor(scope protoreflect.FullName, ref partialName) (protoreflect.MessageDescriptor, error) { d, err := r.findDescriptor(scope, ref) - if err == protoregistry.NotFound && (r.allowUnresolvable || isWeak) { + if err == protoregistry.NotFound && r.allowUnresolvable { return filedesc.PlaceholderMessage(ref.FullName()), nil } else if err == protoregistry.NotFound { return nil, errors.New("%q not found", ref.FullName()) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_validate.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_validate.go index 6de31c2ebdb..c343d9227b5 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_validate.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/desc_validate.go @@ -149,12 +149,6 @@ func validateMessageDeclarations(file *filedesc.File, ms []filedesc.Message, mds return errors.New("message field %q under proto3 optional semantics must be within a single element oneof", f.FullName()) } } - if f.IsWeak() && !flags.ProtoLegacy { - return errors.New("message field %q is a weak field, which is a legacy proto1 feature that is no longer supported", f.FullName()) - } - if f.IsWeak() && (!f.HasPresence() || !isOptionalMessage(f) || f.ContainingOneof() != nil) { - return errors.New("message field %q may only be weak for an optional message", f.FullName()) - } if f.IsPacked() && !isPackable(f) { return errors.New("message field %q is not packable", f.FullName()) } @@ -199,9 +193,6 @@ func validateMessageDeclarations(file *filedesc.File, ms []filedesc.Message, mds if f.Cardinality() != protoreflect.Optional { return errors.New("message field %q belongs in a oneof and must be optional", f.FullName()) } - if f.IsWeak() { - return errors.New("message field %q belongs in a oneof and must not be a weak reference", f.FullName()) - } } } @@ -254,9 +245,6 @@ func validateExtensionDeclarations(f *filedesc.File, xs []filedesc.Extension, xd return errors.New("extension field %q has an invalid number: %d", x.FullName(), x.Number()) } } - if xd.GetOptions().GetWeak() { - return errors.New("extension field %q cannot be a weak reference", x.FullName()) - } if x.IsPacked() && !isPackable(x) { return errors.New("extension field %q is not packable", x.FullName()) } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/editions.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/editions.go index bf0a0ccdeed..697a61b290e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/editions.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/editions.go @@ -11,6 +11,7 @@ import ( "google.golang.org/protobuf/internal/editiondefaults" "google.golang.org/protobuf/internal/filedesc" + "google.golang.org/protobuf/internal/genid" "google.golang.org/protobuf/proto" "google.golang.org/protobuf/reflect/protoreflect" "google.golang.org/protobuf/types/descriptorpb" @@ -125,16 +126,43 @@ func mergeEditionFeatures(parentDesc protoreflect.Descriptor, child *descriptorp parentFS.IsJSONCompliant = *jf == descriptorpb.FeatureSet_ALLOW } - if goFeatures, ok := proto.GetExtension(child, gofeaturespb.E_Go).(*gofeaturespb.GoFeatures); ok && goFeatures != nil { - if luje := goFeatures.LegacyUnmarshalJsonEnum; luje != nil { - parentFS.GenerateLegacyUnmarshalJSON = *luje - } - if sep := goFeatures.StripEnumPrefix; sep != nil { - parentFS.StripEnumPrefix = int(*sep) - } - if al := goFeatures.ApiLevel; al != nil { - parentFS.APILevel = int(*al) - } + // We must not use proto.GetExtension(child, gofeaturespb.E_Go) + // because that only works for messages we generated, but not for + // dynamicpb messages. See golang/protobuf#1669. + // + // Further, we harden this code against adversarial inputs: a + // service which accepts descriptors from a possibly malicious + // source shouldn't crash. + goFeatures := child.ProtoReflect().Get(gofeaturespb.E_Go.TypeDescriptor()) + if !goFeatures.IsValid() { + return parentFS + } + gf, ok := goFeatures.Interface().(protoreflect.Message) + if !ok { + return parentFS + } + // gf.Interface() could be *dynamicpb.Message or *gofeaturespb.GoFeatures. + fields := gf.Descriptor().Fields() + + if fd := fields.ByNumber(genid.GoFeatures_LegacyUnmarshalJsonEnum_field_number); fd != nil && + !fd.IsList() && + fd.Kind() == protoreflect.BoolKind && + gf.Has(fd) { + parentFS.GenerateLegacyUnmarshalJSON = gf.Get(fd).Bool() + } + + if fd := fields.ByNumber(genid.GoFeatures_StripEnumPrefix_field_number); fd != nil && + !fd.IsList() && + fd.Kind() == protoreflect.EnumKind && + gf.Has(fd) { + parentFS.StripEnumPrefix = int(gf.Get(fd).Enum()) + } + + if fd := fields.ByNumber(genid.GoFeatures_ApiLevel_field_number); fd != nil && + !fd.IsList() && + fd.Kind() == protoreflect.EnumKind && + gf.Has(fd) { + parentFS.APILevel = int(gf.Get(fd).Enum()) } return parentFS diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/proto.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/proto.go index a5de8d40013..9b880aa8c96 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/proto.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protodesc/proto.go @@ -32,9 +32,6 @@ func ToFileDescriptorProto(file protoreflect.FileDescriptor) *descriptorpb.FileD if imp.IsPublic { p.PublicDependency = append(p.PublicDependency, int32(i)) } - if imp.IsWeak { - p.WeakDependency = append(p.WeakDependency, int32(i)) - } } for i, locs := 0, file.SourceLocations(); i < locs.Len(); i++ { loc := locs.Get(i) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protoreflect/type.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protoreflect/type.go index cd8fadbaf8f..cd7fbc87a47 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protoreflect/type.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/reflect/protoreflect/type.go @@ -68,7 +68,7 @@ type Descriptor interface { // dependency is not resolved, in which case only name information is known. // // Placeholder types may only be returned by the following accessors - // as a result of unresolved dependencies or weak imports: + // as a result of unresolved dependencies: // // ╔═══════════════════════════════════╤═════════════════════╗ // ║ Accessor │ Descriptor ║ @@ -168,11 +168,7 @@ type FileImport struct { // The current file and the imported file must be within proto package. IsPublic bool - // IsWeak reports whether this is a weak import, which does not impose - // a direct dependency on the target file. - // - // Weak imports are a legacy proto1 feature. Equivalent behavior is - // achieved using proto2 extension fields or proto3 Any messages. + // Deprecated: support for weak fields has been removed. IsWeak bool } @@ -325,9 +321,7 @@ type FieldDescriptor interface { // specified in the source .proto file. HasOptionalKeyword() bool - // IsWeak reports whether this is a weak field, which does not impose a - // direct dependency on the target type. - // If true, then Message returns a placeholder type. + // Deprecated: support for weak fields has been removed. IsWeak() bool // IsPacked reports whether repeated primitive numeric kinds should be diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/descriptorpb/descriptor.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/descriptorpb/descriptor.pb.go index a551e7ae945..a5163376741 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/descriptorpb/descriptor.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/descriptorpb/descriptor.pb.go @@ -46,6 +46,7 @@ import ( protoimpl "google.golang.org/protobuf/runtime/protoimpl" reflect "reflect" sync "sync" + unsafe "unsafe" ) // The full set of known editions. @@ -4360,7 +4361,7 @@ func (x *GeneratedCodeInfo_Annotation) GetSemantic() GeneratedCodeInfo_Annotatio var File_google_protobuf_descriptor_proto protoreflect.FileDescriptor -var file_google_protobuf_descriptor_proto_rawDesc = []byte{ +var file_google_protobuf_descriptor_proto_rawDesc = string([]byte{ 0x0a, 0x20, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x6f, 0x72, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, @@ -5130,16 +5131,16 @@ var file_google_protobuf_descriptor_proto_rawDesc = []byte{ 0x70, 0x62, 0xf8, 0x01, 0x01, 0xa2, 0x02, 0x03, 0x47, 0x50, 0x42, 0xaa, 0x02, 0x1a, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x52, 0x65, 0x66, 0x6c, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, -} +}) var ( file_google_protobuf_descriptor_proto_rawDescOnce sync.Once - file_google_protobuf_descriptor_proto_rawDescData = file_google_protobuf_descriptor_proto_rawDesc + file_google_protobuf_descriptor_proto_rawDescData []byte ) func file_google_protobuf_descriptor_proto_rawDescGZIP() []byte { file_google_protobuf_descriptor_proto_rawDescOnce.Do(func() { - file_google_protobuf_descriptor_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_descriptor_proto_rawDescData) + file_google_protobuf_descriptor_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_descriptor_proto_rawDesc), len(file_google_protobuf_descriptor_proto_rawDesc))) }) return file_google_protobuf_descriptor_proto_rawDescData } @@ -5292,7 +5293,7 @@ func file_google_protobuf_descriptor_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_descriptor_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_descriptor_proto_rawDesc), len(file_google_protobuf_descriptor_proto_rawDesc)), NumEnums: 17, NumMessages: 33, NumExtensions: 0, @@ -5304,7 +5305,6 @@ func file_google_protobuf_descriptor_proto_init() { MessageInfos: file_google_protobuf_descriptor_proto_msgTypes, }.Build() File_google_protobuf_descriptor_proto = out.File - file_google_protobuf_descriptor_proto_rawDesc = nil file_google_protobuf_descriptor_proto_goTypes = nil file_google_protobuf_descriptor_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/dynamicpb/types.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/dynamicpb/types.go index c432817bb9c..8e759fc9f72 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/dynamicpb/types.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/dynamicpb/types.go @@ -28,11 +28,7 @@ type extField struct { type Types struct { // atomicExtFiles is used with sync/atomic and hence must be the first word // of the struct to guarantee 64-bit alignment. - // - // TODO(stapelberg): once we only support Go 1.19 and newer, switch this - // field to be of type atomic.Uint64 to guarantee alignment on - // stack-allocated values, too. - atomicExtFiles uint64 + atomicExtFiles atomic.Uint64 extMu sync.Mutex files *protoregistry.Files @@ -90,7 +86,7 @@ func (t *Types) FindExtensionByName(name protoreflect.FullName) (protoreflect.Ex func (t *Types) FindExtensionByNumber(message protoreflect.FullName, field protoreflect.FieldNumber) (protoreflect.ExtensionType, error) { // Construct the extension number map lazily, since not every user will need it. // Update the map if new files are added to the registry. - if atomic.LoadUint64(&t.atomicExtFiles) != uint64(t.files.NumFiles()) { + if t.atomicExtFiles.Load() != uint64(t.files.NumFiles()) { t.updateExtensions() } xd := t.extensionsByMessage[extField{message, field}] @@ -133,10 +129,10 @@ func (t *Types) FindMessageByURL(url string) (protoreflect.MessageType, error) { func (t *Types) updateExtensions() { t.extMu.Lock() defer t.extMu.Unlock() - if atomic.LoadUint64(&t.atomicExtFiles) == uint64(t.files.NumFiles()) { + if t.atomicExtFiles.Load() == uint64(t.files.NumFiles()) { return } - defer atomic.StoreUint64(&t.atomicExtFiles, uint64(t.files.NumFiles())) + defer t.atomicExtFiles.Store(uint64(t.files.NumFiles())) t.files.RangeFiles(func(fd protoreflect.FileDescriptor) bool { t.registerExtensions(fd.Extensions()) t.registerExtensionsInMessages(fd.Messages()) diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/gofeaturespb/go_features.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/gofeaturespb/go_features.pb.go index e0b72eaf922..28d24bad79e 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/gofeaturespb/go_features.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/gofeaturespb/go_features.pb.go @@ -16,6 +16,7 @@ import ( descriptorpb "google.golang.org/protobuf/types/descriptorpb" reflect "reflect" sync "sync" + unsafe "unsafe" ) type GoFeatures_APILevel int32 @@ -227,7 +228,7 @@ var ( var File_google_protobuf_go_features_proto protoreflect.FileDescriptor -var file_google_protobuf_go_features_proto_rawDesc = []byte{ +var file_google_protobuf_go_features_proto_rawDesc = string([]byte{ 0x0a, 0x21, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x67, 0x6f, 0x5f, 0x66, 0x65, 0x61, 0x74, 0x75, 0x72, 0x65, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x02, 0x70, 0x62, 0x1a, 0x20, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, @@ -283,16 +284,16 @@ var file_google_protobuf_go_features_proto_rawDesc = []byte{ 0x67, 0x6f, 0x6c, 0x61, 0x6e, 0x67, 0x2e, 0x6f, 0x72, 0x67, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x74, 0x79, 0x70, 0x65, 0x73, 0x2f, 0x67, 0x6f, 0x66, 0x65, 0x61, 0x74, 0x75, 0x72, 0x65, 0x73, 0x70, 0x62, -} +}) var ( file_google_protobuf_go_features_proto_rawDescOnce sync.Once - file_google_protobuf_go_features_proto_rawDescData = file_google_protobuf_go_features_proto_rawDesc + file_google_protobuf_go_features_proto_rawDescData []byte ) func file_google_protobuf_go_features_proto_rawDescGZIP() []byte { file_google_protobuf_go_features_proto_rawDescOnce.Do(func() { - file_google_protobuf_go_features_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_go_features_proto_rawDescData) + file_google_protobuf_go_features_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_go_features_proto_rawDesc), len(file_google_protobuf_go_features_proto_rawDesc))) }) return file_google_protobuf_go_features_proto_rawDescData } @@ -326,7 +327,7 @@ func file_google_protobuf_go_features_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_go_features_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_go_features_proto_rawDesc), len(file_google_protobuf_go_features_proto_rawDesc)), NumEnums: 2, NumMessages: 1, NumExtensions: 1, @@ -339,7 +340,6 @@ func file_google_protobuf_go_features_proto_init() { ExtensionInfos: file_google_protobuf_go_features_proto_extTypes, }.Build() File_google_protobuf_go_features_proto = out.File - file_google_protobuf_go_features_proto_rawDesc = nil file_google_protobuf_go_features_proto_goTypes = nil file_google_protobuf_go_features_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/anypb/any.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/anypb/any.pb.go index 191552cce09..497da66e91f 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/anypb/any.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/anypb/any.pb.go @@ -122,6 +122,7 @@ import ( reflect "reflect" strings "strings" sync "sync" + unsafe "unsafe" ) // `Any` contains an arbitrary serialized protocol buffer message along with a @@ -411,7 +412,7 @@ func (x *Any) GetValue() []byte { var File_google_protobuf_any_proto protoreflect.FileDescriptor -var file_google_protobuf_any_proto_rawDesc = []byte{ +var file_google_protobuf_any_proto_rawDesc = string([]byte{ 0x0a, 0x19, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x61, 0x6e, 0x79, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x22, 0x36, 0x0a, 0x03, @@ -427,16 +428,16 @@ var file_google_protobuf_any_proto_rawDesc = []byte{ 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_any_proto_rawDescOnce sync.Once - file_google_protobuf_any_proto_rawDescData = file_google_protobuf_any_proto_rawDesc + file_google_protobuf_any_proto_rawDescData []byte ) func file_google_protobuf_any_proto_rawDescGZIP() []byte { file_google_protobuf_any_proto_rawDescOnce.Do(func() { - file_google_protobuf_any_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_any_proto_rawDescData) + file_google_protobuf_any_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_any_proto_rawDesc), len(file_google_protobuf_any_proto_rawDesc))) }) return file_google_protobuf_any_proto_rawDescData } @@ -462,7 +463,7 @@ func file_google_protobuf_any_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_any_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_any_proto_rawDesc), len(file_google_protobuf_any_proto_rawDesc)), NumEnums: 0, NumMessages: 1, NumExtensions: 0, @@ -473,7 +474,6 @@ func file_google_protobuf_any_proto_init() { MessageInfos: file_google_protobuf_any_proto_msgTypes, }.Build() File_google_protobuf_any_proto = out.File - file_google_protobuf_any_proto_rawDesc = nil file_google_protobuf_any_proto_goTypes = nil file_google_protobuf_any_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/durationpb/duration.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/durationpb/duration.pb.go index 34d76e6cd93..193880d1813 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/durationpb/duration.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/durationpb/duration.pb.go @@ -80,6 +80,7 @@ import ( reflect "reflect" sync "sync" time "time" + unsafe "unsafe" ) // A Duration represents a signed, fixed-length span of time represented @@ -288,7 +289,7 @@ func (x *Duration) GetNanos() int32 { var File_google_protobuf_duration_proto protoreflect.FileDescriptor -var file_google_protobuf_duration_proto_rawDesc = []byte{ +var file_google_protobuf_duration_proto_rawDesc = string([]byte{ 0x0a, 0x1e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x64, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, @@ -305,16 +306,16 @@ var file_google_protobuf_duration_proto_rawDesc = []byte{ 0x50, 0x42, 0xaa, 0x02, 0x1e, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_duration_proto_rawDescOnce sync.Once - file_google_protobuf_duration_proto_rawDescData = file_google_protobuf_duration_proto_rawDesc + file_google_protobuf_duration_proto_rawDescData []byte ) func file_google_protobuf_duration_proto_rawDescGZIP() []byte { file_google_protobuf_duration_proto_rawDescOnce.Do(func() { - file_google_protobuf_duration_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_duration_proto_rawDescData) + file_google_protobuf_duration_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_duration_proto_rawDesc), len(file_google_protobuf_duration_proto_rawDesc))) }) return file_google_protobuf_duration_proto_rawDescData } @@ -340,7 +341,7 @@ func file_google_protobuf_duration_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_duration_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_duration_proto_rawDesc), len(file_google_protobuf_duration_proto_rawDesc)), NumEnums: 0, NumMessages: 1, NumExtensions: 0, @@ -351,7 +352,6 @@ func file_google_protobuf_duration_proto_init() { MessageInfos: file_google_protobuf_duration_proto_msgTypes, }.Build() File_google_protobuf_duration_proto = out.File - file_google_protobuf_duration_proto_rawDesc = nil file_google_protobuf_duration_proto_goTypes = nil file_google_protobuf_duration_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go index 7fcdd382cc9..a5b8657c4ba 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/emptypb/empty.pb.go @@ -38,6 +38,7 @@ import ( protoimpl "google.golang.org/protobuf/runtime/protoimpl" reflect "reflect" sync "sync" + unsafe "unsafe" ) // A generic empty message that you can re-use to avoid defining duplicated @@ -85,7 +86,7 @@ func (*Empty) Descriptor() ([]byte, []int) { var File_google_protobuf_empty_proto protoreflect.FileDescriptor -var file_google_protobuf_empty_proto_rawDesc = []byte{ +var file_google_protobuf_empty_proto_rawDesc = string([]byte{ 0x0a, 0x1b, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x65, 0x6d, 0x70, 0x74, 0x79, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x22, 0x07, @@ -98,16 +99,16 @@ var file_google_protobuf_empty_proto_rawDesc = []byte{ 0x02, 0x03, 0x47, 0x50, 0x42, 0xaa, 0x02, 0x1e, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_empty_proto_rawDescOnce sync.Once - file_google_protobuf_empty_proto_rawDescData = file_google_protobuf_empty_proto_rawDesc + file_google_protobuf_empty_proto_rawDescData []byte ) func file_google_protobuf_empty_proto_rawDescGZIP() []byte { file_google_protobuf_empty_proto_rawDescOnce.Do(func() { - file_google_protobuf_empty_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_empty_proto_rawDescData) + file_google_protobuf_empty_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_empty_proto_rawDesc), len(file_google_protobuf_empty_proto_rawDesc))) }) return file_google_protobuf_empty_proto_rawDescData } @@ -133,7 +134,7 @@ func file_google_protobuf_empty_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_empty_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_empty_proto_rawDesc), len(file_google_protobuf_empty_proto_rawDesc)), NumEnums: 0, NumMessages: 1, NumExtensions: 0, @@ -144,7 +145,6 @@ func file_google_protobuf_empty_proto_init() { MessageInfos: file_google_protobuf_empty_proto_msgTypes, }.Build() File_google_protobuf_empty_proto = out.File - file_google_protobuf_empty_proto_rawDesc = nil file_google_protobuf_empty_proto_goTypes = nil file_google_protobuf_empty_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/fieldmaskpb/field_mask.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/fieldmaskpb/field_mask.pb.go index e5d7da38c20..041feb0f3ec 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/fieldmaskpb/field_mask.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/fieldmaskpb/field_mask.pb.go @@ -83,6 +83,7 @@ import ( sort "sort" strings "strings" sync "sync" + unsafe "unsafe" ) // `FieldMask` represents a set of symbolic field paths, for example: @@ -503,7 +504,7 @@ func (x *FieldMask) GetPaths() []string { var File_google_protobuf_field_mask_proto protoreflect.FileDescriptor -var file_google_protobuf_field_mask_proto_rawDesc = []byte{ +var file_google_protobuf_field_mask_proto_rawDesc = string([]byte{ 0x0a, 0x20, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x66, 0x69, 0x65, 0x6c, 0x64, 0x5f, 0x6d, 0x61, 0x73, 0x6b, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, @@ -519,16 +520,16 @@ var file_google_protobuf_field_mask_proto_rawDesc = []byte{ 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_field_mask_proto_rawDescOnce sync.Once - file_google_protobuf_field_mask_proto_rawDescData = file_google_protobuf_field_mask_proto_rawDesc + file_google_protobuf_field_mask_proto_rawDescData []byte ) func file_google_protobuf_field_mask_proto_rawDescGZIP() []byte { file_google_protobuf_field_mask_proto_rawDescOnce.Do(func() { - file_google_protobuf_field_mask_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_field_mask_proto_rawDescData) + file_google_protobuf_field_mask_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_field_mask_proto_rawDesc), len(file_google_protobuf_field_mask_proto_rawDesc))) }) return file_google_protobuf_field_mask_proto_rawDescData } @@ -554,7 +555,7 @@ func file_google_protobuf_field_mask_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_field_mask_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_field_mask_proto_rawDesc), len(file_google_protobuf_field_mask_proto_rawDesc)), NumEnums: 0, NumMessages: 1, NumExtensions: 0, @@ -565,7 +566,6 @@ func file_google_protobuf_field_mask_proto_init() { MessageInfos: file_google_protobuf_field_mask_proto_msgTypes, }.Build() File_google_protobuf_field_mask_proto = out.File - file_google_protobuf_field_mask_proto_rawDesc = nil file_google_protobuf_field_mask_proto_goTypes = nil file_google_protobuf_field_mask_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go index f2c53ea337c..ecdd31ab538 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/structpb/struct.pb.go @@ -128,6 +128,7 @@ import ( reflect "reflect" sync "sync" utf8 "unicode/utf8" + unsafe "unsafe" ) // `NullValue` is a singleton enumeration to represent the null value for the @@ -671,7 +672,7 @@ func (x *ListValue) GetValues() []*Value { var File_google_protobuf_struct_proto protoreflect.FileDescriptor -var file_google_protobuf_struct_proto_rawDesc = []byte{ +var file_google_protobuf_struct_proto_rawDesc = string([]byte{ 0x0a, 0x1c, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x73, 0x74, 0x72, 0x75, 0x63, 0x74, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x22, @@ -719,16 +720,16 @@ var file_google_protobuf_struct_proto_rawDesc = []byte{ 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_struct_proto_rawDescOnce sync.Once - file_google_protobuf_struct_proto_rawDescData = file_google_protobuf_struct_proto_rawDesc + file_google_protobuf_struct_proto_rawDescData []byte ) func file_google_protobuf_struct_proto_rawDescGZIP() []byte { file_google_protobuf_struct_proto_rawDescOnce.Do(func() { - file_google_protobuf_struct_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_struct_proto_rawDescData) + file_google_protobuf_struct_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_struct_proto_rawDesc), len(file_google_protobuf_struct_proto_rawDesc))) }) return file_google_protobuf_struct_proto_rawDescData } @@ -773,7 +774,7 @@ func file_google_protobuf_struct_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_struct_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_struct_proto_rawDesc), len(file_google_protobuf_struct_proto_rawDesc)), NumEnums: 1, NumMessages: 4, NumExtensions: 0, @@ -785,7 +786,6 @@ func file_google_protobuf_struct_proto_init() { MessageInfos: file_google_protobuf_struct_proto_msgTypes, }.Build() File_google_protobuf_struct_proto = out.File - file_google_protobuf_struct_proto_rawDesc = nil file_google_protobuf_struct_proto_goTypes = nil file_google_protobuf_struct_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/timestamppb/timestamp.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/timestamppb/timestamp.pb.go index 9550109aa3b..00ac835c0bb 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/timestamppb/timestamp.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/timestamppb/timestamp.pb.go @@ -78,6 +78,7 @@ import ( reflect "reflect" sync "sync" time "time" + unsafe "unsafe" ) // A Timestamp represents a point in time independent of any time zone or local @@ -297,7 +298,7 @@ func (x *Timestamp) GetNanos() int32 { var File_google_protobuf_timestamp_proto protoreflect.FileDescriptor -var file_google_protobuf_timestamp_proto_rawDesc = []byte{ +var file_google_protobuf_timestamp_proto_rawDesc = string([]byte{ 0x0a, 0x1f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x74, 0x69, 0x6d, 0x65, 0x73, 0x74, 0x61, 0x6d, 0x70, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, @@ -314,16 +315,16 @@ var file_google_protobuf_timestamp_proto_rawDesc = []byte{ 0xa2, 0x02, 0x03, 0x47, 0x50, 0x42, 0xaa, 0x02, 0x1e, 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_timestamp_proto_rawDescOnce sync.Once - file_google_protobuf_timestamp_proto_rawDescData = file_google_protobuf_timestamp_proto_rawDesc + file_google_protobuf_timestamp_proto_rawDescData []byte ) func file_google_protobuf_timestamp_proto_rawDescGZIP() []byte { file_google_protobuf_timestamp_proto_rawDescOnce.Do(func() { - file_google_protobuf_timestamp_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_timestamp_proto_rawDescData) + file_google_protobuf_timestamp_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_timestamp_proto_rawDesc), len(file_google_protobuf_timestamp_proto_rawDesc))) }) return file_google_protobuf_timestamp_proto_rawDescData } @@ -349,7 +350,7 @@ func file_google_protobuf_timestamp_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_timestamp_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_timestamp_proto_rawDesc), len(file_google_protobuf_timestamp_proto_rawDesc)), NumEnums: 0, NumMessages: 1, NumExtensions: 0, @@ -360,7 +361,6 @@ func file_google_protobuf_timestamp_proto_init() { MessageInfos: file_google_protobuf_timestamp_proto_msgTypes, }.Build() File_google_protobuf_timestamp_proto = out.File - file_google_protobuf_timestamp_proto_rawDesc = nil file_google_protobuf_timestamp_proto_goTypes = nil file_google_protobuf_timestamp_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/wrapperspb/wrappers.pb.go b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/wrapperspb/wrappers.pb.go index 15b424ec12c..5de5301063b 100644 --- a/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/wrapperspb/wrappers.pb.go +++ b/cluster-api/providers/vsphere/vendor/google.golang.org/protobuf/types/known/wrapperspb/wrappers.pb.go @@ -48,6 +48,7 @@ import ( protoimpl "google.golang.org/protobuf/runtime/protoimpl" reflect "reflect" sync "sync" + unsafe "unsafe" ) // Wrapper message for `double`. @@ -529,7 +530,7 @@ func (x *BytesValue) GetValue() []byte { var File_google_protobuf_wrappers_proto protoreflect.FileDescriptor -var file_google_protobuf_wrappers_proto_rawDesc = []byte{ +var file_google_protobuf_wrappers_proto_rawDesc = string([]byte{ 0x0a, 0x1e, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2f, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2f, 0x77, 0x72, 0x61, 0x70, 0x70, 0x65, 0x72, 0x73, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x0f, 0x67, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, @@ -563,16 +564,16 @@ var file_google_protobuf_wrappers_proto_rawDesc = []byte{ 0x47, 0x6f, 0x6f, 0x67, 0x6c, 0x65, 0x2e, 0x50, 0x72, 0x6f, 0x74, 0x6f, 0x62, 0x75, 0x66, 0x2e, 0x57, 0x65, 0x6c, 0x6c, 0x4b, 0x6e, 0x6f, 0x77, 0x6e, 0x54, 0x79, 0x70, 0x65, 0x73, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} +}) var ( file_google_protobuf_wrappers_proto_rawDescOnce sync.Once - file_google_protobuf_wrappers_proto_rawDescData = file_google_protobuf_wrappers_proto_rawDesc + file_google_protobuf_wrappers_proto_rawDescData []byte ) func file_google_protobuf_wrappers_proto_rawDescGZIP() []byte { file_google_protobuf_wrappers_proto_rawDescOnce.Do(func() { - file_google_protobuf_wrappers_proto_rawDescData = protoimpl.X.CompressGZIP(file_google_protobuf_wrappers_proto_rawDescData) + file_google_protobuf_wrappers_proto_rawDescData = protoimpl.X.CompressGZIP(unsafe.Slice(unsafe.StringData(file_google_protobuf_wrappers_proto_rawDesc), len(file_google_protobuf_wrappers_proto_rawDesc))) }) return file_google_protobuf_wrappers_proto_rawDescData } @@ -606,7 +607,7 @@ func file_google_protobuf_wrappers_proto_init() { out := protoimpl.TypeBuilder{ File: protoimpl.DescBuilder{ GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_google_protobuf_wrappers_proto_rawDesc, + RawDescriptor: unsafe.Slice(unsafe.StringData(file_google_protobuf_wrappers_proto_rawDesc), len(file_google_protobuf_wrappers_proto_rawDesc)), NumEnums: 0, NumMessages: 9, NumExtensions: 0, @@ -617,7 +618,6 @@ func file_google_protobuf_wrappers_proto_init() { MessageInfos: file_google_protobuf_wrappers_proto_msgTypes, }.Build() File_google_protobuf_wrappers_proto = out.File - file_google_protobuf_wrappers_proto_rawDesc = nil file_google_protobuf_wrappers_proto_goTypes = nil file_google_protobuf_wrappers_proto_depIdxs = nil } diff --git a/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1alpha3/types.go b/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1alpha3/types.go index fb4d7041dbd..49d7c86de31 100644 --- a/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1alpha3/types.go +++ b/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1alpha3/types.go @@ -145,6 +145,10 @@ type ResourceSliceSpec struct { Devices []Device `json:"devices" protobuf:"bytes,6,name=devices"` } +// DriverNameMaxLength is the maximum valid length of a driver name in the +// ResourceSliceSpec and other places. It's the same as for CSI driver names. +const DriverNameMaxLength = 63 + // ResourcePool describes the pool that ResourceSlices belong to. type ResourcePool struct { // Name is used to identify the pool. For node-local devices, this diff --git a/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1beta1/types.go b/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1beta1/types.go index ca79c5a6640..fbdc35ca86b 100644 --- a/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1beta1/types.go +++ b/cluster-api/providers/vsphere/vendor/k8s.io/api/resource/v1beta1/types.go @@ -144,6 +144,10 @@ type ResourceSliceSpec struct { Devices []Device `json:"devices" protobuf:"bytes,6,name=devices"` } +// DriverNameMaxLength is the maximum valid length of a driver name in the +// ResourceSliceSpec and other places. It's the same as for CSI driver names. +const DriverNameMaxLength = 63 + // ResourcePool describes the pool that ResourceSlices belong to. type ResourcePool struct { // Name is used to identify the pool. For node-local devices, this diff --git a/cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/OWNERS b/cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/OWNERS new file mode 100644 index 00000000000..75736b5aace --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/OWNERS @@ -0,0 +1,4 @@ +# See the OWNERS docs at https://go.k8s.io/owners + +reviewers: + - caesarxuchao diff --git a/cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/util.go b/cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/util.go new file mode 100644 index 00000000000..0c6e504a6dc --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/k8s.io/client-go/util/retry/util.go @@ -0,0 +1,105 @@ +/* +Copyright 2016 The Kubernetes Authors. + +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 retry + +import ( + "time" + + "k8s.io/apimachinery/pkg/api/errors" + "k8s.io/apimachinery/pkg/util/wait" +) + +// DefaultRetry is the recommended retry for a conflict where multiple clients +// are making changes to the same resource. +var DefaultRetry = wait.Backoff{ + Steps: 5, + Duration: 10 * time.Millisecond, + Factor: 1.0, + Jitter: 0.1, +} + +// DefaultBackoff is the recommended backoff for a conflict where a client +// may be attempting to make an unrelated modification to a resource under +// active management by one or more controllers. +var DefaultBackoff = wait.Backoff{ + Steps: 4, + Duration: 10 * time.Millisecond, + Factor: 5.0, + Jitter: 0.1, +} + +// OnError allows the caller to retry fn in case the error returned by fn is retriable +// according to the provided function. backoff defines the maximum retries and the wait +// interval between two retries. +func OnError(backoff wait.Backoff, retriable func(error) bool, fn func() error) error { + var lastErr error + err := wait.ExponentialBackoff(backoff, func() (bool, error) { + err := fn() + switch { + case err == nil: + return true, nil + case retriable(err): + lastErr = err + return false, nil + default: + return false, err + } + }) + if err == wait.ErrWaitTimeout { + err = lastErr + } + return err +} + +// RetryOnConflict is used to make an update to a resource when you have to worry about +// conflicts caused by other code making unrelated updates to the resource at the same +// time. fn should fetch the resource to be modified, make appropriate changes to it, try +// to update it, and return (unmodified) the error from the update function. On a +// successful update, RetryOnConflict will return nil. If the update function returns a +// "Conflict" error, RetryOnConflict will wait some amount of time as described by +// backoff, and then try again. On a non-"Conflict" error, or if it retries too many times +// and gives up, RetryOnConflict will return an error to the caller. +// +// err := retry.RetryOnConflict(retry.DefaultRetry, func() error { +// // Fetch the resource here; you need to refetch it on every try, since +// // if you got a conflict on the last update attempt then you need to get +// // the current version before making your own changes. +// pod, err := c.Pods("mynamespace").Get(name, metav1.GetOptions{}) +// if err != nil { +// return err +// } +// +// // Make whatever updates to the resource are needed +// pod.Status.Phase = v1.PodFailed +// +// // Try to update +// _, err = c.Pods("mynamespace").UpdateStatus(pod) +// // You have to return err itself here (not wrapped inside another error) +// // so that RetryOnConflict can identify it correctly. +// return err +// }) +// if err != nil { +// // May be conflict if max retries were hit, or may be something unrelated +// // like permissions or a network error +// return err +// } +// ... +// +// TODO: Make Backoff an interface? +func RetryOnConflict(backoff wait.Backoff, fn func() error) error { + return OnError(backoff, errors.IsConflict, fn) +} diff --git a/cluster-api/providers/vsphere/vendor/modules.txt b/cluster-api/providers/vsphere/vendor/modules.txt index 56c8fd93fc0..8aeb60cf5d1 100644 --- a/cluster-api/providers/vsphere/vendor/modules.txt +++ b/cluster-api/providers/vsphere/vendor/modules.txt @@ -7,8 +7,8 @@ github.com/NYTimes/gziphandler # github.com/antlr4-go/antlr/v4 v4.13.0 ## explicit; go 1.20 github.com/antlr4-go/antlr/v4 -# github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 -## explicit; go 1.13 +# github.com/asaskevich/govalidator v0.0.0-20190424111038-f61b66f89f4a +## explicit github.com/asaskevich/govalidator # github.com/beorn7/perks v1.0.1 ## explicit; go 1.11 @@ -28,20 +28,21 @@ github.com/cespare/xxhash/v2 # github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc ## explicit github.com/davecgh/go-spew/spew -# github.com/emicklei/go-restful/v3 v3.12.1 +# github.com/emicklei/go-restful/v3 v3.12.2 ## explicit; go 1.13 github.com/emicklei/go-restful/v3 github.com/emicklei/go-restful/v3/log -# github.com/evanphx/json-patch/v5 v5.9.0 +# github.com/evanphx/json-patch/v5 v5.9.11 ## explicit; go 1.18 github.com/evanphx/json-patch/v5 github.com/evanphx/json-patch/v5/internal/json # github.com/felixge/httpsnoop v1.0.4 ## explicit; go 1.13 github.com/felixge/httpsnoop -# github.com/fsnotify/fsnotify v1.7.0 +# github.com/fsnotify/fsnotify v1.8.0 ## explicit; go 1.17 github.com/fsnotify/fsnotify +github.com/fsnotify/fsnotify/internal # github.com/fxamacker/cbor/v2 v2.7.0 ## explicit; go 1.17 github.com/fxamacker/cbor/v2 @@ -117,8 +118,8 @@ github.com/google/gnostic-models/extensions github.com/google/gnostic-models/jsonschema github.com/google/gnostic-models/openapiv2 github.com/google/gnostic-models/openapiv3 -# github.com/google/go-cmp v0.6.0 -## explicit; go 1.13 +# github.com/google/go-cmp v0.7.0 +## explicit; go 1.21 github.com/google/go-cmp/cmp github.com/google/go-cmp/cmp/internal/diff github.com/google/go-cmp/cmp/internal/flags @@ -159,8 +160,8 @@ github.com/modern-go/reflect2 # github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 ## explicit github.com/munnerz/goautoneg -# github.com/onsi/gomega v1.36.2 -## explicit; go 1.22.0 +# github.com/onsi/gomega v1.37.0 +## explicit; go 1.23.0 github.com/onsi/gomega github.com/onsi/gomega/format github.com/onsi/gomega/internal @@ -196,10 +197,10 @@ github.com/prometheus/common/model github.com/prometheus/procfs github.com/prometheus/procfs/internal/fs github.com/prometheus/procfs/internal/util -# github.com/spf13/cobra v1.8.1 +# github.com/spf13/cobra v1.9.1 ## explicit; go 1.15 github.com/spf13/cobra -# github.com/spf13/pflag v1.0.5 +# github.com/spf13/pflag v1.0.6 ## explicit; go 1.12 github.com/spf13/pflag # github.com/stoewer/go-strcase v1.3.0 @@ -208,7 +209,7 @@ github.com/stoewer/go-strcase # github.com/vmware-tanzu/net-operator-api v0.0.0-20240326163340-1f32d6bf7f9d ## explicit; go 1.19 github.com/vmware-tanzu/net-operator-api/api/v1alpha1 -# github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20241112044858-9da8637c1b0d => github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20240827061921-8f0982975508 +# github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20241112044858-9da8637c1b0d ## explicit; go 1.21 github.com/vmware-tanzu/nsx-operator/pkg/apis/vpc/v1alpha1 # github.com/vmware-tanzu/vm-operator/api v1.8.6 @@ -220,8 +221,8 @@ github.com/vmware-tanzu/vm-operator/api/v1alpha2/sysprep # github.com/vmware-tanzu/vm-operator/external/ncp v0.0.0-20240404200847-de75746a9505 ## explicit; go 1.13 github.com/vmware-tanzu/vm-operator/external/ncp/api/v1alpha1 -# github.com/vmware/govmomi v0.47.1 -## explicit; go 1.21 +# github.com/vmware/govmomi v0.49.0 +## explicit; go 1.23.0 github.com/vmware/govmomi github.com/vmware/govmomi/fault github.com/vmware/govmomi/find @@ -256,12 +257,13 @@ github.com/vmware/govmomi/vim25/xml # github.com/x448/float16 v0.8.4 ## explicit; go 1.11 github.com/x448/float16 -# go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.53.0 +# go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.54.0 ## explicit; go 1.21 go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp +go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/request go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconv go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp/internal/semconvutil -# go.opentelemetry.io/otel v1.28.0 +# go.opentelemetry.io/otel v1.29.0 ## explicit; go 1.21 go.opentelemetry.io/otel go.opentelemetry.io/otel/attribute @@ -274,7 +276,6 @@ go.opentelemetry.io/otel/internal/global go.opentelemetry.io/otel/propagation go.opentelemetry.io/otel/semconv/v1.17.0 go.opentelemetry.io/otel/semconv/v1.20.0 -go.opentelemetry.io/otel/semconv/v1.24.0 go.opentelemetry.io/otel/semconv/v1.26.0 # go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.28.0 ## explicit; go 1.21 @@ -287,11 +288,12 @@ go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc/internal go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc/internal/envconfig go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc/internal/otlpconfig go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc/internal/retry -# go.opentelemetry.io/otel/metric v1.28.0 +# go.opentelemetry.io/otel/metric v1.29.0 ## explicit; go 1.21 go.opentelemetry.io/otel/metric go.opentelemetry.io/otel/metric/embedded -# go.opentelemetry.io/otel/sdk v1.28.0 +go.opentelemetry.io/otel/metric/noop +# go.opentelemetry.io/otel/sdk v1.29.0 ## explicit; go 1.21 go.opentelemetry.io/otel/sdk go.opentelemetry.io/otel/sdk/instrumentation @@ -299,7 +301,7 @@ go.opentelemetry.io/otel/sdk/internal/env go.opentelemetry.io/otel/sdk/internal/x go.opentelemetry.io/otel/sdk/resource go.opentelemetry.io/otel/sdk/trace -# go.opentelemetry.io/otel/trace v1.28.0 +# go.opentelemetry.io/otel/trace v1.29.0 ## explicit; go 1.21 go.opentelemetry.io/otel/trace go.opentelemetry.io/otel/trace/embedded @@ -328,8 +330,8 @@ go.uber.org/zap/zapcore ## explicit; go 1.20 golang.org/x/exp/constraints golang.org/x/exp/slices -# golang.org/x/net v0.34.0 -## explicit; go 1.18 +# golang.org/x/net v0.38.0 +## explicit; go 1.23.0 golang.org/x/net/html golang.org/x/net/html/atom golang.org/x/net/html/charset @@ -337,28 +339,29 @@ golang.org/x/net/http/httpguts golang.org/x/net/http2 golang.org/x/net/http2/hpack golang.org/x/net/idna +golang.org/x/net/internal/httpcommon golang.org/x/net/internal/timeseries golang.org/x/net/trace golang.org/x/net/websocket -# golang.org/x/oauth2 v0.25.0 -## explicit; go 1.18 +# golang.org/x/oauth2 v0.28.0 +## explicit; go 1.23.0 golang.org/x/oauth2 golang.org/x/oauth2/internal -# golang.org/x/sync v0.10.0 -## explicit; go 1.18 +# golang.org/x/sync v0.12.0 +## explicit; go 1.23.0 golang.org/x/sync/errgroup golang.org/x/sync/singleflight -# golang.org/x/sys v0.29.0 -## explicit; go 1.18 +# golang.org/x/sys v0.32.0 +## explicit; go 1.23.0 golang.org/x/sys/plan9 golang.org/x/sys/unix golang.org/x/sys/windows golang.org/x/sys/windows/registry -# golang.org/x/term v0.28.0 -## explicit; go 1.18 +# golang.org/x/term v0.30.0 +## explicit; go 1.23.0 golang.org/x/term -# golang.org/x/text v0.21.0 -## explicit; go 1.18 +# golang.org/x/text v0.23.0 +## explicit; go 1.23.0 golang.org/x/text/encoding golang.org/x/text/encoding/charmap golang.org/x/text/encoding/htmlindex @@ -387,21 +390,21 @@ golang.org/x/text/secure/bidirule golang.org/x/text/transform golang.org/x/text/unicode/bidi golang.org/x/text/unicode/norm -# golang.org/x/time v0.7.0 +# golang.org/x/time v0.8.0 ## explicit; go 1.18 golang.org/x/time/rate -# gomodules.xyz/jsonpatch/v2 v2.4.0 +# gomodules.xyz/jsonpatch/v2 v2.5.0 ## explicit; go 1.20 gomodules.xyz/jsonpatch/v2 -# google.golang.org/genproto/googleapis/api v0.0.0-20240826202546-f6391c0de4c7 +# google.golang.org/genproto/googleapis/api v0.0.0-20241209162323-e6fa225c2576 ## explicit; go 1.21 google.golang.org/genproto/googleapis/api/expr/v1alpha1 google.golang.org/genproto/googleapis/api/httpbody -# google.golang.org/genproto/googleapis/rpc v0.0.0-20240826202546-f6391c0de4c7 +# google.golang.org/genproto/googleapis/rpc v0.0.0-20241223144023-3abc09e42ca8 ## explicit; go 1.21 google.golang.org/genproto/googleapis/rpc/errdetails google.golang.org/genproto/googleapis/rpc/status -# google.golang.org/grpc v1.65.1 +# google.golang.org/grpc v1.67.3 ## explicit; go 1.21 google.golang.org/grpc google.golang.org/grpc/attributes @@ -420,7 +423,9 @@ google.golang.org/grpc/credentials/insecure google.golang.org/grpc/encoding google.golang.org/grpc/encoding/gzip google.golang.org/grpc/encoding/proto +google.golang.org/grpc/experimental/stats google.golang.org/grpc/grpclog +google.golang.org/grpc/grpclog/internal google.golang.org/grpc/health/grpc_health_v1 google.golang.org/grpc/internal google.golang.org/grpc/internal/backoff @@ -443,11 +448,13 @@ google.golang.org/grpc/internal/resolver/dns/internal google.golang.org/grpc/internal/resolver/passthrough google.golang.org/grpc/internal/resolver/unix google.golang.org/grpc/internal/serviceconfig +google.golang.org/grpc/internal/stats google.golang.org/grpc/internal/status google.golang.org/grpc/internal/syscall google.golang.org/grpc/internal/transport google.golang.org/grpc/internal/transport/networktype google.golang.org/grpc/keepalive +google.golang.org/grpc/mem google.golang.org/grpc/metadata google.golang.org/grpc/peer google.golang.org/grpc/resolver @@ -456,7 +463,7 @@ google.golang.org/grpc/serviceconfig google.golang.org/grpc/stats google.golang.org/grpc/status google.golang.org/grpc/tap -# google.golang.org/protobuf v1.36.1 +# google.golang.org/protobuf v1.36.5 ## explicit; go 1.21 google.golang.org/protobuf/encoding/protodelim google.golang.org/protobuf/encoding/protojson @@ -522,7 +529,7 @@ gopkg.in/warnings.v0 # gopkg.in/yaml.v3 v3.0.1 ## explicit gopkg.in/yaml.v3 -# k8s.io/api v0.32.1 +# k8s.io/api v0.32.3 ## explicit; go 1.23.0 k8s.io/api/admission/v1 k8s.io/api/admission/v1beta1 @@ -582,11 +589,11 @@ k8s.io/api/storage/v1 k8s.io/api/storage/v1alpha1 k8s.io/api/storage/v1beta1 k8s.io/api/storagemigration/v1alpha1 -# k8s.io/apiextensions-apiserver v0.32.1 +# k8s.io/apiextensions-apiserver v0.32.3 ## explicit; go 1.23.0 k8s.io/apiextensions-apiserver/pkg/apis/apiextensions k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1 -# k8s.io/apimachinery v0.32.1 +# k8s.io/apimachinery v0.32.3 ## explicit; go 1.23.0 k8s.io/apimachinery/pkg/api/apitesting k8s.io/apimachinery/pkg/api/apitesting/fuzzer @@ -652,7 +659,7 @@ k8s.io/apimachinery/pkg/version k8s.io/apimachinery/pkg/watch k8s.io/apimachinery/third_party/forked/golang/json k8s.io/apimachinery/third_party/forked/golang/reflect -# k8s.io/apiserver v0.32.1 +# k8s.io/apiserver v0.32.3 ## explicit; go 1.23.0 k8s.io/apiserver/pkg/admission k8s.io/apiserver/pkg/apis/apiserver @@ -712,7 +719,7 @@ k8s.io/apiserver/pkg/warning k8s.io/apiserver/plugin/pkg/authenticator/token/webhook k8s.io/apiserver/plugin/pkg/authorizer/webhook k8s.io/apiserver/plugin/pkg/authorizer/webhook/metrics -# k8s.io/client-go v0.32.1 +# k8s.io/client-go v0.32.3 ## explicit; go 1.23.0 k8s.io/client-go/applyconfigurations/admissionregistration/v1 k8s.io/client-go/applyconfigurations/admissionregistration/v1alpha1 @@ -982,13 +989,14 @@ k8s.io/client-go/util/consistencydetector k8s.io/client-go/util/flowcontrol k8s.io/client-go/util/homedir k8s.io/client-go/util/keyutil +k8s.io/client-go/util/retry k8s.io/client-go/util/watchlist k8s.io/client-go/util/workqueue -# k8s.io/cluster-bootstrap v0.32.1 +# k8s.io/cluster-bootstrap v0.32.3 ## explicit; go 1.23.0 k8s.io/cluster-bootstrap/token/api k8s.io/cluster-bootstrap/token/util -# k8s.io/component-base v0.32.1 +# k8s.io/component-base v0.32.3 ## explicit; go 1.23.0 k8s.io/component-base/cli/flag k8s.io/component-base/featuregate @@ -1057,12 +1065,13 @@ sigs.k8s.io/apiserver-network-proxy/konnectivity-client/pkg/client sigs.k8s.io/apiserver-network-proxy/konnectivity-client/pkg/client/metrics sigs.k8s.io/apiserver-network-proxy/konnectivity-client/pkg/common/metrics sigs.k8s.io/apiserver-network-proxy/konnectivity-client/proto/client -# sigs.k8s.io/cluster-api v0.0.0-00010101000000-000000000000 => sigs.k8s.io/cluster-api v1.9.1 -## explicit; go 1.22.0 +# sigs.k8s.io/cluster-api v0.0.0-00010101000000-000000000000 => sigs.k8s.io/cluster-api v1.10.1 +## explicit; go 1.23.0 sigs.k8s.io/cluster-api/api/v1beta1 sigs.k8s.io/cluster-api/api/v1beta1/index sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1 sigs.k8s.io/cluster-api/controllers/clustercache +sigs.k8s.io/cluster-api/controllers/crdmigrator sigs.k8s.io/cluster-api/controllers/remote sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1 sigs.k8s.io/cluster-api/errors @@ -1072,24 +1081,27 @@ sigs.k8s.io/cluster-api/feature sigs.k8s.io/cluster-api/util sigs.k8s.io/cluster-api/util/annotations sigs.k8s.io/cluster-api/util/apiwarnings +sigs.k8s.io/cluster-api/util/cache sigs.k8s.io/cluster-api/util/certs sigs.k8s.io/cluster-api/util/collections sigs.k8s.io/cluster-api/util/conditions sigs.k8s.io/cluster-api/util/conditions/v1beta2 sigs.k8s.io/cluster-api/util/contract sigs.k8s.io/cluster-api/util/conversion +sigs.k8s.io/cluster-api/util/finalizers sigs.k8s.io/cluster-api/util/flags sigs.k8s.io/cluster-api/util/kubeconfig sigs.k8s.io/cluster-api/util/labels sigs.k8s.io/cluster-api/util/labels/format sigs.k8s.io/cluster-api/util/log sigs.k8s.io/cluster-api/util/patch +sigs.k8s.io/cluster-api/util/paused sigs.k8s.io/cluster-api/util/predicates sigs.k8s.io/cluster-api/util/secret sigs.k8s.io/cluster-api/util/topology sigs.k8s.io/cluster-api/util/version sigs.k8s.io/cluster-api/version -# sigs.k8s.io/cluster-api-provider-vsphere v1.12.0-rc.0.0.20250203113257-38f6b67f9b7d +# sigs.k8s.io/cluster-api-provider-vsphere v1.13.1 ## explicit; go 1.23.0 sigs.k8s.io/cluster-api-provider-vsphere sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3 @@ -1126,7 +1138,9 @@ sigs.k8s.io/cluster-api-provider-vsphere/pkg/session sigs.k8s.io/cluster-api-provider-vsphere/pkg/taggable sigs.k8s.io/cluster-api-provider-vsphere/pkg/util sigs.k8s.io/cluster-api-provider-vsphere/pkg/version -# sigs.k8s.io/controller-runtime v0.20.1 +sigs.k8s.io/cluster-api-provider-vsphere/webhooks +sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware +# sigs.k8s.io/controller-runtime v0.20.4 ## explicit; go 1.23.0 sigs.k8s.io/controller-runtime sigs.k8s.io/controller-runtime/pkg/builder @@ -1190,6 +1204,5 @@ sigs.k8s.io/structured-merge-diff/v4/value ## explicit; go 1.12 sigs.k8s.io/yaml sigs.k8s.io/yaml/goyaml.v2 -# sigs.k8s.io/cluster-api => sigs.k8s.io/cluster-api v1.9.1 +# sigs.k8s.io/cluster-api => sigs.k8s.io/cluster-api v1.10.1 # github.com/vmware-tanzu/vm-operator/pkg/constants/testlabels => github.com/vmware-tanzu/vm-operator/pkg/constants/testlabels v0.0.0-20240404200847-de75746a9505 -# github.com/vmware-tanzu/nsx-operator/pkg/apis => github.com/vmware-tanzu/nsx-operator/pkg/apis v0.0.0-20240827061921-8f0982975508 diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/.golangci.yml b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/.golangci.yml index c22845804df..c742366a1ab 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/.golangci.yml +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/.golangci.yml @@ -1,11 +1,6 @@ run: timeout: 10m go: "1.23" - skip-files: - - "zz_generated.*\\.go$" - - "_conversion\\.go$" - - "vendored_cluster_api\\.go$" - - "^internal/apis/topology/v1alpha1" allow-parallel-runners: true linters: @@ -143,14 +138,13 @@ linters-settings: - pkg: sigs.k8s.io/cluster-api/exp/api/v1beta1 alias: expv1 # CAPI exp addons - - pkg: sigs.k8s.io/cluster-api/exp/addons/api/v1beta1 + - pkg: sigs.k8s.io/cluster-api/api/addons/v1beta1 alias: addonsv1 # CAPI IPAM - pkg: sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1 alias: ipamv1 nolintlint: allow-unused: false - allow-leading-space: false require-specific: true revive: rules: @@ -196,6 +190,11 @@ issues: # We are disabling default golangci exclusions because we want to help reviewers to focus on reviewing the most relevant # changes in PRs and avoid nitpicking. exclude-use-default: false + exclude-files: + - "zz_generated.*\\.go$" + - "_conversion\\.go$" + - "vendored_cluster_api\\.go$" + - "^internal/apis/topology/v1alpha1" exclude-rules: # Specific exclude rules for deprecated items that are still part of the codebase. These # should be removed as the referenced deprecated item is removed from the project. @@ -215,10 +214,6 @@ issues: - linters: - staticcheck text: "SA1019: \"sigs.k8s.io/cluster-api-provider-vsphere/apis/(v1alpha3|v1alpha4)\" is deprecated: This package will be removed in one of the next releases." - # Deprecations for Cluster API's predicates.ClusterUnpausedAndInfrastructureReady - - linters: - - staticcheck - text: "SA1019: predicates.ClusterUnpausedAndInfrastructureReady is deprecated: This predicate is deprecated and will be removed in a future version, use ClusterPausedTransitionsOrInfrastructureReady instead." - linters: - revive text: "exported: exported method .*\\.(Reconcile|SetupWithManager|SetupWebhookWithManager) should have comment or be unexported" diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/Makefile b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/Makefile index 29f2cadd4f3..8168da1c0ec 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/Makefile +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/Makefile @@ -23,8 +23,8 @@ SHELL:=/usr/bin/env bash # # Go. # -GO_VERSION ?= 1.23.5 -GO_DIRECTIVE_VERSION ?= 1.23.5 +GO_VERSION ?= 1.23.10 +GO_DIRECTIVE_VERSION ?= 1.23.0 GO_CONTAINER_IMAGE ?= docker.io/library/golang:$(GO_VERSION) # Ensure correct toolchain is used @@ -79,8 +79,12 @@ export PATH := $(abspath $(TOOLS_BIN_DIR)):$(PATH) # GINKGO_FOCUS ?= GINKGO_SKIP ?= +GINKGO_LABEL_FILTER ?= GINKGO_NODES ?= 1 GINKGO_TIMEOUT ?= 3h +GINKGO_ARGS ?= +GINKGO_POLL_PROGRESS_AFTER ?= 60m +GINKGO_POLL_PROGRESS_INTERVAL ?= 5m E2E_CONF_FILE ?= $(abspath test/e2e/config/vsphere.yaml) E2E_CONF_OVERRIDE_FILE ?= $(abspath test/e2e/config/config-overrides.yaml) E2E_VSPHERE_IP_POOL ?= @@ -186,7 +190,7 @@ IMPORT_BOSS_VER := v0.28.1 IMPORT_BOSS := $(abspath $(TOOLS_BIN_DIR)/$(IMPORT_BOSS_BIN)) IMPORT_BOSS_PKG := k8s.io/code-generator/cmd/import-boss -CAPI_HACK_TOOLS_VER := b04c79ca02d3bed23c84115e5c42fa3de1a163dc # Note: this is the commit ID of CAPI v1.9.1 +CAPI_HACK_TOOLS_VER := 647a1b741bc86dd759583a44b50a3ba8dbd326c4 # Note: this the commit ID of CAPI v1.10.1 BOSKOSCTL_BIN := boskosctl BOSKOSCTL := $(abspath $(TOOLS_BIN_DIR)/$(BOSKOSCTL_BIN)) @@ -280,6 +284,7 @@ NETOP_RBAC_ROOT ?= $(NETOP_DIR)/config/rbac TEST_EXTENSION_RBAC_ROOT ?= $(TEST_EXTENSION_DIR)/config/rbac JANITOR_DIR ?= ./$(TOOLS_DIR)/janitor +JANITOR_ARGS ?= --resource-type=gcve-vsphere-project help: # Display this help @awk 'BEGIN {FS = ":.*##"; printf "\nUsage:\n make \033[36m\033[0m\n"} /^[0-9A-Za-z_-]+:.*?##/ { printf " \033[36m%-50s\033[0m %s\n", $$1, $$2 } /^\$$\([0-9A-Za-z_-]+\):.*?##/ { gsub("_","-", $$1); printf " \033[36m%-50s\033[0m %s\n", tolower(substr($$1, 3, length($$1)-7)), $$2 } /^##@/ { printf "\n\033[1m%s\033[0m\n", substr($$0, 5) } ' $(MAKEFILE_LIST) @@ -444,18 +449,11 @@ generate-e2e-templates-v1.10: $(KUSTOMIZE) .PHONY: generate-test-infra-prowjobs generate-test-infra-prowjobs: $(PROWJOB_GEN) ## Generates the prowjob configurations in test-infra @if [ -z "${TEST_INFRA_DIR}" ]; then echo "TEST_INFRA_DIR is not set"; exit 1; fi - mkdir -p "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/downstream" $(PROWJOB_GEN) \ -config "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/cluster-api-provider-vsphere-prowjob-gen.yaml" \ -templates-dir "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/templates" \ - -output-dir "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/downstream" - @for f in "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/downstream/"*periodics*; do \ - cat "$${f}" | yq '.periodics |= map(select(.cluster != null))' > "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/$$(basename $${f})"; \ - cat "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/$$(basename $${f})" | grep -q 'periodics: \[\]' && rm "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/$$(basename $${f})" || true; \ - done - @for f in "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/downstream/"*presubmits*; do \ - cat "$${f}" | yq '.presubmits."kubernetes-sigs/cluster-api-provider-vsphere" |= map(select(.cluster != null))' > "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere/$$(basename $${f})";\ - done + -output-dir "$(TEST_INFRA_DIR)/config/jobs/kubernetes-sigs/cluster-api-provider-vsphere" + ## -------------------------------------- ## Lint / Verify ## -------------------------------------- @@ -698,11 +696,16 @@ e2e: $(GINKGO) $(KUSTOMIZE) $(KIND) $(GOVC) ## Run e2e tests @echo Contents of $(TOOLS_BIN_DIR): @ls $(TOOLS_BIN_DIR) @echo - time $(GINKGO) -v --trace -focus="$(GINKGO_FOCUS)" $(_SKIP_ARGS) --nodes=$(GINKGO_NODES) -timeout=$(GINKGO_TIMEOUT) \ - --output-dir="$(ARTIFACTS)" --junit-report="junit.e2e_suite.1.xml" ./test/e2e -- \ + time $(GINKGO) -v --trace \ + --nodes=$(GINKGO_NODES) --timeout=$(GINKGO_TIMEOUT) \ + --label-filter="$(GINKGO_LABEL_FILTER)" --focus="$(GINKGO_FOCUS)" $(_SKIP_ARGS) \ + --poll-progress-after=$(GINKGO_POLL_PROGRESS_AFTER) --poll-progress-interval=$(GINKGO_POLL_PROGRESS_INTERVAL) \ + --fail-on-pending --fail-on-empty \ + --no-color=$(GINKGO_NOCOLOR) --output-dir="$(ARTIFACTS)" --junit-report="junit.e2e_suite.1.xml" \ + $(GINKGO_ARGS) ./test/e2e -- \ + --e2e.artifacts-folder="$(ARTIFACTS)" \ --e2e.config="$(E2E_CONF_FILE)" \ --e2e.config-overrides="$(E2E_CONF_OVERRIDE_FILE)" \ - --e2e.artifacts-folder="$(ARTIFACTS)" \ --e2e.skip-resource-cleanup=$(SKIP_RESOURCE_CLEANUP) \ --e2e.use-existing-cluster="$(USE_EXISTING_CLUSTER)" \ --e2e.ip-pool='$(E2E_VSPHERE_IP_POOL)' @@ -915,7 +918,7 @@ docker-vm-operator-build-%: docker-build-vm-operator: checkout-vm-operator @if [ -z "${VM_OPERATOR_VERSION}" ]; then echo "VM_OPERATOR_VERSION is not set"; exit 1; fi cd $(VM_OPERATOR_TMP_DIR) && \ - $(MAKE) IMAGE=$(VM_OPERATOR_CONTROLLER_IMG)-$(ARCH) IMAGE_TAG=$(VM_OPERATOR_VERSION) GOARCH=$(ARCH) docker-build + $(MAKE) IMAGE=$(VM_OPERATOR_CONTROLLER_IMG)-$(ARCH) IMAGE_TAG=$(VM_OPERATOR_IMAGE_TAG) GOARCH=$(ARCH) docker-build .PHONY: docker-push-all-vm-operator docker-push-all-vm-operator: $(addprefix docker-vm-operator-push-,$(VM_OPERATOR_ALL_ARCH)) ## Push the docker images to be included in the release for all architectures + related multiarch manifests @@ -970,7 +973,7 @@ clean-ci: ## Cleanup orphaned objects in CI @if [ -z "${GOVC_URL}" ]; then echo "GOVC_URL is not set"; exit 1; fi @if [ -z "${VSPHERE_TLS_THUMBPRINT}" ]; then echo "VSPHERE_TLS_THUMBPRINT is not set"; exit 1; fi @if [ -z "${BOSKOS_HOST}" ]; then echo "BOSKOS_HOST is not set"; exit 1; fi - go run $(JANITOR_DIR) --dry-run=false + go run $(JANITOR_DIR) --dry-run=false $(JANITOR_ARGS) .PHONY: clean-temporary clean-temporary: ## Remove all temporary files and folders diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/conversion.go index 8cbe0dc91d7..72c5f368f89 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/conversion.go @@ -29,10 +29,12 @@ func Convert_v1beta1_VirtualMachineCloneSpec_To_v1alpha3_VirtualMachineCloneSpec // Convert_v1beta1_VSphereVMStatus_To_v1alpha3_VSphereVMStatus is an autogenerated conversion function. func Convert_v1beta1_VSphereVMStatus_To_v1alpha3_VSphereVMStatus(in *infrav1.VSphereVMStatus, out *VSphereVMStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 return autoConvert_v1beta1_VSphereVMStatus_To_v1alpha3_VSphereVMStatus(in, out, s) } func Convert_v1beta1_VSphereClusterStatus_To_v1alpha3_VSphereClusterStatus(in *infrav1.VSphereClusterStatus, out *VSphereClusterStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 return autoConvert_v1beta1_VSphereClusterStatus_To_v1alpha3_VSphereClusterStatus(in, out, s) } @@ -47,3 +49,18 @@ func Convert_v1beta1_VSphereMachineSpec_To_v1alpha3_VSphereMachineSpec(in *infra func Convert_v1beta1_VSphereVMSpec_To_v1alpha3_VSphereVMSpec(in *infrav1.VSphereVMSpec, out *VSphereVMSpec, s conversion.Scope) error { return autoConvert_v1beta1_VSphereVMSpec_To_v1alpha3_VSphereVMSpec(in, out, s) } + +func Convert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(in *infrav1.VSphereMachineStatus, out *VSphereMachineStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 + return autoConvert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(in, out, s) +} + +func Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(in *infrav1.VSphereDeploymentZoneStatus, out *VSphereDeploymentZoneStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 + return autoConvert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(in, out, s) +} + +func Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(in *infrav1.VSphereClusterIdentityStatus, out *VSphereClusterIdentityStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 + return autoConvert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(in, out, s) +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherecluster_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherecluster_conversion.go index a3875f0c6f8..46f9d780b11 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherecluster_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherecluster_conversion.go @@ -39,6 +39,8 @@ func (src *VSphereCluster) ConvertTo(dstRaw conversion.Hub) error { if restored.Spec.IdentityRef != nil { dst.Spec.IdentityRef = restored.Spec.IdentityRef } + dst.Status.V1Beta2 = restored.Status.V1Beta2 + return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vsphereclusteridentity_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vsphereclusteridentity_conversion.go index 82492a80332..7a4eb7bd772 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vsphereclusteridentity_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vsphereclusteridentity_conversion.go @@ -17,6 +17,7 @@ limitations under the License. package v1alpha3 import ( + utilconversion "sigs.k8s.io/cluster-api/util/conversion" "sigs.k8s.io/controller-runtime/pkg/conversion" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -25,18 +26,35 @@ import ( // ConvertTo converts this VSphereClusterIdentity to the Hub version (v1beta1). func (src *VSphereClusterIdentity) ConvertTo(dstRaw conversion.Hub) error { dst := dstRaw.(*infrav1.VSphereClusterIdentity) + if err := Convert_v1alpha3_VSphereClusterIdentity_To_v1beta1_VSphereClusterIdentity(src, dst, nil); err != nil { return err } + + // Manually restore data. + restored := &infrav1.VSphereClusterIdentity{} + if ok, err := utilconversion.UnmarshalData(src, restored); err != nil || !ok { + return err + } + + dst.Status.V1Beta2 = restored.Status.V1Beta2 + return nil } // ConvertFrom converts from the Hub version (v1beta1) to this VSphereClusterIdentity. func (dst *VSphereClusterIdentity) ConvertFrom(srcRaw conversion.Hub) error { src := srcRaw.(*infrav1.VSphereClusterIdentity) + if err := Convert_v1beta1_VSphereClusterIdentity_To_v1alpha3_VSphereClusterIdentity(src, dst, nil); err != nil { return err } + + // Preserve Hub data on down-conversion except for metadata + if err := utilconversion.MarshalData(src, dst); err != nil { + return err + } + return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheredeploymentzone_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheredeploymentzone_conversion.go index 6e1ea2b2250..99eafd53b15 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheredeploymentzone_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheredeploymentzone_conversion.go @@ -17,6 +17,7 @@ limitations under the License. package v1alpha3 import ( + utilconversion "sigs.k8s.io/cluster-api/util/conversion" "sigs.k8s.io/controller-runtime/pkg/conversion" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -25,13 +26,37 @@ import ( // ConvertTo converts this VSphereDeploymentZone to the Hub version (v1beta1). func (src *VSphereDeploymentZone) ConvertTo(dstRaw conversion.Hub) error { dst := dstRaw.(*infrav1.VSphereDeploymentZone) - return Convert_v1alpha3_VSphereDeploymentZone_To_v1beta1_VSphereDeploymentZone(src, dst, nil) + + if err := Convert_v1alpha3_VSphereDeploymentZone_To_v1beta1_VSphereDeploymentZone(src, dst, nil); err != nil { + return err + } + + // Manually restore data. + restored := &infrav1.VSphereDeploymentZone{} + if ok, err := utilconversion.UnmarshalData(src, restored); err != nil || !ok { + return err + } + + dst.Status.V1Beta2 = restored.Status.V1Beta2 + + return nil + } // ConvertFrom converts from the Hub version (v1beta1) to this VSphereDeploymentZone. func (dst *VSphereDeploymentZone) ConvertFrom(srcRaw conversion.Hub) error { src := srcRaw.(*infrav1.VSphereDeploymentZone) - return Convert_v1beta1_VSphereDeploymentZone_To_v1alpha3_VSphereDeploymentZone(src, dst, nil) + + if err := Convert_v1beta1_VSphereDeploymentZone_To_v1alpha3_VSphereDeploymentZone(src, dst, nil); err != nil { + return err + } + + // Preserve Hub data on down-conversion except for metadata + if err := utilconversion.MarshalData(src, dst); err != nil { + return err + } + + return nil } // ConvertTo converts this VSphereDeploymentZoneList to the Hub version (v1beta1). diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheremachine_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheremachine_conversion.go index 4b33b02ffa3..eafef460fa5 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheremachine_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspheremachine_conversion.go @@ -48,6 +48,7 @@ func (src *VSphereMachine) ConvertTo(dstRaw conversion.Hub) error { dst.Spec.Network.Devices[i].SkipIPAllocation = restored.Spec.Network.Devices[i].SkipIPAllocation } dst.Spec.DataDisks = restored.Spec.DataDisks + dst.Status.V1Beta2 = restored.Status.V1Beta2 return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherevm_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherevm_conversion.go index 95c144c9ecc..e8ec172314c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherevm_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/vspherevm_conversion.go @@ -47,6 +47,7 @@ func (src *VSphereVM) ConvertTo(dstRaw conversion.Hub) error { dst.Spec.Network.Devices[i].SkipIPAllocation = restored.Spec.Network.Devices[i].SkipIPAllocation } dst.Spec.DataDisks = restored.Spec.DataDisks + dst.Status.V1Beta2 = restored.Status.V1Beta2 return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/zz_generated.conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/zz_generated.conversion.go index f92ba0b018e..8b39fd137f9 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/zz_generated.conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha3/zz_generated.conversion.go @@ -200,11 +200,6 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.VSphereClusterIdentityStatus)(nil), (*VSphereClusterIdentityStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(a.(*v1beta1.VSphereClusterIdentityStatus), b.(*VSphereClusterIdentityStatus), scope) - }); err != nil { - return err - } if err := s.AddGeneratedConversionFunc((*VSphereClusterList)(nil), (*v1beta1.VSphereClusterList)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1alpha3_VSphereClusterList_To_v1beta1_VSphereClusterList(a.(*VSphereClusterList), b.(*v1beta1.VSphereClusterList), scope) }); err != nil { @@ -255,11 +250,6 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.VSphereDeploymentZoneStatus)(nil), (*VSphereDeploymentZoneStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(a.(*v1beta1.VSphereDeploymentZoneStatus), b.(*VSphereDeploymentZoneStatus), scope) - }); err != nil { - return err - } if err := s.AddGeneratedConversionFunc((*VSphereFailureDomain)(nil), (*v1beta1.VSphereFailureDomain)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1alpha3_VSphereFailureDomain_To_v1beta1_VSphereFailureDomain(a.(*VSphereFailureDomain), b.(*v1beta1.VSphereFailureDomain), scope) }); err != nil { @@ -330,11 +320,6 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.VSphereMachineStatus)(nil), (*VSphereMachineStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(a.(*v1beta1.VSphereMachineStatus), b.(*VSphereMachineStatus), scope) - }); err != nil { - return err - } if err := s.AddGeneratedConversionFunc((*VSphereMachineTemplate)(nil), (*v1beta1.VSphereMachineTemplate)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1alpha3_VSphereMachineTemplate_To_v1beta1_VSphereMachineTemplate(a.(*VSphereMachineTemplate), b.(*v1beta1.VSphereMachineTemplate), scope) }); err != nil { @@ -460,6 +445,11 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddConversionFunc((*v1beta1.VSphereClusterIdentityStatus)(nil), (*VSphereClusterIdentityStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(a.(*v1beta1.VSphereClusterIdentityStatus), b.(*VSphereClusterIdentityStatus), scope) + }); err != nil { + return err + } if err := s.AddConversionFunc((*v1beta1.VSphereClusterSpec)(nil), (*VSphereClusterSpec)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_VSphereClusterSpec_To_v1alpha3_VSphereClusterSpec(a.(*v1beta1.VSphereClusterSpec), b.(*VSphereClusterSpec), scope) }); err != nil { @@ -470,11 +460,21 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddConversionFunc((*v1beta1.VSphereDeploymentZoneStatus)(nil), (*VSphereDeploymentZoneStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(a.(*v1beta1.VSphereDeploymentZoneStatus), b.(*VSphereDeploymentZoneStatus), scope) + }); err != nil { + return err + } if err := s.AddConversionFunc((*v1beta1.VSphereMachineSpec)(nil), (*VSphereMachineSpec)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_VSphereMachineSpec_To_v1alpha3_VSphereMachineSpec(a.(*v1beta1.VSphereMachineSpec), b.(*VSphereMachineSpec), scope) }); err != nil { return err } + if err := s.AddConversionFunc((*v1beta1.VSphereMachineStatus)(nil), (*VSphereMachineStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(a.(*v1beta1.VSphereMachineStatus), b.(*VSphereMachineStatus), scope) + }); err != nil { + return err + } if err := s.AddConversionFunc((*v1beta1.VSphereVMSpec)(nil), (*VSphereVMSpec)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_VSphereVMSpec_To_v1alpha3_VSphereVMSpec(a.(*v1beta1.VSphereVMSpec), b.(*VSphereVMSpec), scope) }); err != nil { @@ -930,7 +930,17 @@ func Convert_v1beta1_VSphereClusterIdentity_To_v1alpha3_VSphereClusterIdentity(i func autoConvert_v1alpha3_VSphereClusterIdentityList_To_v1beta1_VSphereClusterIdentityList(in *VSphereClusterIdentityList, out *v1beta1.VSphereClusterIdentityList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]v1beta1.VSphereClusterIdentity)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]v1beta1.VSphereClusterIdentity, len(*in)) + for i := range *in { + if err := Convert_v1alpha3_VSphereClusterIdentity_To_v1beta1_VSphereClusterIdentity(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -941,7 +951,17 @@ func Convert_v1alpha3_VSphereClusterIdentityList_To_v1beta1_VSphereClusterIdenti func autoConvert_v1beta1_VSphereClusterIdentityList_To_v1alpha3_VSphereClusterIdentityList(in *v1beta1.VSphereClusterIdentityList, out *VSphereClusterIdentityList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]VSphereClusterIdentity)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]VSphereClusterIdentity, len(*in)) + for i := range *in { + if err := Convert_v1beta1_VSphereClusterIdentity_To_v1alpha3_VSphereClusterIdentity(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -986,14 +1006,10 @@ func Convert_v1alpha3_VSphereClusterIdentityStatus_To_v1beta1_VSphereClusterIden func autoConvert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(in *v1beta1.VSphereClusterIdentityStatus, out *VSphereClusterIdentityStatus, s conversion.Scope) error { out.Ready = in.Ready out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } -// Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus is an autogenerated conversion function. -func Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(in *v1beta1.VSphereClusterIdentityStatus, out *VSphereClusterIdentityStatus, s conversion.Scope) error { - return autoConvert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha3_VSphereClusterIdentityStatus(in, out, s) -} - func autoConvert_v1alpha3_VSphereClusterList_To_v1beta1_VSphereClusterList(in *VSphereClusterList, out *v1beta1.VSphereClusterList, s conversion.Scope) error { out.ListMeta = in.ListMeta if in.Items != nil { @@ -1079,6 +1095,7 @@ func autoConvert_v1beta1_VSphereClusterStatus_To_v1alpha3_VSphereClusterStatus(i out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) out.FailureDomains = *(*FailureDomains)(unsafe.Pointer(&in.FailureDomains)) // WARNING: in.VCenterVersion requires manual conversion: does not exist in peer-type + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } @@ -1116,7 +1133,17 @@ func Convert_v1beta1_VSphereDeploymentZone_To_v1alpha3_VSphereDeploymentZone(in func autoConvert_v1alpha3_VSphereDeploymentZoneList_To_v1beta1_VSphereDeploymentZoneList(in *VSphereDeploymentZoneList, out *v1beta1.VSphereDeploymentZoneList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]v1beta1.VSphereDeploymentZone)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]v1beta1.VSphereDeploymentZone, len(*in)) + for i := range *in { + if err := Convert_v1alpha3_VSphereDeploymentZone_To_v1beta1_VSphereDeploymentZone(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -1127,7 +1154,17 @@ func Convert_v1alpha3_VSphereDeploymentZoneList_To_v1beta1_VSphereDeploymentZone func autoConvert_v1beta1_VSphereDeploymentZoneList_To_v1alpha3_VSphereDeploymentZoneList(in *v1beta1.VSphereDeploymentZoneList, out *VSphereDeploymentZoneList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]VSphereDeploymentZone)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]VSphereDeploymentZone, len(*in)) + for i := range *in { + if err := Convert_v1beta1_VSphereDeploymentZone_To_v1alpha3_VSphereDeploymentZone(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -1180,14 +1217,10 @@ func Convert_v1alpha3_VSphereDeploymentZoneStatus_To_v1beta1_VSphereDeploymentZo func autoConvert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(in *v1beta1.VSphereDeploymentZoneStatus, out *VSphereDeploymentZoneStatus, s conversion.Scope) error { out.Ready = (*bool)(unsafe.Pointer(in.Ready)) out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } -// Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus is an autogenerated conversion function. -func Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(in *v1beta1.VSphereDeploymentZoneStatus, out *VSphereDeploymentZoneStatus, s conversion.Scope) error { - return autoConvert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha3_VSphereDeploymentZoneStatus(in, out, s) -} - func autoConvert_v1alpha3_VSphereFailureDomain_To_v1beta1_VSphereFailureDomain(in *VSphereFailureDomain, out *v1beta1.VSphereFailureDomain, s conversion.Scope) error { out.ObjectMeta = in.ObjectMeta if err := Convert_v1alpha3_VSphereFailureDomainSpec_To_v1beta1_VSphereFailureDomainSpec(&in.Spec, &out.Spec, s); err != nil { @@ -1436,14 +1469,10 @@ func autoConvert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(i out.FailureReason = (*errors.MachineStatusError)(unsafe.Pointer(in.FailureReason)) out.FailureMessage = (*string)(unsafe.Pointer(in.FailureMessage)) out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } -// Convert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus is an autogenerated conversion function. -func Convert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(in *v1beta1.VSphereMachineStatus, out *VSphereMachineStatus, s conversion.Scope) error { - return autoConvert_v1beta1_VSphereMachineStatus_To_v1alpha3_VSphereMachineStatus(in, out, s) -} - func autoConvert_v1alpha3_VSphereMachineTemplate_To_v1beta1_VSphereMachineTemplate(in *VSphereMachineTemplate, out *v1beta1.VSphereMachineTemplate, s conversion.Scope) error { out.ObjectMeta = in.ObjectMeta if err := Convert_v1alpha3_VSphereMachineTemplateSpec_To_v1beta1_VSphereMachineTemplateSpec(&in.Spec, &out.Spec, s); err != nil { @@ -1698,6 +1727,7 @@ func autoConvert_v1beta1_VSphereVMStatus_To_v1alpha3_VSphereVMStatus(in *v1beta1 out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) // WARNING: in.ModuleUUID requires manual conversion: does not exist in peer-type // WARNING: in.VMRef requires manual conversion: does not exist in peer-type + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/conversion.go index 289c7933a3f..95798d3e028 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/conversion.go @@ -28,10 +28,12 @@ func Convert_v1beta1_VirtualMachineCloneSpec_To_v1alpha4_VirtualMachineCloneSpec } func Convert_v1beta1_VSphereVMStatus_To_v1alpha4_VSphereVMStatus(in *infrav1.VSphereVMStatus, out *VSphereVMStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 return autoConvert_v1beta1_VSphereVMStatus_To_v1alpha4_VSphereVMStatus(in, out, s) } func Convert_v1beta1_VSphereClusterStatus_To_v1alpha4_VSphereClusterStatus(in *infrav1.VSphereClusterStatus, out *VSphereClusterStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 return autoConvert_v1beta1_VSphereClusterStatus_To_v1alpha4_VSphereClusterStatus(in, out, s) } @@ -46,3 +48,18 @@ func Convert_v1beta1_VSphereMachineSpec_To_v1alpha4_VSphereMachineSpec(in *infra func Convert_v1beta1_VSphereVMSpec_To_v1alpha4_VSphereVMSpec(in *infrav1.VSphereVMSpec, out *VSphereVMSpec, s conversion.Scope) error { return autoConvert_v1beta1_VSphereVMSpec_To_v1alpha4_VSphereVMSpec(in, out, s) } + +func Convert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(in *infrav1.VSphereMachineStatus, out *VSphereMachineStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 + return autoConvert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(in, out, s) +} + +func Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(in *infrav1.VSphereDeploymentZoneStatus, out *VSphereDeploymentZoneStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 + return autoConvert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(in, out, s) +} + +func Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(in *infrav1.VSphereClusterIdentityStatus, out *VSphereClusterIdentityStatus, s conversion.Scope) error { + // V1Beta2 was added in v1beta1 + return autoConvert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(in, out, s) +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherecluster_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherecluster_conversion.go index e8ffaaf1145..f84a83ac801 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherecluster_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherecluster_conversion.go @@ -17,6 +17,7 @@ limitations under the License. package v1alpha4 import ( + utilconversion "sigs.k8s.io/cluster-api/util/conversion" "sigs.k8s.io/controller-runtime/pkg/conversion" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -25,13 +26,29 @@ import ( // ConvertTo converts this VSphereCluster to the Hub version (v1beta1). func (src *VSphereCluster) ConvertTo(dstRaw conversion.Hub) error { dst := dstRaw.(*infrav1.VSphereCluster) - return Convert_v1alpha4_VSphereCluster_To_v1beta1_VSphereCluster(src, dst, nil) + if err := Convert_v1alpha4_VSphereCluster_To_v1beta1_VSphereCluster(src, dst, nil); err != nil { + return err + } + + // Manually restore data. + restored := &infrav1.VSphereCluster{} + if ok, err := utilconversion.UnmarshalData(src, restored); err != nil || !ok { + return err + } + dst.Status.V1Beta2 = restored.Status.V1Beta2 + + return nil } // ConvertFrom converts from the Hub version (v1beta1) to this VSphereCluster. func (dst *VSphereCluster) ConvertFrom(srcRaw conversion.Hub) error { src := srcRaw.(*infrav1.VSphereCluster) - return Convert_v1beta1_VSphereCluster_To_v1alpha4_VSphereCluster(src, dst, nil) + + if err := Convert_v1beta1_VSphereCluster_To_v1alpha4_VSphereCluster(src, dst, nil); err != nil { + return err + } + + return utilconversion.MarshalData(src, dst) } // ConvertTo converts this VSphereClusterList to the Hub version (v1beta1). diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vsphereclusteridentity_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vsphereclusteridentity_conversion.go index b6499ddc7c8..f3e091f55af 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vsphereclusteridentity_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vsphereclusteridentity_conversion.go @@ -17,6 +17,7 @@ limitations under the License. package v1alpha4 import ( + utilconversion "sigs.k8s.io/cluster-api/util/conversion" "sigs.k8s.io/controller-runtime/pkg/conversion" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -25,13 +26,36 @@ import ( // ConvertTo converts this VSphereClusterIdentity to the Hub version (v1beta1). func (src *VSphereClusterIdentity) ConvertTo(dstRaw conversion.Hub) error { dst := dstRaw.(*infrav1.VSphereClusterIdentity) - return Convert_v1alpha4_VSphereClusterIdentity_To_v1beta1_VSphereClusterIdentity(src, dst, nil) + + if err := Convert_v1alpha4_VSphereClusterIdentity_To_v1beta1_VSphereClusterIdentity(src, dst, nil); err != nil { + return err + } + + // Manually restore data. + restored := &infrav1.VSphereClusterIdentity{} + if ok, err := utilconversion.UnmarshalData(src, restored); err != nil || !ok { + return err + } + + dst.Status.V1Beta2 = restored.Status.V1Beta2 + + return nil } // ConvertFrom converts from the Hub version (v1beta1) to this VSphereClusterIdentity. func (dst *VSphereClusterIdentity) ConvertFrom(srcRaw conversion.Hub) error { src := srcRaw.(*infrav1.VSphereClusterIdentity) - return Convert_v1beta1_VSphereClusterIdentity_To_v1alpha4_VSphereClusterIdentity(src, dst, nil) + + if err := Convert_v1beta1_VSphereClusterIdentity_To_v1alpha4_VSphereClusterIdentity(src, dst, nil); err != nil { + return err + } + + // Preserve Hub data on down-conversion except for metadata + if err := utilconversion.MarshalData(src, dst); err != nil { + return err + } + + return nil } // ConvertTo converts this VSphereClusterIdentityList to the Hub version (v1beta1). diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheredeploymentzone_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheredeploymentzone_conversion.go index 857fc6e741a..95a69e2817d 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheredeploymentzone_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheredeploymentzone_conversion.go @@ -17,6 +17,7 @@ limitations under the License. package v1alpha4 import ( + utilconversion "sigs.k8s.io/cluster-api/util/conversion" "sigs.k8s.io/controller-runtime/pkg/conversion" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -25,13 +26,36 @@ import ( // ConvertTo converts this VSphereDeploymentZone to the Hub version (v1beta1). func (src *VSphereDeploymentZone) ConvertTo(dstRaw conversion.Hub) error { dst := dstRaw.(*infrav1.VSphereDeploymentZone) - return Convert_v1alpha4_VSphereDeploymentZone_To_v1beta1_VSphereDeploymentZone(src, dst, nil) + + if err := Convert_v1alpha4_VSphereDeploymentZone_To_v1beta1_VSphereDeploymentZone(src, dst, nil); err != nil { + return err + } + + // Manually restore data. + restored := &infrav1.VSphereDeploymentZone{} + if ok, err := utilconversion.UnmarshalData(src, restored); err != nil || !ok { + return err + } + + dst.Status.V1Beta2 = restored.Status.V1Beta2 + + return nil } // ConvertFrom converts from the Hub version (v1beta1) to this VSphereDeploymentZone. func (dst *VSphereDeploymentZone) ConvertFrom(srcRaw conversion.Hub) error { src := srcRaw.(*infrav1.VSphereDeploymentZone) - return Convert_v1beta1_VSphereDeploymentZone_To_v1alpha4_VSphereDeploymentZone(src, dst, nil) + + if err := Convert_v1beta1_VSphereDeploymentZone_To_v1alpha4_VSphereDeploymentZone(src, dst, nil); err != nil { + return err + } + + // Preserve Hub data on down-conversion except for metadata + if err := utilconversion.MarshalData(src, dst); err != nil { + return err + } + + return nil } // ConvertTo converts this VSphereDeploymentZoneList to the Hub version (v1beta1). diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheremachine_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheremachine_conversion.go index 1277f2db007..23e1d7269cc 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheremachine_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspheremachine_conversion.go @@ -48,6 +48,7 @@ func (src *VSphereMachine) ConvertTo(dstRaw conversion.Hub) error { dst.Spec.Network.Devices[i].SkipIPAllocation = restored.Spec.Network.Devices[i].SkipIPAllocation } dst.Spec.DataDisks = restored.Spec.DataDisks + dst.Status.V1Beta2 = restored.Status.V1Beta2 return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherevm_conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherevm_conversion.go index 7fd9a4aebb7..d87f0969c8e 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherevm_conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/vspherevm_conversion.go @@ -47,6 +47,7 @@ func (src *VSphereVM) ConvertTo(dstRaw conversion.Hub) error { dst.Spec.Network.Devices[i].SkipIPAllocation = restored.Spec.Network.Devices[i].SkipIPAllocation } dst.Spec.DataDisks = restored.Spec.DataDisks + dst.Status.V1Beta2 = restored.Status.V1Beta2 return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/zz_generated.conversion.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/zz_generated.conversion.go index 55e25811bc1..2e644a16e86 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/zz_generated.conversion.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1alpha4/zz_generated.conversion.go @@ -200,11 +200,6 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.VSphereClusterIdentityStatus)(nil), (*VSphereClusterIdentityStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(a.(*v1beta1.VSphereClusterIdentityStatus), b.(*VSphereClusterIdentityStatus), scope) - }); err != nil { - return err - } if err := s.AddGeneratedConversionFunc((*VSphereClusterList)(nil), (*v1beta1.VSphereClusterList)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1alpha4_VSphereClusterList_To_v1beta1_VSphereClusterList(a.(*VSphereClusterList), b.(*v1beta1.VSphereClusterList), scope) }); err != nil { @@ -300,11 +295,6 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.VSphereDeploymentZoneStatus)(nil), (*VSphereDeploymentZoneStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(a.(*v1beta1.VSphereDeploymentZoneStatus), b.(*VSphereDeploymentZoneStatus), scope) - }); err != nil { - return err - } if err := s.AddGeneratedConversionFunc((*VSphereFailureDomain)(nil), (*v1beta1.VSphereFailureDomain)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1alpha4_VSphereFailureDomain_To_v1beta1_VSphereFailureDomain(a.(*VSphereFailureDomain), b.(*v1beta1.VSphereFailureDomain), scope) }); err != nil { @@ -375,11 +365,6 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } - if err := s.AddGeneratedConversionFunc((*v1beta1.VSphereMachineStatus)(nil), (*VSphereMachineStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { - return Convert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(a.(*v1beta1.VSphereMachineStatus), b.(*VSphereMachineStatus), scope) - }); err != nil { - return err - } if err := s.AddGeneratedConversionFunc((*VSphereMachineTemplate)(nil), (*v1beta1.VSphereMachineTemplate)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1alpha4_VSphereMachineTemplate_To_v1beta1_VSphereMachineTemplate(a.(*VSphereMachineTemplate), b.(*v1beta1.VSphereMachineTemplate), scope) }); err != nil { @@ -500,6 +485,11 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddConversionFunc((*v1beta1.VSphereClusterIdentityStatus)(nil), (*VSphereClusterIdentityStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(a.(*v1beta1.VSphereClusterIdentityStatus), b.(*VSphereClusterIdentityStatus), scope) + }); err != nil { + return err + } if err := s.AddConversionFunc((*v1beta1.VSphereClusterSpec)(nil), (*VSphereClusterSpec)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_VSphereClusterSpec_To_v1alpha4_VSphereClusterSpec(a.(*v1beta1.VSphereClusterSpec), b.(*VSphereClusterSpec), scope) }); err != nil { @@ -510,11 +500,21 @@ func RegisterConversions(s *runtime.Scheme) error { }); err != nil { return err } + if err := s.AddConversionFunc((*v1beta1.VSphereDeploymentZoneStatus)(nil), (*VSphereDeploymentZoneStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(a.(*v1beta1.VSphereDeploymentZoneStatus), b.(*VSphereDeploymentZoneStatus), scope) + }); err != nil { + return err + } if err := s.AddConversionFunc((*v1beta1.VSphereMachineSpec)(nil), (*VSphereMachineSpec)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_VSphereMachineSpec_To_v1alpha4_VSphereMachineSpec(a.(*v1beta1.VSphereMachineSpec), b.(*VSphereMachineSpec), scope) }); err != nil { return err } + if err := s.AddConversionFunc((*v1beta1.VSphereMachineStatus)(nil), (*VSphereMachineStatus)(nil), func(a, b interface{}, scope conversion.Scope) error { + return Convert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(a.(*v1beta1.VSphereMachineStatus), b.(*VSphereMachineStatus), scope) + }); err != nil { + return err + } if err := s.AddConversionFunc((*v1beta1.VSphereVMSpec)(nil), (*VSphereVMSpec)(nil), func(a, b interface{}, scope conversion.Scope) error { return Convert_v1beta1_VSphereVMSpec_To_v1alpha4_VSphereVMSpec(a.(*v1beta1.VSphereVMSpec), b.(*VSphereVMSpec), scope) }); err != nil { @@ -966,7 +966,17 @@ func Convert_v1beta1_VSphereClusterIdentity_To_v1alpha4_VSphereClusterIdentity(i func autoConvert_v1alpha4_VSphereClusterIdentityList_To_v1beta1_VSphereClusterIdentityList(in *VSphereClusterIdentityList, out *v1beta1.VSphereClusterIdentityList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]v1beta1.VSphereClusterIdentity)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]v1beta1.VSphereClusterIdentity, len(*in)) + for i := range *in { + if err := Convert_v1alpha4_VSphereClusterIdentity_To_v1beta1_VSphereClusterIdentity(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -977,7 +987,17 @@ func Convert_v1alpha4_VSphereClusterIdentityList_To_v1beta1_VSphereClusterIdenti func autoConvert_v1beta1_VSphereClusterIdentityList_To_v1alpha4_VSphereClusterIdentityList(in *v1beta1.VSphereClusterIdentityList, out *VSphereClusterIdentityList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]VSphereClusterIdentity)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]VSphereClusterIdentity, len(*in)) + for i := range *in { + if err := Convert_v1beta1_VSphereClusterIdentity_To_v1alpha4_VSphereClusterIdentity(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -1022,14 +1042,10 @@ func Convert_v1alpha4_VSphereClusterIdentityStatus_To_v1beta1_VSphereClusterIden func autoConvert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(in *v1beta1.VSphereClusterIdentityStatus, out *VSphereClusterIdentityStatus, s conversion.Scope) error { out.Ready = in.Ready out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } -// Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus is an autogenerated conversion function. -func Convert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(in *v1beta1.VSphereClusterIdentityStatus, out *VSphereClusterIdentityStatus, s conversion.Scope) error { - return autoConvert_v1beta1_VSphereClusterIdentityStatus_To_v1alpha4_VSphereClusterIdentityStatus(in, out, s) -} - func autoConvert_v1alpha4_VSphereClusterList_To_v1beta1_VSphereClusterList(in *VSphereClusterList, out *v1beta1.VSphereClusterList, s conversion.Scope) error { out.ListMeta = in.ListMeta if in.Items != nil { @@ -1117,6 +1133,7 @@ func autoConvert_v1beta1_VSphereClusterStatus_To_v1alpha4_VSphereClusterStatus(i out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) out.FailureDomains = *(*FailureDomains)(unsafe.Pointer(&in.FailureDomains)) // WARNING: in.VCenterVersion requires manual conversion: does not exist in peer-type + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } @@ -1270,7 +1287,17 @@ func Convert_v1beta1_VSphereDeploymentZone_To_v1alpha4_VSphereDeploymentZone(in func autoConvert_v1alpha4_VSphereDeploymentZoneList_To_v1beta1_VSphereDeploymentZoneList(in *VSphereDeploymentZoneList, out *v1beta1.VSphereDeploymentZoneList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]v1beta1.VSphereDeploymentZone)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]v1beta1.VSphereDeploymentZone, len(*in)) + for i := range *in { + if err := Convert_v1alpha4_VSphereDeploymentZone_To_v1beta1_VSphereDeploymentZone(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -1281,7 +1308,17 @@ func Convert_v1alpha4_VSphereDeploymentZoneList_To_v1beta1_VSphereDeploymentZone func autoConvert_v1beta1_VSphereDeploymentZoneList_To_v1alpha4_VSphereDeploymentZoneList(in *v1beta1.VSphereDeploymentZoneList, out *VSphereDeploymentZoneList, s conversion.Scope) error { out.ListMeta = in.ListMeta - out.Items = *(*[]VSphereDeploymentZone)(unsafe.Pointer(&in.Items)) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]VSphereDeploymentZone, len(*in)) + for i := range *in { + if err := Convert_v1beta1_VSphereDeploymentZone_To_v1alpha4_VSphereDeploymentZone(&(*in)[i], &(*out)[i], s); err != nil { + return err + } + } + } else { + out.Items = nil + } return nil } @@ -1334,14 +1371,10 @@ func Convert_v1alpha4_VSphereDeploymentZoneStatus_To_v1beta1_VSphereDeploymentZo func autoConvert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(in *v1beta1.VSphereDeploymentZoneStatus, out *VSphereDeploymentZoneStatus, s conversion.Scope) error { out.Ready = (*bool)(unsafe.Pointer(in.Ready)) out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } -// Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus is an autogenerated conversion function. -func Convert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(in *v1beta1.VSphereDeploymentZoneStatus, out *VSphereDeploymentZoneStatus, s conversion.Scope) error { - return autoConvert_v1beta1_VSphereDeploymentZoneStatus_To_v1alpha4_VSphereDeploymentZoneStatus(in, out, s) -} - func autoConvert_v1alpha4_VSphereFailureDomain_To_v1beta1_VSphereFailureDomain(in *VSphereFailureDomain, out *v1beta1.VSphereFailureDomain, s conversion.Scope) error { out.ObjectMeta = in.ObjectMeta if err := Convert_v1alpha4_VSphereFailureDomainSpec_To_v1beta1_VSphereFailureDomainSpec(&in.Spec, &out.Spec, s); err != nil { @@ -1590,14 +1623,10 @@ func autoConvert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(i out.FailureReason = (*errors.MachineStatusError)(unsafe.Pointer(in.FailureReason)) out.FailureMessage = (*string)(unsafe.Pointer(in.FailureMessage)) out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } -// Convert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus is an autogenerated conversion function. -func Convert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(in *v1beta1.VSphereMachineStatus, out *VSphereMachineStatus, s conversion.Scope) error { - return autoConvert_v1beta1_VSphereMachineStatus_To_v1alpha4_VSphereMachineStatus(in, out, s) -} - func autoConvert_v1alpha4_VSphereMachineTemplate_To_v1beta1_VSphereMachineTemplate(in *VSphereMachineTemplate, out *v1beta1.VSphereMachineTemplate, s conversion.Scope) error { out.ObjectMeta = in.ObjectMeta if err := Convert_v1alpha4_VSphereMachineTemplateSpec_To_v1beta1_VSphereMachineTemplateSpec(&in.Spec, &out.Spec, s); err != nil { @@ -1852,6 +1881,7 @@ func autoConvert_v1beta1_VSphereVMStatus_To_v1alpha4_VSphereVMStatus(in *v1beta1 out.Conditions = *(*Conditions)(unsafe.Pointer(&in.Conditions)) // WARNING: in.ModuleUUID requires manual conversion: does not exist in peer-type // WARNING: in.VMRef requires manual conversion: does not exist in peer-type + // WARNING: in.V1Beta2 requires manual conversion: does not exist in peer-type return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherecluster_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherecluster_types.go index f7df2204b1c..4dccb519528 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherecluster_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherecluster_types.go @@ -28,6 +28,75 @@ const ( ClusterFinalizer = "vspherecluster.infrastructure.cluster.x-k8s.io" ) +// VSphereCluster's Ready condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterReadyV1Beta2Condition is true if the VSphereCluster's deletionTimestamp is not set, VSphereCluster's + // FailureDomainsReady, VCenterAvailable and ClusterModulesReady conditions are true. + VSphereClusterReadyV1Beta2Condition = clusterv1.ReadyV1Beta2Condition + + // VSphereClusterReadyV1Beta2Reason surfaces when the VSphereCluster readiness criteria is met. + VSphereClusterReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterNotReadyV1Beta2Reason surfaces when the VSphereCluster readiness criteria is not met. + VSphereClusterNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterReadyUnknownV1Beta2Reason surfaces when at least one VSphereCluster readiness criteria is unknown + // and no VSphereCluster readiness criteria is not met. + VSphereClusterReadyUnknownV1Beta2Reason = clusterv1.ReadyUnknownV1Beta2Reason +) + +// VSphereCluster's FailureDomainsReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterFailureDomainsReadyV1Beta2Condition documents the status of failure domains for a VSphereCluster. + VSphereClusterFailureDomainsReadyV1Beta2Condition = "FailureDomainsReady" + + // VSphereClusterFailureDomainsReadyV1Beta2Reason surfaces when the failure domains for a VSphereCluster are ready. + VSphereClusterFailureDomainsReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterFailureDomainsWaitingForFailureDomainStatusV1Beta2Reason surfaces when not all VSphereFailureDomains for a VSphereCluster are ready. + VSphereClusterFailureDomainsWaitingForFailureDomainStatusV1Beta2Reason = "WaitingForFailureDomainStatus" + + // VSphereClusterFailureDomainsNotReadyV1Beta2Reason surfaces when the failure domains for a VSphereCluster are not ready. + VSphereClusterFailureDomainsNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterFailureDomainsDeletingV1Beta2Reason surfaces when the failure domains for a VSphereCluster are being deleted. + VSphereClusterFailureDomainsDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereCluster's VCenterAvailable condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterVCenterAvailableV1Beta2Condition documents the status of vCenter for a VSphereCluster. + VSphereClusterVCenterAvailableV1Beta2Condition = "VCenterAvailable" + + // VSphereClusterVCenterAvailableV1Beta2Reason surfaces when the vCenter for a VSphereCluster is available. + VSphereClusterVCenterAvailableV1Beta2Reason = clusterv1.AvailableV1Beta2Reason + + // VSphereClusterVCenterUnreachableV1Beta2Reason surfaces when the vCenter for a VSphereCluster is unreachable. + VSphereClusterVCenterUnreachableV1Beta2Reason = "VCenterUnreachable" + + // VSphereClusterVCenterAvailableDeletingV1Beta2Reason surfaces when the VSphereCluster is being deleted. + VSphereClusterVCenterAvailableDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereCluster's ClusterModulesReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterClusterModulesReadyV1Beta2Condition documents the status of vCenter for a VSphereCluster. + VSphereClusterClusterModulesReadyV1Beta2Condition = "ClusterModulesReady" + + // VSphereClusterClusterModulesReadyV1Beta2Reason surfaces when the cluster modules for a VSphereCluster are ready. + VSphereClusterClusterModulesReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterModulesInvalidVCenterVersionV1Beta2Reason surfaces when the cluster modules for a VSphereCluster can't be reconciled + // due to an invalid vCenter version. + VSphereClusterModulesInvalidVCenterVersionV1Beta2Reason = "InvalidVCenterVersion" + + // VSphereClusterClusterModulesNotReadyV1Beta2Reason surfaces when the cluster modules for a VSphereCluster are not ready. + VSphereClusterClusterModulesNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterClusterModulesDeletingV1Beta2Reason surfaces when the cluster modules for a VSphereCluster are being deleted. + VSphereClusterClusterModulesDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + // VCenterVersion conveys the API version of the vCenter instance. type VCenterVersion string @@ -104,6 +173,22 @@ type VSphereClusterStatus struct { // VCenterVersion defines the version of the vCenter server defined in the spec. VCenterVersion VCenterVersion `json:"vCenterVersion,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereCluster's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereClusterV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereClusterV1Beta2Status groups all the fields that will be added or modified in VSphereClusterStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereClusterV1Beta2Status struct { + // conditions represents the observations of a VSphereCluster's current state. + // Known condition types are Ready, FailureDomainsReady, VCenterAvailable, ClusterModulesReady and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // +kubebuilder:object:root=true @@ -143,6 +228,22 @@ type VSphereClusterList struct { Items []VSphereCluster `json:"items"` } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (c *VSphereCluster) GetV1Beta2Conditions() []metav1.Condition { + if c.Status.V1Beta2 == nil { + return nil + } + return c.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (c *VSphereCluster) SetV1Beta2Conditions(conditions []metav1.Condition) { + if c.Status.V1Beta2 == nil { + c.Status.V1Beta2 = &VSphereClusterV1Beta2Status{} + } + c.Status.V1Beta2.Conditions = conditions +} + func init() { objectTypes = append(objectTypes, &VSphereCluster{}, &VSphereClusterList{}) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vsphereclusteridentity_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vsphereclusteridentity_types.go index 97130334d39..ae23092fff4 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vsphereclusteridentity_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vsphereclusteridentity_types.go @@ -28,6 +28,27 @@ const ( VSphereClusterIdentityFinalizer = "vsphereclusteridentity/infrastructure.cluster.x-k8s.io" ) +// VSphereClusterIdentity's Available condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterIdentityAvailableV1Beta2Condition documents the availability for a VSphereClusterIdentity. + VSphereClusterIdentityAvailableV1Beta2Condition = clusterv1.AvailableV1Beta2Condition + + // VSphereClusterIdentityAvailableV1Beta2Reason surfaces when the VSphereClusterIdentity is available. + VSphereClusterIdentityAvailableV1Beta2Reason = clusterv1.AvailableV1Beta2Reason + + // VSphereClusterIdentitySecretNotAvailableV1Beta2Reason surfaces when the VSphereClusterIdentity secret is not available. + VSphereClusterIdentitySecretNotAvailableV1Beta2Reason = "SecretNotAvailable" + + // VSphereClusterIdentitySecretAlreadyInUseV1Beta2Reason surfaces when the VSphereClusterIdentity secret is already in use. + VSphereClusterIdentitySecretAlreadyInUseV1Beta2Reason = "SecretAlreadyInUse" + + // VSphereClusterIdentitySettingSecretOwnerReferenceFailedV1Beta2Reason surfaces when setting the owner reference on the VSphereClusterIdentity secret failed. + VSphereClusterIdentitySettingSecretOwnerReferenceFailedV1Beta2Reason = "SettingSecretOwnerReferenceFailed" + + // VSphereClusterIdentityDeletingV1Beta2Reason surfaces when the VSphereClusterIdentity is being deleted. + VSphereClusterIdentityDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + // VSphereClusterIdentitySpec contains a secret reference and a group of allowed namespaces. type VSphereClusterIdentitySpec struct { // SecretName references a Secret inside the controller namespace with the credentials to use @@ -49,6 +70,22 @@ type VSphereClusterIdentityStatus struct { // Conditions defines current service state of the VSphereCluster. // +optional Conditions clusterv1.Conditions `json:"conditions,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereClusterIdentity's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereClusterIdentityV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereClusterIdentityV1Beta2Status groups all the fields that will be added or modified in VSphereClusterIdentityStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereClusterIdentityV1Beta2Status struct { + // conditions represents the observations of a VSphereClusterIdentity's current state. + // Known condition types are Available and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // AllowedNamespaces restricts the namespaces this VSphereClusterIdentity can be used from. @@ -89,6 +126,22 @@ func (c *VSphereClusterIdentity) SetConditions(conditions clusterv1.Conditions) c.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (c *VSphereClusterIdentity) GetV1Beta2Conditions() []metav1.Condition { + if c.Status.V1Beta2 == nil { + return nil + } + return c.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (c *VSphereClusterIdentity) SetV1Beta2Conditions(conditions []metav1.Condition) { + if c.Status.V1Beta2 == nil { + c.Status.V1Beta2 = &VSphereClusterIdentityV1Beta2Status{} + } + c.Status.V1Beta2.Conditions = conditions +} + // +kubebuilder:object:root=true // +kubebuilder:resource:path=vsphereclusteridentities,scope=Cluster,categories=cluster-api // +kubebuilder:storageversion diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheredeploymentzone_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheredeploymentzone_types.go index efdbc60b614..6b288361b5a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheredeploymentzone_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheredeploymentzone_types.go @@ -28,6 +28,92 @@ const ( DeploymentZoneFinalizer = "vspheredeploymentzone.infrastructure.cluster.x-k8s.io" ) +// VSphereDeploymentZone's Ready condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereDeploymentZoneReadyV1Beta2Condition is true if the VSphereDeploymentZone's deletionTimestamp is not set, VSphereDeploymentZone's + // VCenterAvailable, PlacementConstraintReady and FailureDomainValidated conditions are true. + VSphereDeploymentZoneReadyV1Beta2Condition = clusterv1.ReadyV1Beta2Condition + + // VSphereDeploymentZoneReadyV1Beta2Reason surfaces when the VSphereDeploymentZone readiness criteria is met. + VSphereDeploymentZoneReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereDeploymentZoneNotReadyV1Beta2Reason surfaces when the VSphereDeploymentZone readiness criteria is not met. + VSphereDeploymentZoneNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereDeploymentZoneReadyUnknownV1Beta2Reason surfaces when at least one VSphereDeploymentZone readiness criteria is unknown + // and no VSphereDeploymentZone readiness criteria is not met. + VSphereDeploymentZoneReadyUnknownV1Beta2Reason = clusterv1.ReadyUnknownV1Beta2Reason +) + +// VSphereDeploymentZone's VCenterAvailable condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereDeploymentZoneVCenterAvailableV1Beta2Condition documents the status of vCenter for a VSphereDeploymentZone. + VSphereDeploymentZoneVCenterAvailableV1Beta2Condition = "VCenterAvailable" + + // VSphereDeploymentZoneVCenterAvailableV1Beta2Reason surfaces when the vCenter for a VSphereDeploymentZone is available. + VSphereDeploymentZoneVCenterAvailableV1Beta2Reason = clusterv1.AvailableV1Beta2Reason + + // VSphereDeploymentZoneVCenterUnreachableV1Beta2Reason surfaces when the vCenter for a VSphereDeploymentZone is unreachable. + VSphereDeploymentZoneVCenterUnreachableV1Beta2Reason = "VCenterUnreachable" + + // VSphereDeploymentZoneVCenterAvailableDeletingV1Beta2Reason surfaces when the vCenter for a VSphereDeploymentZone is being deleted. + VSphereDeploymentZoneVCenterAvailableDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereDeploymentZone's PlacementConstraintReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition documents the placement constraint status for a VSphereDeploymentZone. + VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition = "PlacementConstraintReady" + + // VSphereDeploymentZonePlacementConstraintReadyV1Beta2Reason surfaces when the placement status for a VSphereDeploymentZone is ready. + VSphereDeploymentZonePlacementConstraintReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereDeploymentZonePlacementConstraintResourcePoolNotFoundV1Beta2Reason surfaces when the resource pool for a VSphereDeploymentZone is not found. + VSphereDeploymentZonePlacementConstraintResourcePoolNotFoundV1Beta2Reason = "ResourcePoolNotFound" + + // VSphereDeploymentZonePlacementConstraintFolderNotFoundV1Beta2Reason surfaces when the folder for a VSphereDeploymentZone is not found. + VSphereDeploymentZonePlacementConstraintFolderNotFoundV1Beta2Reason = "FolderNotFound" + + // VSphereDeploymentZonePlacementConstraintDeletingV1Beta2Reason surfaces when the VSphereDeploymentZone is being deleted. + VSphereDeploymentZonePlacementConstraintDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereDeploymentZone's FailureDomainValidated condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition documents failure domain validation status for a VSphereDeploymentZone. + VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition = "FailureDomainValidated" + + // VSphereDeploymentZoneFailureDomainValidatedV1Beta2Reason surfaces when the failure domain for a VSphereDeploymentZone is validated. + VSphereDeploymentZoneFailureDomainValidatedV1Beta2Reason = "Validated" + + // VSphereDeploymentZoneFailureDomainValidationFailedV1Beta2Reason surfaces when the failure domain's validation for a VSphereDeploymentZone failed. + VSphereDeploymentZoneFailureDomainValidationFailedV1Beta2Reason = "ValidationFailed" + + // VSphereDeploymentZoneFailureDomainRegionMisconfiguredV1Beta2Reason surfaces when the failure domain's region for a VSphereDeploymentZone is misconfigured. + VSphereDeploymentZoneFailureDomainRegionMisconfiguredV1Beta2Reason = "RegionMisconfigured" + + // VSphereDeploymentZoneFailureDomainZoneMisconfiguredV1Beta2Reason surfaces when the failure domain's zone for a VSphereDeploymentZone is misconfigured. + VSphereDeploymentZoneFailureDomainZoneMisconfiguredV1Beta2Reason = "ZoneMisconfigured" + + // VSphereDeploymentZoneFailureDomainHostsMisconfiguredV1Beta2Reason surfaces when the failure domain's hosts for a VSphereDeploymentZone are misconfigured. + VSphereDeploymentZoneFailureDomainHostsMisconfiguredV1Beta2Reason = "HostsMisconfigured" + + // VSphereDeploymentZoneFailureDomainDatastoreNotFoundV1Beta2Reason surfaces when the failure domain's datastore for a VSphereDeploymentZone is not found. + VSphereDeploymentZoneFailureDomainDatastoreNotFoundV1Beta2Reason = "DatastoreNotFound" + + // VSphereDeploymentZoneFailureDomainNetworkNotFoundV1Beta2Reason surfaces when the failure domain's network for a VSphereDeploymentZone is not found. + VSphereDeploymentZoneFailureDomainNetworkNotFoundV1Beta2Reason = "NetworkNotFound" + + // VSphereDeploymentZoneFailureDomainComputeClusterNotFoundV1Beta2Reason surfaces when the failure domain's compute cluster for a VSphereDeploymentZone is not found. + VSphereDeploymentZoneFailureDomainComputeClusterNotFoundV1Beta2Reason = "ComputeClusterNotFound" + + // VSphereDeploymentZoneFailureDomainResourcePoolNotFoundV1Beta2Reason surfaces when the failure domain's resource pool for a VSphereDeploymentZone is not found. + VSphereDeploymentZoneFailureDomainResourcePoolNotFoundV1Beta2Reason = "ResourcePoolNotFound" + + // VSphereDeploymentZoneFailureDomainDeletingV1Beta2Reason surfaces when the VSphereDeploymentZone is being deleted. + VSphereDeploymentZoneFailureDomainDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + // VSphereDeploymentZoneSpec defines the desired state of VSphereDeploymentZone. type VSphereDeploymentZoneSpec struct { @@ -83,6 +169,22 @@ type VSphereDeploymentZoneStatus struct { // Conditions defines current service state of the VSphereMachine. // +optional Conditions clusterv1.Conditions `json:"conditions,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereDeploymentZone's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereDeploymentZoneV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereDeploymentZoneV1Beta2Status groups all the fields that will be added or modified in VSphereDeploymentZoneStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereDeploymentZoneV1Beta2Status struct { + // conditions represents the observations of a VSphereDeploymentZone's current state. + // Known condition types are Ready, VCenterAvailable, PlacementConstraintReady, FailureDomainValidated and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // +kubebuilder:object:root=true @@ -109,6 +211,22 @@ func (z *VSphereDeploymentZone) SetConditions(conditions clusterv1.Conditions) { z.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (z *VSphereDeploymentZone) GetV1Beta2Conditions() []metav1.Condition { + if z.Status.V1Beta2 == nil { + return nil + } + return z.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (z *VSphereDeploymentZone) SetV1Beta2Conditions(conditions []metav1.Condition) { + if z.Status.V1Beta2 == nil { + z.Status.V1Beta2 = &VSphereDeploymentZoneV1Beta2Status{} + } + z.Status.V1Beta2.Conditions = conditions +} + // +kubebuilder:object:root=true // VSphereDeploymentZoneList contains a list of VSphereDeploymentZone. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheremachine_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheremachine_types.go index d6ec9bab170..945b463fe0e 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheremachine_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspheremachine_types.go @@ -29,6 +29,80 @@ const ( MachineFinalizer = "vspheremachine.infrastructure.cluster.x-k8s.io" ) +// VSphereMachine's Ready condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereMachineReadyV1Beta2Condition is true if the VSphereMachine's deletionTimestamp is not set, VSphereMachine's + // VirtualMachineProvisioned is true. + VSphereMachineReadyV1Beta2Condition = clusterv1.ReadyV1Beta2Condition + + // VSphereMachineReadyV1Beta2Reason surfaces when the VSphereMachine readiness criteria is met. + VSphereMachineReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereMachineNotReadyV1Beta2Reason surfaces when the VSphereMachine readiness criteria is not met. + VSphereMachineNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereMachineReadyUnknownV1Beta2Reason surfaces when at least one VSphereMachine readiness criteria is unknown + // and no VSphereMachine readiness criteria is not met. + VSphereMachineReadyUnknownV1Beta2Reason = clusterv1.ReadyUnknownV1Beta2Reason +) + +// VSphereMachine's VirtualMachineProvisioned condition and corresponding reasons that will be used in v1Beta2 API version. +// +// NOTE: +// - In supervisor mode, before creating the VM the VirtualMachine goes trough a series of preflight checks; if one is failing, the +// reason for this failure and the message are surfaced in the VSphereMachine's VirtualMachineProvisioned condition. +// - In govmomi mode, in some cases, reason and message from the VSphereVM are surfaced in the VSphereMachine's +// VirtualMachineProvisioned condition. +const ( + // VSphereMachineVirtualMachineProvisionedV1Beta2Condition documents the status of the VirtualMachine that is controlled + // by the VSphereMachine. + VSphereMachineVirtualMachineProvisionedV1Beta2Condition = "VirtualMachineProvisioned" + + // VSphereMachineVirtualMachineWaitingForClusterInfrastructureReadyV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereMachine waiting for the cluster infrastructure to be ready. + // Note: This reason is used only in govmomi mode. + VSphereMachineVirtualMachineWaitingForClusterInfrastructureReadyV1Beta2Reason = clusterv1.WaitingForClusterInfrastructureReadyV1Beta2Reason + + // VSphereMachineVirtualMachineWaitingForControlPlaneInitializedV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereMachine waiting for the control plane to be initialized. + VSphereMachineVirtualMachineWaitingForControlPlaneInitializedV1Beta2Reason = clusterv1.WaitingForControlPlaneInitializedV1Beta2Reason + + // VSphereMachineVirtualMachineWaitingForBootstrapDataV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereMachine waiting for the bootstrap data to be ready. + VSphereMachineVirtualMachineWaitingForBootstrapDataV1Beta2Reason = clusterv1.WaitingForBootstrapDataV1Beta2Reason + + // VSphereMachineVirtualMachineProvisioningV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine is provisioning. + // Note: This reason is used only in supervisor mode. + VSphereMachineVirtualMachineProvisioningV1Beta2Reason = "Provisioning" + + // VSphereMachineVirtualMachinePoweringOnV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine is executing the power on sequence. + // Note: This reason is used only in supervisor mode. + VSphereMachineVirtualMachinePoweringOnV1Beta2Reason = "PoweringOn" + + // VSphereMachineVirtualMachineWaitingForNetworkAddressV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine waiting for the machine network settings to be reported after machine being powered on. + VSphereMachineVirtualMachineWaitingForNetworkAddressV1Beta2Reason = "WaitingForNetworkAddress" + + // VSphereMachineVirtualMachineWaitingForBIOSUUIDV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine waiting for the machine to have a BIOS UUID. + // Note: This reason is used only in supervisor mode. + VSphereMachineVirtualMachineWaitingForBIOSUUIDV1Beta2Reason = "WaitingForBIOSUUID" + + // VSphereMachineVirtualMachineProvisionedV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine is provisioned. + VSphereMachineVirtualMachineProvisionedV1Beta2Reason = clusterv1.ProvisionedV1Beta2Reason + + // VSphereMachineVirtualMachineNotProvisionedV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine is not provisioned. + VSphereMachineVirtualMachineNotProvisionedV1Beta2Reason = clusterv1.NotProvisionedV1Beta2Reason + + // VSphereMachineVirtualMachineDeletingV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereMachine is being deleted. + VSphereMachineVirtualMachineDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + // VSphereMachineSpec defines the desired state of VSphereMachine. type VSphereMachineSpec struct { VirtualMachineCloneSpec `json:",inline"` @@ -149,6 +223,22 @@ type VSphereMachineStatus struct { // Conditions defines current service state of the VSphereMachine. // +optional Conditions clusterv1.Conditions `json:"conditions,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereMachine's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereMachineV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereMachineV1Beta2Status groups all the fields that will be added or modified in VSphereMachineStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereMachineV1Beta2Status struct { + // conditions represents the observations of a VSphereMachine's current state. + // Known condition types are Ready, VirtualMachineProvisioned and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // +kubebuilder:object:root=true @@ -180,6 +270,22 @@ func (m *VSphereMachine) SetConditions(conditions clusterv1.Conditions) { m.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (m *VSphereMachine) GetV1Beta2Conditions() []metav1.Condition { + if m.Status.V1Beta2 == nil { + return nil + } + return m.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (m *VSphereMachine) SetV1Beta2Conditions(conditions []metav1.Condition) { + if m.Status.V1Beta2 == nil { + m.Status.V1Beta2 = &VSphereMachineV1Beta2Status{} + } + m.Status.V1Beta2.Conditions = conditions +} + // +kubebuilder:object:root=true // VSphereMachineList contains a list of VSphereMachine. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherevm_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherevm_types.go index 13a827b5501..15c2b60fdd9 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherevm_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/vspherevm_types.go @@ -40,6 +40,143 @@ const ( GuestSoftPowerOffDefaultTimeout = 5 * time.Minute ) +// VSphereVM's Ready condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereVMReadyV1Beta2Condition is true if the VSphereVM's deletionTimestamp is not set, VSphereVM's + // VirtualMachineProvisioned, VCenterAvailable and IPAddressClaimsFulfilled are true. + VSphereVMReadyV1Beta2Condition = clusterv1.ReadyV1Beta2Condition + + // VSphereVMReadyV1Beta2Reason surfaces when the VSphereVM readiness criteria is met. + VSphereVMReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereVMNotReadyV1Beta2Reason surfaces when the VSphereVM readiness criteria is not met. + VSphereVMNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereVMReadyUnknownV1Beta2Reason surfaces when at least one VSphereVM readiness criteria is unknown + // and no VSphereVM readiness criteria is not met. + VSphereVMReadyUnknownV1Beta2Reason = clusterv1.ReadyUnknownV1Beta2Reason +) + +// VSphereVM's VirtualMachineProvisioned condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereVMVirtualMachineProvisionedV1Beta2Condition documents the status of the VirtualMachine that is controlled + // by the VSphereVM. + VSphereVMVirtualMachineProvisionedV1Beta2Condition = "VirtualMachineProvisioned" + + // VSphereVMVirtualMachineWaitingForCloneV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereVM waiting for the clone operation to complete. + VSphereVMVirtualMachineWaitingForCloneV1Beta2Reason = "WaitingForClone" + + // VSphereVMVirtualMachineWaitingForStaticIPAllocationV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereVM waiting for the allocation of a static IP address. + VSphereVMVirtualMachineWaitingForStaticIPAllocationV1Beta2Reason = "WaitingForStaticIPAllocation" + + // VSphereVMVirtualMachineWaitingForIPAddressV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereVM waiting for an IP address to be provisioned from the IPAM provider. + VSphereVMVirtualMachineWaitingForIPAddressV1Beta2Reason = "WaitingForIPAddress" + + // VSphereVMVirtualMachineWaitingForIPAllocationV1Beta2Reason documents the VirtualMachine that is controlled + // by the VSphereVM waiting for the allocation of an IP address. + // This is used when the dhcp4 or dhcp6 for a VirtualMachine is set and the VirtualMachine is waiting for the + // relevant IP address to show up on the VM. + VSphereVMVirtualMachineWaitingForIPAllocationV1Beta2Reason = "WaitingForIPAllocation" + + // VSphereVMVirtualMachinePoweringOnV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereVM is executing the power on sequence. + VSphereVMVirtualMachinePoweringOnV1Beta2Reason = "PoweringOn" + + // VSphereVMVirtualMachineProvisionedV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereVM is provisioned. + VSphereVMVirtualMachineProvisionedV1Beta2Reason = clusterv1.ProvisionedV1Beta2Reason + + // VSphereVMVirtualMachineTaskFailedV1Beta2Reason surfaces when a task for the VirtualMachine that is controlled + // by the VSphereVM failed; the reconcile look will automatically retry the operation, + // but a user intervention might be required to fix the problem. + VSphereVMVirtualMachineTaskFailedV1Beta2Reason = "TaskFailed" + + // VSphereVMVirtualMachineNotFoundByBIOSUUIDV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereVM can't be found by BIOS UUID. + // Those kind of errors could be transient sometimes and failed VSphereVM are automatically + // reconciled by the controller. + VSphereVMVirtualMachineNotFoundByBIOSUUIDV1Beta2Reason = "NotFoundByBIOSUUID" + + // VSphereVMVirtualMachineNotProvisionedV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereVM is not provisioned. + VSphereVMVirtualMachineNotProvisionedV1Beta2Reason = clusterv1.NotProvisionedV1Beta2Reason + + // VSphereVMVirtualMachineDeletingV1Beta2Reason surfaces when the VirtualMachine that is controlled + // by the VSphereVM is being deleted. + VSphereVMVirtualMachineDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereVM's VCenterAvailable condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereVMVCenterAvailableV1Beta2Condition documents the availability of the VCenter hosting the VSphereVM. + VSphereVMVCenterAvailableV1Beta2Condition = "VCenterAvailable" + + // VSphereVMVCenterAvailableV1Beta2Reason documents the VCenter hosting the VSphereVM + // being available. + VSphereVMVCenterAvailableV1Beta2Reason = clusterv1.AvailableV1Beta2Reason + + // VSphereVMVCenterUnreachableV1Beta2Reason documents the VCenter hosting the VSphereVM + // cannot be reached. + VSphereVMVCenterUnreachableV1Beta2Reason = "VCenterUnreachable" +) + +// VSphereVM's IPAddressClaimsFulfilled condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereVMIPAddressClaimsFulfilledV1Beta2Condition documents the status of claiming an IP address + // from an IPAM provider. + VSphereVMIPAddressClaimsFulfilledV1Beta2Condition = "IPAddressClaimsFulfilled" + + // VSphereVMIPAddressClaimsBeingCreatedV1Beta2Reason documents that claims for the + // IP addresses required by the VSphereVM are being created. + VSphereVMIPAddressClaimsBeingCreatedV1Beta2Reason = "IPAddressClaimsBeingCreated" + + // VSphereVMIPAddressClaimsWaitingForIPAddressV1Beta2Reason documents that claims for the + // IP addresses required by the VSphereVM are waiting for IP addresses. + VSphereVMIPAddressClaimsWaitingForIPAddressV1Beta2Reason = "WaitingForIPAddress" + + // VSphereVMIPAddressClaimsFulfilledV1Beta2Reason documents that claims for the + // IP addresses required by the VSphereVM are fulfilled. + VSphereVMIPAddressClaimsFulfilledV1Beta2Reason = "Fulfilled" + + // VSphereVMIPAddressClaimsNotFulfilledV1Beta2Reason documents that claims for the + // IP addresses required by the VSphereVM are not fulfilled. + VSphereVMIPAddressClaimsNotFulfilledV1Beta2Reason = "NotFulfilled" +) + +// VSphereVM's GuestSoftPowerOffSucceeded condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition documents the status of performing guest initiated + // graceful shutdown. + VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition string = "GuestSoftPowerOffSucceeded" + + // VSphereVMGuestSoftPowerOffInProgressV1Beta2Reason documents that the guest receives + // a graceful shutdown request. + VSphereVMGuestSoftPowerOffInProgressV1Beta2Reason = "InProgress" + + // GuestSoftPowerOffFailedV1Beta2Reason documents that the graceful + // shutdown request failed. + VSphereVMGuestSoftPowerOffFailedV1Beta2Reason = "Failed" + + // GuestSoftPowerOffSucceededV1Beta2Reason documents that the graceful + // shutdown request succeeded. + VSphereVMGuestSoftPowerOffSucceededV1Beta2Reason = "Succeeded" +) + +// VSphereVM's PCIDevicesDetached condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereVMPCIDevicesDetachedV1Beta2Condition documents the status of the attached PCI devices on the VSphereVM. + // It is a negative condition to notify the user that the device(s) is no longer attached to + // the underlying VM and would require manual intervention to fix the situation. + VSphereVMPCIDevicesDetachedV1Beta2Condition string = "PCIDevicesDetached" + + // VSphereVMPCIDevicesDetachedNotFoundV1Beta2Reason documents the VSphereVM not having the PCI device attached during VM startup. + // This would indicate that the PCI devices were removed out of band by an external entity. + VSphereVMPCIDevicesDetachedNotFoundV1Beta2Reason = "NotFound" +) + // VSphereVMSpec defines the desired state of VSphereVM. type VSphereVMSpec struct { VirtualMachineCloneSpec `json:",inline"` @@ -178,6 +315,23 @@ type VSphereVMStatus struct { // This field is set once the machine is created and should not be changed // +optional VMRef string `json:"vmRef,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereVM's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereVMV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereVMV1Beta2Status groups all the fields that will be added or modified in VSphereVMStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereVMV1Beta2Status struct { + // conditions represents the observations of a VSphereVM's current state. + // Known condition types are Ready, VirtualMachineProvisioned, VCenterAvailable and IPAddressClaimsFulfilled, + // GuestSoftPowerOffSucceeded, PCIDevicesDetached and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // +kubebuilder:object:root=true @@ -204,6 +358,22 @@ func (r *VSphereVM) SetConditions(conditions clusterv1.Conditions) { r.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (r *VSphereVM) GetV1Beta2Conditions() []metav1.Condition { + if r.Status.V1Beta2 == nil { + return nil + } + return r.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (r *VSphereVM) SetV1Beta2Conditions(conditions []metav1.Condition) { + if r.Status.V1Beta2 == nil { + r.Status.V1Beta2 = &VSphereVMV1Beta2Status{} + } + r.Status.V1Beta2.Conditions = conditions +} + // +kubebuilder:object:root=true // VSphereVMList contains a list of VSphereVM. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/zz_generated.deepcopy.go index 3d338d028ff..1f11e3adbf9 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1/zz_generated.deepcopy.go @@ -578,6 +578,11 @@ func (in *VSphereClusterIdentityStatus) DeepCopyInto(out *VSphereClusterIdentity (*in)[i].DeepCopyInto(&(*out)[i]) } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereClusterIdentityV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereClusterIdentityStatus. @@ -590,6 +595,28 @@ func (in *VSphereClusterIdentityStatus) DeepCopy() *VSphereClusterIdentityStatus return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereClusterIdentityV1Beta2Status) DeepCopyInto(out *VSphereClusterIdentityV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereClusterIdentityV1Beta2Status. +func (in *VSphereClusterIdentityV1Beta2Status) DeepCopy() *VSphereClusterIdentityV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereClusterIdentityV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VSphereClusterList) DeepCopyInto(out *VSphereClusterList) { *out = *in @@ -670,6 +697,11 @@ func (in *VSphereClusterStatus) DeepCopyInto(out *VSphereClusterStatus) { (*out)[key] = *val.DeepCopy() } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereClusterV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereClusterStatus. @@ -772,6 +804,28 @@ func (in *VSphereClusterTemplateSpec) DeepCopy() *VSphereClusterTemplateSpec { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereClusterV1Beta2Status) DeepCopyInto(out *VSphereClusterV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereClusterV1Beta2Status. +func (in *VSphereClusterV1Beta2Status) DeepCopy() *VSphereClusterV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereClusterV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VSphereDeploymentZone) DeepCopyInto(out *VSphereDeploymentZone) { *out = *in @@ -867,6 +921,11 @@ func (in *VSphereDeploymentZoneStatus) DeepCopyInto(out *VSphereDeploymentZoneSt (*in)[i].DeepCopyInto(&(*out)[i]) } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereDeploymentZoneV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereDeploymentZoneStatus. @@ -879,6 +938,28 @@ func (in *VSphereDeploymentZoneStatus) DeepCopy() *VSphereDeploymentZoneStatus { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereDeploymentZoneV1Beta2Status) DeepCopyInto(out *VSphereDeploymentZoneV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereDeploymentZoneV1Beta2Status. +func (in *VSphereDeploymentZoneV1Beta2Status) DeepCopy() *VSphereDeploymentZoneV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereDeploymentZoneV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VSphereDisk) DeepCopyInto(out *VSphereDisk) { *out = *in @@ -1112,6 +1193,11 @@ func (in *VSphereMachineStatus) DeepCopyInto(out *VSphereMachineStatus) { (*in)[i].DeepCopyInto(&(*out)[i]) } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereMachineV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereMachineStatus. @@ -1215,6 +1301,28 @@ func (in *VSphereMachineTemplateSpec) DeepCopy() *VSphereMachineTemplateSpec { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereMachineV1Beta2Status) DeepCopyInto(out *VSphereMachineV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereMachineV1Beta2Status. +func (in *VSphereMachineV1Beta2Status) DeepCopy() *VSphereMachineV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereMachineV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VSphereVM) DeepCopyInto(out *VSphereVM) { *out = *in @@ -1358,6 +1466,11 @@ func (in *VSphereVMStatus) DeepCopyInto(out *VSphereVMStatus) { *out = new(string) **out = **in } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereVMV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereVMStatus. @@ -1370,6 +1483,28 @@ func (in *VSphereVMStatus) DeepCopy() *VSphereVMStatus { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereVMV1Beta2Status) DeepCopyInto(out *VSphereVMV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereVMV1Beta2Status. +func (in *VSphereVMV1Beta2Status) DeepCopy() *VSphereVMV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereVMV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VirtualMachine) DeepCopyInto(out *VirtualMachine) { *out = *in diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspherecluster_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspherecluster_types.go index 268e11b7c0e..e3eda762465 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspherecluster_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspherecluster_types.go @@ -34,6 +34,95 @@ const ( ProviderServiceAccountFinalizer = "providerserviceaccount.vmware.infrastructure.cluster.x-k8s.io" ) +// VSphereCluster's Ready condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterReadyV1Beta2Condition is true if the VSphereCluster's deletionTimestamp is not set, VSphereCluster's + // ResourcePolicyReady, NetworkReady, LoadBalancerReady, ProviderServiceAccountsReady and ServiceDiscoveryReady conditions are true. + VSphereClusterReadyV1Beta2Condition = clusterv1.ReadyV1Beta2Condition + + // VSphereClusterReadyV1Beta2Reason surfaces when the VSphereCluster readiness criteria is met. + VSphereClusterReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterNotReadyV1Beta2Reason surfaces when the VSphereCluster readiness criteria is not met. + VSphereClusterNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterReadyUnknownV1Beta2Reason surfaces when at least one VSphereCluster readiness criteria is unknown + // and no VSphereCluster readiness criteria is not met. + VSphereClusterReadyUnknownV1Beta2Reason = clusterv1.ReadyUnknownV1Beta2Reason +) + +// VSphereCluster's ResourcePolicyReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterResourcePolicyReadyV1Beta2Condition documents the status of the ResourcePolicy for a VSphereCluster. + VSphereClusterResourcePolicyReadyV1Beta2Condition = "ResourcePolicyReady" + + // VSphereClusterResourcePolicyReadyV1Beta2Reason surfaces when the ResourcePolicy for a VSphereCluster is ready. + VSphereClusterResourcePolicyReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterResourcePolicyNotReadyV1Beta2Reason surfaces when the ResourcePolicy for a VSphereCluster is not ready. + VSphereClusterResourcePolicyNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterResourcePolicyReadyDeletingV1Beta2Reason surfaces when the resource policy for a VSphereCluster is being deleted. + VSphereClusterResourcePolicyReadyDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereCluster's NetworkReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterNetworkReadyV1Beta2Condition documents the status of the network for a VSphereCluster. + VSphereClusterNetworkReadyV1Beta2Condition = "NetworkReady" + + // VSphereClusterNetworkReadyV1Beta2Reason surfaces when the network for a VSphereCluster is ready. + VSphereClusterNetworkReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterNetworkNotReadyV1Beta2Reason surfaces when the network for a VSphereCluster is not ready. + VSphereClusterNetworkNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterNetworkReadyDeletingV1Beta2Reason surfaces when the network for a VSphereCluster is being deleted. + VSphereClusterNetworkReadyDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereCluster's LoadBalancerReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterLoadBalancerReadyV1Beta2Condition documents the status of the LoadBalancer for a VSphereCluster. + VSphereClusterLoadBalancerReadyV1Beta2Condition = "LoadBalancerReady" + + // VSphereClusterLoadBalancerReadyV1Beta2Reason surfaces when the LoadBalancer for a VSphereCluster is ready. + VSphereClusterLoadBalancerReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterLoadBalancerNotReadyV1Beta2Reason surfaces when the LoadBalancer for a VSphereCluster is not ready. + VSphereClusterLoadBalancerNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason + + // VSphereClusterLoadBalancerWaitingForIPV1Beta2Reason surfaces when the LoadBalancer for a VSphereCluster is waiting for an IP to be assigned. + VSphereClusterLoadBalancerWaitingForIPV1Beta2Reason = "WaitingForIP" + + // VSphereClusterLoadBalancerDeletingV1Beta2Reason surfaces when the LoadBalancer for a VSphereCluster is being deleted. + VSphereClusterLoadBalancerDeletingV1Beta2Reason = clusterv1.DeletingV1Beta2Reason +) + +// VSphereCluster's ProviderServiceAccountsReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterProviderServiceAccountsReadyV1Beta2Condition documents the status of the provider service accounts for a VSphereCluster. + VSphereClusterProviderServiceAccountsReadyV1Beta2Condition = "ProviderServiceAccountsReady" + + // VSphereClusterProviderServiceAccountsReadyV1Beta2Reason surfaces when the provider service accounts for a VSphereCluster is ready. + VSphereClusterProviderServiceAccountsReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterProviderServiceAccountsNotReadyV1Beta2Reason surfaces when the provider service accounts for a VSphereCluster is not ready. + VSphereClusterProviderServiceAccountsNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason +) + +// VSphereCluster's ServiceDiscoveryReady condition and corresponding reasons that will be used in v1Beta2 API version. +const ( + // VSphereClusterServiceDiscoveryReadyV1Beta2Condition documents the status of the service discovery for a VSphereCluster. + VSphereClusterServiceDiscoveryReadyV1Beta2Condition = "ServiceDiscoveryReady" + + // VSphereClusterServiceDiscoveryReadyV1Beta2Reason surfaces when the service discovery for a VSphereCluster is ready. + VSphereClusterServiceDiscoveryReadyV1Beta2Reason = clusterv1.ReadyV1Beta2Reason + + // VSphereClusterServiceDiscoveryNotReadyV1Beta2Reason surfaces when the service discovery for a VSphereCluster is not ready. + VSphereClusterServiceDiscoveryNotReadyV1Beta2Reason = clusterv1.NotReadyV1Beta2Reason +) + // VSphereClusterSpec defines the desired state of VSphereCluster. type VSphereClusterSpec struct { // +optional @@ -59,6 +148,23 @@ type VSphereClusterStatus struct { // FailureDomains is a list of failure domain objects synced from the // infrastructure provider. FailureDomains clusterv1.FailureDomains `json:"failureDomains,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereCluster's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereClusterV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereClusterV1Beta2Status groups all the fields that will be added or modified in VSphereClusterStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereClusterV1Beta2Status struct { + // conditions represents the observations of a VSphereCluster's current state. + // Known condition types are Ready, ResourcePolicyReady, NetworkReady, LoadBalancerReady, + // ProviderServiceAccountsReady, ServiceDiscoveryReady and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // +kubebuilder:object:root=true @@ -94,6 +200,22 @@ func (r *VSphereCluster) SetConditions(conditions clusterv1.Conditions) { r.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (r *VSphereCluster) GetV1Beta2Conditions() []metav1.Condition { + if r.Status.V1Beta2 == nil { + return nil + } + return r.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (r *VSphereCluster) SetV1Beta2Conditions(conditions []metav1.Condition) { + if r.Status.V1Beta2 == nil { + r.Status.V1Beta2 = &VSphereClusterV1Beta2Status{} + } + r.Status.V1Beta2.Conditions = conditions +} + func init() { objectTypes = append(objectTypes, &VSphereCluster{}, &VSphereClusterList{}) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspheremachine_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspheremachine_types.go index 5f5cd271378..4b0a91319f5 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspheremachine_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/vspheremachine_types.go @@ -176,6 +176,22 @@ type VSphereMachineStatus struct { // Conditions defines current service state of the VSphereMachine. // +optional Conditions clusterv1.Conditions `json:"conditions,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in VSphereMachine's status with the V1Beta2 version. + // +optional + V1Beta2 *VSphereMachineV1Beta2Status `json:"v1beta2,omitempty"` +} + +// VSphereMachineV1Beta2Status groups all the fields that will be added or modified in VSphereMachineStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type VSphereMachineV1Beta2Status struct { + // conditions represents the observations of a VSphereMachine's current state. + // Known condition types are Ready, VirtualMachineProvisioned and Paused. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // VSphereMachine is the Schema for the vspheremachines API @@ -214,6 +230,22 @@ func (r *VSphereMachine) SetConditions(conditions clusterv1.Conditions) { r.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (r *VSphereMachine) GetV1Beta2Conditions() []metav1.Condition { + if r.Status.V1Beta2 == nil { + return nil + } + return r.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (r *VSphereMachine) SetV1Beta2Conditions(conditions []metav1.Condition) { + if r.Status.V1Beta2 == nil { + r.Status.V1Beta2 = &VSphereMachineV1Beta2Status{} + } + r.Status.V1Beta2.Conditions = conditions +} + func init() { objectTypes = append(objectTypes, &VSphereMachine{}, &VSphereMachineList{}) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/zz_generated.deepcopy.go index 09e4af4637c..7358ccaa1ca 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1/zz_generated.deepcopy.go @@ -23,6 +23,7 @@ package v1beta1 import ( "k8s.io/api/core/v1" rbacv1 "k8s.io/api/rbac/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" apiv1beta1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/errors" @@ -220,6 +221,11 @@ func (in *VSphereClusterStatus) DeepCopyInto(out *VSphereClusterStatus) { (*out)[key] = *val.DeepCopy() } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereClusterV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereClusterStatus. @@ -322,6 +328,28 @@ func (in *VSphereClusterTemplateSpec) DeepCopy() *VSphereClusterTemplateSpec { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereClusterV1Beta2Status) DeepCopyInto(out *VSphereClusterV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereClusterV1Beta2Status. +func (in *VSphereClusterV1Beta2Status) DeepCopy() *VSphereClusterV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereClusterV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VSphereMachine) DeepCopyInto(out *VSphereMachine) { *out = *in @@ -448,6 +476,11 @@ func (in *VSphereMachineStatus) DeepCopyInto(out *VSphereMachineStatus) { (*in)[i].DeepCopyInto(&(*out)[i]) } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(VSphereMachineV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereMachineStatus. @@ -573,6 +606,28 @@ func (in *VSphereMachineTemplateStatus) DeepCopy() *VSphereMachineTemplateStatus return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *VSphereMachineV1Beta2Status) DeepCopyInto(out *VSphereMachineV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]metav1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new VSphereMachineV1Beta2Status. +func (in *VSphereMachineV1Beta2Status) DeepCopy() *VSphereMachineV1Beta2Status { + if in == nil { + return nil + } + out := new(VSphereMachineV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *VSphereMachineVolume) DeepCopyInto(out *VSphereMachineVolume) { *out = *in diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/clustermodule_reconciler.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/clustermodule_reconciler.go index fa1edcd16e0..a2bed77da17 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/clustermodule_reconciler.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/clustermodule_reconciler.go @@ -28,6 +28,7 @@ import ( controlplanev1 "sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1" "sigs.k8s.io/cluster-api/util" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" "sigs.k8s.io/controller-runtime/pkg/controller" @@ -69,6 +70,12 @@ func (r Reconciler) Reconcile(ctx context.Context, clusterCtx *capvcontext.Clust if !clustermodule.IsClusterCompatible(clusterCtx) { conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition, infrav1.VCenterVersionIncompatibleReason, clusterv1.ConditionSeverityInfo, "vCenter version %s does not support cluster modules", clusterCtx.VSphereCluster.Status.VCenterVersion) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterModulesInvalidVCenterVersionV1Beta2Reason, + Message: fmt.Sprintf("vCenter version %s does not support cluster modules", clusterCtx.VSphereCluster.Status.VCenterVersion), + }) log.V(5).Info(fmt.Sprintf("vCenter version %s does not support cluster modules to implement anti affinity (vCenter >= 7 required)", clusterCtx.VSphereCluster.Status.VCenterVersion)) return reconcile.Result{}, nil } @@ -170,11 +177,23 @@ func (r Reconciler) Reconcile(ctx context.Context, clusterCtx *capvcontext.Clust } conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition, infrav1.ClusterModuleSetupFailedReason, clusterv1.ConditionSeverityWarning, generateClusterModuleErrorMessage(modErrs)) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterClusterModulesNotReadyV1Beta2Reason, + Message: generateClusterModuleErrorMessage(modErrs), + }) + return reconcile.Result{}, err case len(modErrs) == 0 && len(clusterModuleSpecs) > 0: conditions.MarkTrue(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition) default: conditions.Delete(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition) } + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereClusterClusterModulesReadyV1Beta2Reason, + }) return reconcile.Result{}, err } @@ -319,7 +338,7 @@ type clusterModError struct { func generateClusterModuleErrorMessage(errList []clusterModError) string { sb := strings.Builder{} - sb.WriteString("failed to create cluster modules for: ") + sb.WriteString("Failed to create cluster modules for: ") for _, e := range errList { sb.WriteString(fmt.Sprintf("%s %s, ", e.name, e.err.Error())) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/serviceaccount_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/serviceaccount_controller.go index 54435f02ad6..05f5d06d99b 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/serviceaccount_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/serviceaccount_controller.go @@ -36,6 +36,7 @@ import ( clusterutilv1 "sigs.k8s.io/cluster-api/util" "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" "sigs.k8s.io/cluster-api/util/patch" "sigs.k8s.io/cluster-api/util/predicates" ctrl "sigs.k8s.io/controller-runtime" @@ -52,7 +53,7 @@ import ( "sigs.k8s.io/cluster-api-provider-vsphere/pkg/util" ) -// +kubebuilder:rbac:groups=vmware.infrastructure.cluster.x-k8s.io,resources=providerserviceaccounts,verbs=get;list;watch; +// +kubebuilder:rbac:groups=vmware.infrastructure.cluster.x-k8s.io,resources=providerserviceaccounts,verbs=get;list;watch;patch;update // +kubebuilder:rbac:groups=vmware.infrastructure.cluster.x-k8s.io,resources=providerserviceaccounts/status,verbs=get;update;patch // +kubebuilder:rbac:groups="",resources=serviceaccounts,verbs=get;list;watch;create;update;patch;delete // +kubebuilder:rbac:groups="",resources=secrets,verbs=get @@ -129,6 +130,7 @@ func (r *ServiceAccountReconciler) Reconcile(ctx context.Context, req reconcile. // Pause reconciliation if entire VSphereCluster or Cluster is paused // Note: Pause on the ProviderServiceAccount level is handled in ensureProviderServiceAccounts. + // In future we might consider to surface a separate paused condition for this controller. if annotations.IsPaused(cluster, vsphereCluster) { log.Info("Reconciliation is paused for this object") return reconcile.Result{}, nil @@ -150,7 +152,7 @@ func (r *ServiceAccountReconciler) Reconcile(ctx context.Context, req reconcile. // Always issue a patch when exiting this function so changes to the // resource are patched back to the API server. defer func() { - if err := clusterContext.Patch(ctx); err != nil { + if err := r.patch(ctx, clusterContext); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) } }() @@ -188,14 +190,37 @@ func (r *ServiceAccountReconciler) Reconcile(ctx context.Context, req reconcile. }) } +func (r *ServiceAccountReconciler) patch(ctx context.Context, clusterCtx *vmwarecontext.ClusterContext) error { + // NOTE: this controller only owns the ProviderServiceAccountsReady condition on the VSphereCluster object. + return clusterCtx.PatchHelper.Patch(ctx, clusterCtx.VSphereCluster, + patch.WithOwnedConditions{Conditions: []clusterv1.ConditionType{ + vmwarev1.ProviderServiceAccountsReadyCondition, + }}, + patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + vmwarev1.VSphereClusterProviderServiceAccountsReadyV1Beta2Condition, + }}, + ) +} + // reconcileNormal handles create and update events for ProviderServiceAccounts. func (r *ServiceAccountReconciler) reconcileNormal(ctx context.Context, guestClusterCtx *vmwarecontext.GuestClusterContext) (_ reconcile.Result, reterr error) { defer func() { if reterr != nil { conditions.MarkFalse(guestClusterCtx.VSphereCluster, vmwarev1.ProviderServiceAccountsReadyCondition, vmwarev1.ProviderServiceAccountsReconciliationFailedReason, clusterv1.ConditionSeverityWarning, reterr.Error()) + v1beta2conditions.Set(guestClusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterProviderServiceAccountsReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterProviderServiceAccountsNotReadyV1Beta2Reason, + Message: reterr.Error(), + }) } else { conditions.MarkTrue(guestClusterCtx.VSphereCluster, vmwarev1.ProviderServiceAccountsReadyCondition) + v1beta2conditions.Set(guestClusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterProviderServiceAccountsReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterProviderServiceAccountsReadyV1Beta2Reason, + }) } }() diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/servicediscovery_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/servicediscovery_controller.go index 7c9dbe86e01..5c8d2d5e0a3 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/servicediscovery_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/servicediscovery_controller.go @@ -41,6 +41,7 @@ import ( clusterutilv1 "sigs.k8s.io/cluster-api/util" "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" "sigs.k8s.io/cluster-api/util/patch" "sigs.k8s.io/cluster-api/util/predicates" ctrl "sigs.k8s.io/controller-runtime" @@ -61,9 +62,7 @@ import ( const ( clusterNotReadyRequeueTime = time.Minute * 2 - supervisorLoadBalancerSvcNamespace = "kube-system" - supervisorLoadBalancerSvcName = "kube-apiserver-lb-svc" - supervisorAPIServerPort = 6443 + supervisorAPIServerPort = 6443 supervisorHeadlessSvcNamespace = "default" supervisorHeadlessSvcName = "supervisor" @@ -173,6 +172,7 @@ func (r *serviceDiscoveryReconciler) Reconcile(ctx context.Context, req reconcil log = log.WithValues("Cluster", klog.KObj(cluster)) ctx = ctrl.LoggerInto(ctx, log) + // In future we might consider to surface a separate paused condition for this controller. if annotations.IsPaused(cluster, vsphereCluster) { log.Info("Reconciliation is paused for this object") return ctrl.Result{}, nil @@ -194,7 +194,7 @@ func (r *serviceDiscoveryReconciler) Reconcile(ctx context.Context, req reconcil // Always issue a patch when exiting this function so changes to the // resource are patched back to the API server. defer func() { - if err := clusterContext.Patch(ctx); err != nil { + if err := r.patch(ctx, clusterContext); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) } }() @@ -223,10 +223,28 @@ func (r *serviceDiscoveryReconciler) Reconcile(ctx context.Context, req reconcil }) } +func (r *serviceDiscoveryReconciler) patch(ctx context.Context, clusterCtx *vmwarecontext.ClusterContext) error { + // NOTE: this controller only owns the ServiceDiscoveryReady condition on the VSphereCluster object. + return clusterCtx.PatchHelper.Patch(ctx, clusterCtx.VSphereCluster, + patch.WithOwnedConditions{Conditions: []clusterv1.ConditionType{ + vmwarev1.ServiceDiscoveryReadyCondition, + }}, + patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Condition, + }}, + ) +} + func (r *serviceDiscoveryReconciler) reconcileNormal(ctx context.Context, guestClusterCtx *vmwarecontext.GuestClusterContext) error { if err := r.reconcileSupervisorHeadlessService(ctx, guestClusterCtx); err != nil { conditions.MarkFalse(guestClusterCtx.VSphereCluster, vmwarev1.ServiceDiscoveryReadyCondition, vmwarev1.SupervisorHeadlessServiceSetupFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(guestClusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterServiceDiscoveryNotReadyV1Beta2Reason, + Message: err.Error(), + }) return errors.Wrapf(err, "failed to reconcile supervisor headless Service") } @@ -265,6 +283,12 @@ func (r *serviceDiscoveryReconciler) reconcileSupervisorHeadlessService(ctx cont // There is no need to return an error to keep re-trying. conditions.MarkFalse(guestClusterCtx.VSphereCluster, vmwarev1.ServiceDiscoveryReadyCondition, vmwarev1.SupervisorHeadlessServiceSetupFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(guestClusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterServiceDiscoveryNotReadyV1Beta2Reason, + Message: err.Error(), + }) return nil } @@ -314,6 +338,11 @@ func (r *serviceDiscoveryReconciler) reconcileSupervisorHeadlessService(ctx cont } conditions.MarkTrue(guestClusterCtx.VSphereCluster, vmwarev1.ServiceDiscoveryReadyCondition) + v1beta2conditions.Set(guestClusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Reason, + }) return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspherecluster_reconciler.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspherecluster_reconciler.go index 397663de193..549ff90b9c8 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspherecluster_reconciler.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspherecluster_reconciler.go @@ -23,16 +23,19 @@ import ( "github.com/pkg/errors" apierrors "k8s.io/apimachinery/pkg/api/errors" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/types" kerrors "k8s.io/apimachinery/pkg/util/errors" "k8s.io/client-go/tools/record" "k8s.io/klog/v2" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" - "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/collections" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/finalizers" "sigs.k8s.io/cluster-api/util/patch" + "sigs.k8s.io/cluster-api/util/paused" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -82,6 +85,11 @@ func (r *ClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, err } + // Add finalizer first if not set to avoid the race condition between init and delete. + if finalizerAdded, err := finalizers.EnsureFinalizer(ctx, r.Client, vsphereCluster, vmwarev1.ClusterFinalizer); err != nil || finalizerAdded { + return ctrl.Result{}, err + } + // Fetch the Cluster. cluster, err := clusterutilv1.GetOwnerCluster(ctx, r.Client, vsphereCluster.ObjectMeta) if err != nil { @@ -90,14 +98,6 @@ func (r *ClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ if cluster != nil { log = log.WithValues("Cluster", klog.KObj(cluster)) ctx = ctrl.LoggerInto(ctx, log) - - if annotations.IsPaused(cluster, vsphereCluster) { - log.Info("Reconciliation is paused for this object") - return ctrl.Result{}, nil - } - } else if annotations.HasPaused(vsphereCluster) { - log.Info("Reconciliation is paused for this object") - return ctrl.Result{}, nil } // Build the patch helper. @@ -106,6 +106,10 @@ func (r *ClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, err } + if isPaused, requeue, err := paused.EnsurePausedCondition(ctx, r.Client, cluster, vsphereCluster); err != nil || isPaused || requeue { + return ctrl.Result{}, err + } + // Build the cluster context. clusterContext := &vmware.ClusterContext{ Cluster: cluster, @@ -115,7 +119,7 @@ func (r *ClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ // Always close the context when exiting this function so we can persist any vsphereCluster changes. defer func() { - if err := clusterContext.Patch(ctx); err != nil { + if err := r.patch(ctx, clusterContext); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) } }() @@ -131,17 +135,66 @@ func (r *ClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, nil } - // If the VSphereCluster doesn't have our finalizer, add it. - // Requeue immediately after adding finalizer to avoid the race condition between init and delete - if !controllerutil.ContainsFinalizer(vsphereCluster, vmwarev1.ClusterFinalizer) { - controllerutil.AddFinalizer(vsphereCluster, vmwarev1.ClusterFinalizer) - return ctrl.Result{}, nil - } - // Handle non-deleted clusters return ctrl.Result{}, r.reconcileNormal(ctx, clusterContext) } +func (r *ClusterReconciler) patch(ctx context.Context, clusterCtx *vmware.ClusterContext) error { + // always update the readyCondition. + conditions.SetSummary(clusterCtx.VSphereCluster, + conditions.WithConditions( + vmwarev1.ResourcePolicyReadyCondition, + vmwarev1.ClusterNetworkReadyCondition, + vmwarev1.LoadBalancerReadyCondition, + ), + ) + + if err := v1beta2conditions.SetSummaryCondition(clusterCtx.VSphereCluster, clusterCtx.VSphereCluster, vmwarev1.VSphereClusterReadyV1Beta2Condition, + v1beta2conditions.ForConditionTypes{ + vmwarev1.VSphereClusterResourcePolicyReadyV1Beta2Condition, + vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + // ProviderServiceAccountsReady and ServiceDiscoveryReady will be set by other controllers after + // the API server in the workload cluster is up and running. + vmwarev1.VSphereClusterProviderServiceAccountsReadyV1Beta2Condition, + vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Condition, + }, + v1beta2conditions.IgnoreTypesIfMissing{ + vmwarev1.VSphereClusterProviderServiceAccountsReadyV1Beta2Condition, + vmwarev1.VSphereClusterServiceDiscoveryReadyV1Beta2Condition, + }, + // Using a custom merge strategy to override reasons applied during merge. + v1beta2conditions.CustomMergeStrategy{ + MergeStrategy: v1beta2conditions.DefaultMergeStrategy( + // Use custom reasons. + v1beta2conditions.ComputeReasonFunc(v1beta2conditions.GetDefaultComputeMergeReasonFunc( + vmwarev1.VSphereClusterNotReadyV1Beta2Reason, + vmwarev1.VSphereClusterReadyUnknownV1Beta2Reason, + vmwarev1.VSphereClusterReadyV1Beta2Reason, + )), + ), + }, + ); err != nil { + return errors.Wrapf(err, "failed to set %s condition", vmwarev1.VSphereClusterReadyV1Beta2Condition) + } + + return clusterCtx.PatchHelper.Patch(ctx, clusterCtx.VSphereCluster, + patch.WithOwnedConditions{Conditions: []clusterv1.ConditionType{ + vmwarev1.ResourcePolicyReadyCondition, + vmwarev1.ClusterNetworkReadyCondition, + vmwarev1.LoadBalancerReadyCondition, + }}, + patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + clusterv1.PausedV1Beta2Condition, + vmwarev1.VSphereClusterReadyV1Beta2Condition, + vmwarev1.VSphereClusterResourcePolicyReadyV1Beta2Condition, + vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + // NOTE: ProviderServiceAccountsReady and ServiceDiscoveryReady are not owned by this controller + }}, + ) +} + func (r *ClusterReconciler) reconcileDelete(clusterCtx *vmware.ClusterContext) { deletingConditionTypes := []clusterv1.ConditionType{ vmwarev1.ResourcePolicyReadyCondition, @@ -155,6 +208,24 @@ func (r *ClusterReconciler) reconcileDelete(clusterCtx *vmware.ClusterContext) { } } + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterResourcePolicyReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterResourcePolicyReadyDeletingV1Beta2Reason, + }) + + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkReadyDeletingV1Beta2Reason, + }) + + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterLoadBalancerDeletingV1Beta2Reason, + }) + // Cluster is deleted so remove the finalizer. controllerutil.RemoveFinalizer(clusterCtx.VSphereCluster, vmwarev1.ClusterFinalizer) } @@ -175,11 +246,23 @@ func (r *ClusterReconciler) reconcileNormal(ctx context.Context, clusterCtx *vmw resourcePolicyName, err := r.ResourcePolicyService.ReconcileResourcePolicy(ctx, clusterCtx) if err != nil { conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.ResourcePolicyReadyCondition, vmwarev1.ResourcePolicyCreationFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterResourcePolicyReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterResourcePolicyNotReadyV1Beta2Reason, + Message: err.Error(), + }) return errors.Wrapf(err, "failed to configure resource policy for vsphereCluster %s/%s", clusterCtx.VSphereCluster.Namespace, clusterCtx.VSphereCluster.Name) } conditions.MarkTrue(clusterCtx.VSphereCluster, vmwarev1.ResourcePolicyReadyCondition) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterResourcePolicyReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterResourcePolicyReadyV1Beta2Reason, + }) + clusterCtx.VSphereCluster.Status.ResourcePolicyName = resourcePolicyName // Configure the cluster for the cluster network @@ -204,6 +287,11 @@ func (r *ClusterReconciler) reconcileControlPlaneEndpoint(ctx context.Context, c if !clusterCtx.Cluster.Spec.ControlPlaneEndpoint.IsZero() { clusterCtx.VSphereCluster.Spec.ControlPlaneEndpoint.Host = clusterCtx.Cluster.Spec.ControlPlaneEndpoint.Host clusterCtx.VSphereCluster.Spec.ControlPlaneEndpoint.Port = clusterCtx.Cluster.Spec.ControlPlaneEndpoint.Port + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Reason, + }) if r.NetworkProvider.HasLoadBalancer() { conditions.MarkTrue(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition) } @@ -214,6 +302,11 @@ func (r *ClusterReconciler) reconcileControlPlaneEndpoint(ctx context.Context, c } if !clusterCtx.VSphereCluster.Spec.ControlPlaneEndpoint.IsZero() { + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Reason, + }) if r.NetworkProvider.HasLoadBalancer() { conditions.MarkTrue(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspheremachinetemplate_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspheremachinetemplate_controller.go index e2fdab4354a..0bc971b5d92 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspheremachinetemplate_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware/vspheremachinetemplate_controller.go @@ -74,6 +74,11 @@ func (r *vSphereMachineTemplateReconciler) Reconcile(ctx context.Context, req ct return reconcile.Result{}, err } + // If ClassName is not set, there is nothing to do. + if vSphereMachineTemplate.Spec.Template.Spec.ClassName == "" { + return reconcile.Result{}, nil + } + // Fetch the VirtualMachineClass vmClass := &vmoprv1.VirtualMachineClass{} if err := r.Client.Get(ctx, client.ObjectKey{Namespace: req.Namespace, Name: vSphereMachineTemplate.Spec.Template.Spec.ClassName}, vmClass); err != nil { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_controller.go index 47d1ee9ce43..fafac909de7 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_controller.go @@ -83,7 +83,7 @@ func AddClusterControllerToManager(ctx context.Context, controllerManagerCtx *ca &vmwarev1.VSphereMachine{}, handler.EnqueueRequestsFromMapFunc(reconciler.VSphereMachineToCluster), ). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)) + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)) // Conditionally add a Watch for topologyv1.Zone when the feature gate is enabled if feature.Gates.Enabled(feature.NamespaceScopedZones) { @@ -157,7 +157,7 @@ func AddClusterControllerToManager(ctx context.Context, controllerManagerCtx *ca &handler.EnqueueRequestForObject{}, ), ). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). WithEventFilter(predicates.ResourceIsNotExternallyManaged(mgr.GetScheme(), predicateLog)). Build(reconciler) if err != nil { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_reconciler.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_reconciler.go index 198f2875646..bf7418de007 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_reconciler.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherecluster_reconciler.go @@ -33,9 +33,11 @@ import ( "k8s.io/utils/ptr" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" - "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/finalizers" "sigs.k8s.io/cluster-api/util/patch" + "sigs.k8s.io/cluster-api/util/paused" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -71,21 +73,19 @@ func (r *clusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, err } + // Add finalizer first if not set to avoid the race condition between init and delete. + if finalizerAdded, err := finalizers.EnsureFinalizer(ctx, r.Client, vsphereCluster, infrav1.ClusterFinalizer); err != nil || finalizerAdded { + return ctrl.Result{}, err + } + // Fetch the CAPI Cluster. cluster, err := clusterutilv1.GetOwnerCluster(ctx, r.Client, vsphereCluster.ObjectMeta) if err != nil { return reconcile.Result{}, err } - if cluster == nil { - log.Info("Waiting for Cluster controller to set OwnerRef on VSphereCluster") - return reconcile.Result{}, nil - } - log = log.WithValues("Cluster", klog.KObj(cluster)) - ctx = ctrl.LoggerInto(ctx, log) - - if annotations.IsPaused(cluster, vsphereCluster) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil + if cluster != nil { + log = log.WithValues("Cluster", klog.KObj(cluster)) + ctx = ctrl.LoggerInto(ctx, log) } // Create the patch helper. @@ -94,6 +94,10 @@ func (r *clusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, err } + if isPaused, requeue, err := paused.EnsurePausedCondition(ctx, r.Client, cluster, vsphereCluster); err != nil || isPaused || requeue { + return ctrl.Result{}, err + } + // Create the cluster context for this request. clusterContext := &capvcontext.ClusterContext{ Cluster: cluster, @@ -104,7 +108,7 @@ func (r *clusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ // Always issue a patch when exiting this function so changes to the // resource are patched back to the API server. defer func() { - if err := clusterContext.Patch(ctx); err != nil { + if err := r.patch(ctx, clusterContext); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) } }() @@ -114,10 +118,8 @@ func (r *clusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return r.reconcileDelete(ctx, clusterContext) } - // If the VSphereCluster doesn't have our finalizer, add it. - // Requeue immediately after adding finalizer to avoid the race condition between init and delete - if !ctrlutil.ContainsFinalizer(vsphereCluster, infrav1.ClusterFinalizer) { - ctrlutil.AddFinalizer(vsphereCluster, infrav1.ClusterFinalizer) + if cluster == nil { + log.Info("Waiting for Cluster controller to set OwnerRef on VSphereCluster") return reconcile.Result{}, nil } @@ -125,13 +127,79 @@ func (r *clusterReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return r.reconcileNormal(ctx, clusterContext) } +// patch updates the VSphereCluster and its status on the API server. +func (r *clusterReconciler) patch(ctx context.Context, clusterCtx *capvcontext.ClusterContext) error { + // always update the readyCondition. + conditions.SetSummary(clusterCtx.VSphereCluster, + conditions.WithConditions( + infrav1.VCenterAvailableCondition, + ), + ) + + if err := v1beta2conditions.SetSummaryCondition(clusterCtx.VSphereCluster, clusterCtx.VSphereCluster, infrav1.VSphereClusterReadyV1Beta2Condition, + v1beta2conditions.ForConditionTypes{ + infrav1.VSphereClusterVCenterAvailableV1Beta2Condition, + // FailureDomainsReady and ClusterModuelsReady may not be always set. + infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + }, + v1beta2conditions.IgnoreTypesIfMissing{ + infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + }, + // Using a custom merge strategy to override reasons applied during merge. + v1beta2conditions.CustomMergeStrategy{ + MergeStrategy: v1beta2conditions.DefaultMergeStrategy( + // Use custom reasons. + v1beta2conditions.ComputeReasonFunc(v1beta2conditions.GetDefaultComputeMergeReasonFunc( + infrav1.VSphereClusterNotReadyV1Beta2Reason, + infrav1.VSphereClusterReadyUnknownV1Beta2Reason, + infrav1.VSphereClusterReadyV1Beta2Reason, + )), + ), + }, + ); err != nil { + return pkgerrors.Wrapf(err, "failed to set %s condition", infrav1.VSphereClusterReadyV1Beta2Condition) + } + + return clusterCtx.PatchHelper.Patch(ctx, clusterCtx.VSphereCluster, + patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + clusterv1.PausedV1Beta2Condition, + infrav1.VSphereClusterReadyV1Beta2Condition, + infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + infrav1.VSphereClusterVCenterAvailableV1Beta2Condition, + infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + }}, + ) +} + func (r *clusterReconciler) reconcileDelete(ctx context.Context, clusterCtx *capvcontext.ClusterContext) (reconcile.Result, error) { log := ctrl.LoggerFrom(ctx) - vsphereMachines, err := r.vmService.GetMachinesInCluster(ctx, clusterCtx.Cluster.Namespace, clusterCtx.Cluster.Name) - if err != nil { - return reconcile.Result{}, pkgerrors.Wrapf(err, - "unable to list VSphereMachines part of VSphereCluster %s/%s", clusterCtx.VSphereCluster.Namespace, clusterCtx.VSphereCluster.Name) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterVCenterAvailableDeletingV1Beta2Reason, + }) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterClusterModulesDeletingV1Beta2Reason, + }) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterFailureDomainsDeletingV1Beta2Reason, + }) + + var vsphereMachines []client.Object + var err error + if clusterCtx.Cluster != nil { + vsphereMachines, err = r.vmService.GetMachinesInCluster(ctx, clusterCtx.Cluster.Namespace, clusterCtx.Cluster.Name) + if err != nil { + return reconcile.Result{}, pkgerrors.Wrapf(err, + "unable to list VSphereMachines part of VSphereCluster %s/%s", clusterCtx.VSphereCluster.Namespace, clusterCtx.VSphereCluster.Name) + } } if len(vsphereMachines) > 0 { @@ -186,37 +254,74 @@ func (r *clusterReconciler) reconcileDelete(ctx context.Context, clusterCtx *cap func (r *clusterReconciler) reconcileNormal(ctx context.Context, clusterCtx *capvcontext.ClusterContext) (reconcile.Result, error) { log := ctrl.LoggerFrom(ctx) + // Reconcile failure domains. ok, err := r.reconcileDeploymentZones(ctx, clusterCtx) if err != nil { + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterFailureDomainsNotReadyV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, err } if !ok { - log.Info("Waiting for failure domains to be reconciled") return reconcile.Result{RequeueAfter: 10 * time.Second}, nil } + // Reconcile vCenter availability. if err := r.reconcileIdentitySecret(ctx, clusterCtx); err != nil { conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.VCenterAvailableCondition, infrav1.VCenterUnreachableReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterVCenterUnreachableV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, err } vcenterSession, err := r.reconcileVCenterConnectivity(ctx, clusterCtx) if err != nil { conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.VCenterAvailableCondition, infrav1.VCenterUnreachableReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterVCenterUnreachableV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, pkgerrors.Wrapf(err, "unexpected error while probing vcenter for %s", clusterCtx) } conditions.MarkTrue(clusterCtx.VSphereCluster, infrav1.VCenterAvailableCondition) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereClusterVCenterAvailableV1Beta2Reason, + }) + // Reconcile cluster modules. err = r.reconcileVCenterVersion(clusterCtx, vcenterSession) if err != nil || clusterCtx.VSphereCluster.Status.VCenterVersion == "" { - conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition, infrav1.MissingVCenterVersionReason, clusterv1.ConditionSeverityWarning, "vCenter version not set") + conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition, infrav1.MissingVCenterVersionReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterModulesInvalidVCenterVersionV1Beta2Reason, + Message: err.Error(), + }) log.Error(err, "could not reconcile vCenter version") } affinityReconcileResult, err := r.reconcileClusterModules(ctx, clusterCtx) if err != nil { conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.ClusterModulesAvailableCondition, infrav1.ClusterModuleSetupFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterClusterModulesReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterClusterModulesNotReadyV1Beta2Reason, + Message: err.Error(), + }) return affinityReconcileResult, err } @@ -290,13 +395,14 @@ func (r *clusterReconciler) reconcileVCenterConnectivity(ctx context.Context, cl func (r *clusterReconciler) reconcileVCenterVersion(clusterCtx *capvcontext.ClusterContext, s *session.Session) error { version, err := s.GetVersion() if err != nil { - return err + return pkgerrors.Wrapf(err, "invalid vCenter version") } clusterCtx.VSphereCluster.Status.VCenterVersion = version return nil } func (r *clusterReconciler) reconcileDeploymentZones(ctx context.Context, clusterCtx *capvcontext.ClusterContext) (bool, error) { + log := ctrl.LoggerFrom(ctx) // If there is no failure domain selector, skip reconciliation if clusterCtx.VSphereCluster.Spec.FailureDomainSelector == nil { return true, nil @@ -341,15 +447,33 @@ func (r *clusterReconciler) reconcileDeploymentZones(ctx context.Context, cluste clusterCtx.VSphereCluster.Status.FailureDomains = failureDomains if readyNotReported > 0 { + log.Info("Waiting for failure domains to be reconciled") conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.FailureDomainsAvailableCondition, infrav1.WaitingForFailureDomainStatusReason, clusterv1.ConditionSeverityInfo, "waiting for failure domains to report ready status") + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterFailureDomainsNotReadyV1Beta2Reason, + Message: "Waiting for failure domains to report ready status", + }) return false, nil } if len(failureDomains) > 0 { if notReady > 0 { conditions.MarkFalse(clusterCtx.VSphereCluster, infrav1.FailureDomainsAvailableCondition, infrav1.FailureDomainsSkippedReason, clusterv1.ConditionSeverityInfo, "one or more failure domains are not ready") + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterFailureDomainsNotReadyV1Beta2Reason, + Message: "One or more failure domains are not ready", + }) } else { conditions.MarkTrue(clusterCtx.VSphereCluster, infrav1.FailureDomainsAvailableCondition) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: infrav1.VSphereClusterFailureDomainsReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereClusterFailureDomainsReadyV1Beta2Reason, + }) } } else { // Remove the condition if failure domains do not exist diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vsphereclusteridentity_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vsphereclusteridentity_controller.go index bee4093d1e9..99faa68206f 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vsphereclusteridentity_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vsphereclusteridentity_controller.go @@ -29,9 +29,11 @@ import ( "k8s.io/klog/v2" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" - "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/finalizers" "sigs.k8s.io/cluster-api/util/patch" + "sigs.k8s.io/cluster-api/util/paused" "sigs.k8s.io/cluster-api/util/predicates" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" @@ -61,7 +63,7 @@ func AddVsphereClusterIdentityControllerToManager(ctx context.Context, controlle return ctrl.NewControllerManagedBy(mgr). For(&infrav1.VSphereClusterIdentity{}). WithOptions(options). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). Complete(reconciler) } @@ -72,8 +74,6 @@ type clusterIdentityReconciler struct { } func (r clusterIdentityReconciler) Reconcile(ctx context.Context, req reconcile.Request) (_ reconcile.Result, reterr error) { - log := ctrl.LoggerFrom(ctx) - identity := &infrav1.VSphereClusterIdentity{} if err := r.Client.Get(ctx, req.NamespacedName, identity); err != nil { if apierrors.IsNotFound(err) { @@ -83,9 +83,9 @@ func (r clusterIdentityReconciler) Reconcile(ctx context.Context, req reconcile. return reconcile.Result{}, err } - if annotations.HasPaused(identity) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil + // Add finalizer first if not set to avoid the race condition between init and delete. + if finalizerAdded, err := finalizers.EnsureFinalizer(ctx, r.Client, identity, infrav1.VSphereClusterIdentityFinalizer); err != nil || finalizerAdded { + return ctrl.Result{}, err } // Create the patch helper. @@ -94,10 +94,17 @@ func (r clusterIdentityReconciler) Reconcile(ctx context.Context, req reconcile. return reconcile.Result{}, err } + if isPaused, requeue, err := paused.EnsurePausedCondition(ctx, r.Client, nil, identity); err != nil || isPaused || requeue { + return ctrl.Result{}, err + } + defer func() { conditions.SetSummary(identity, conditions.WithConditions(infrav1.CredentialsAvailableCondidtion)) - if err := patchHelper.Patch(ctx, identity); err != nil { + if err := patchHelper.Patch(ctx, identity, patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + clusterv1.PausedV1Beta2Condition, + infrav1.VSphereClusterIdentityAvailableV1Beta2Condition, + }}); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) } }() @@ -106,12 +113,6 @@ func (r clusterIdentityReconciler) Reconcile(ctx context.Context, req reconcile. return ctrl.Result{}, r.reconcileDelete(ctx, identity) } - // Add a finalizer and requeue to ensure that the secret is deleted when the identity is deleted. - if !ctrlutil.ContainsFinalizer(identity, infrav1.VSphereClusterIdentityFinalizer) { - ctrlutil.AddFinalizer(identity, infrav1.VSphereClusterIdentityFinalizer) - return reconcile.Result{}, nil - } - // fetch secret secret := &corev1.Secret{} secretKey := client.ObjectKey{ @@ -120,12 +121,24 @@ func (r clusterIdentityReconciler) Reconcile(ctx context.Context, req reconcile. } if err := r.Client.Get(ctx, secretKey, secret); err != nil { conditions.MarkFalse(identity, infrav1.CredentialsAvailableCondidtion, infrav1.SecretNotAvailableReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(identity, metav1.Condition{ + Type: infrav1.VSphereClusterIdentityAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterIdentitySecretNotAvailableV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, errors.Wrapf(err, "failed to get Secret %s", klog.KRef(secretKey.Namespace, secretKey.Name)) } // If this secret is owned by a different VSphereClusterIdentity or a VSphereCluster, mark the identity as not ready and return an error. if !clusterutilv1.IsOwnedByObject(secret, identity) && pkgidentity.IsOwnedByIdentityOrCluster(secret.GetOwnerReferences()) { conditions.MarkFalse(identity, infrav1.CredentialsAvailableCondidtion, infrav1.SecretAlreadyInUseReason, clusterv1.ConditionSeverityError, "secret being used by another Cluster/VSphereIdentity") + v1beta2conditions.Set(identity, metav1.Condition{ + Type: infrav1.VSphereClusterIdentityAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterIdentitySecretAlreadyInUseV1Beta2Reason, + Message: "secret being used by another Cluster/VSphereIdentity", + }) identity.Status.Ready = false return reconcile.Result{}, errors.New("secret being used by another Cluster/VSphereIdentity") } @@ -146,10 +159,22 @@ func (r clusterIdentityReconciler) Reconcile(ctx context.Context, req reconcile. err = r.Client.Update(ctx, secret) if err != nil { conditions.MarkFalse(identity, infrav1.CredentialsAvailableCondidtion, infrav1.SecretOwnerReferenceFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(identity, metav1.Condition{ + Type: infrav1.VSphereClusterIdentityAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterIdentitySettingSecretOwnerReferenceFailedV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, err } conditions.MarkTrue(identity, infrav1.CredentialsAvailableCondidtion) + v1beta2conditions.Set(identity, metav1.Condition{ + Type: infrav1.VSphereClusterIdentityAvailableV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereClusterIdentityAvailableV1Beta2Reason, + }) + identity.Status.Ready = true return reconcile.Result{}, nil } @@ -161,6 +186,13 @@ func (r clusterIdentityReconciler) reconcileDelete(ctx context.Context, identity Namespace: r.ControllerManagerCtx.Namespace, Name: identity.Spec.SecretName, } + + v1beta2conditions.Set(identity, metav1.Condition{ + Type: infrav1.VSphereClusterIdentityAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereClusterIdentityDeletingV1Beta2Reason, + }) + err := r.Client.Get(ctx, secretKey, secret) if err != nil { if apierrors.IsNotFound(err) { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller.go index b7671ab46d9..a1aef6cfe6c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller.go @@ -29,10 +29,12 @@ import ( "k8s.io/utils/ptr" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" - "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/collections" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/finalizers" "sigs.k8s.io/cluster-api/util/patch" + "sigs.k8s.io/cluster-api/util/paused" "sigs.k8s.io/cluster-api/util/predicates" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" @@ -78,7 +80,7 @@ func AddVSphereDeploymentZoneControllerToManager(ctx context.Context, controller &handler.EnqueueRequestForObject{}, ), ). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). Complete(reconciler) } @@ -101,9 +103,9 @@ func (r vsphereDeploymentZoneReconciler) Reconcile(ctx context.Context, request log = log.WithValues("VSphereFailureDomain", klog.KRef("", vsphereDeploymentZone.Spec.FailureDomain)) ctx = ctrl.LoggerInto(ctx, log) - if annotations.HasPaused(vsphereDeploymentZone) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil + // Add finalizer first if not set to avoid the race condition between init and delete. + if finalizerAdded, err := finalizers.EnsureFinalizer(ctx, r.Client, vsphereDeploymentZone, infrav1.DeploymentZoneFinalizer); err != nil || finalizerAdded { + return ctrl.Result{}, err } patchHelper, err := patch.NewHelper(vsphereDeploymentZone, r.Client) @@ -111,13 +113,17 @@ func (r vsphereDeploymentZoneReconciler) Reconcile(ctx context.Context, request return reconcile.Result{}, err } + if isPaused, requeue, err := paused.EnsurePausedCondition(ctx, r.Client, nil, vsphereDeploymentZone); err != nil || isPaused || requeue { + return ctrl.Result{}, err + } + vsphereDeploymentZoneContext := &capvcontext.VSphereDeploymentZoneContext{ ControllerManagerContext: r.ControllerManagerContext, VSphereDeploymentZone: vsphereDeploymentZone, PatchHelper: patchHelper, } defer func() { - if err := vsphereDeploymentZoneContext.Patch(ctx); err != nil { + if err := r.patch(ctx, vsphereDeploymentZoneContext); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) } }() @@ -126,14 +132,49 @@ func (r vsphereDeploymentZoneReconciler) Reconcile(ctx context.Context, request return ctrl.Result{}, r.reconcileDelete(ctx, vsphereDeploymentZoneContext) } - // If the VSphereDeploymentZone doesn't have our finalizer, add it. - // Requeue immediately after adding finalizer to avoid the race condition between init and delete - if !ctrlutil.ContainsFinalizer(vsphereDeploymentZone, infrav1.DeploymentZoneFinalizer) { - ctrlutil.AddFinalizer(vsphereDeploymentZone, infrav1.DeploymentZoneFinalizer) - return ctrl.Result{}, nil + return ctrl.Result{}, r.reconcileNormal(ctx, vsphereDeploymentZoneContext) +} + +// Patch patches the VSphereDeploymentZone. +func (r vsphereDeploymentZoneReconciler) patch(ctx context.Context, vsphereDeploymentZoneContext *capvcontext.VSphereDeploymentZoneContext) error { + conditions.SetSummary(vsphereDeploymentZoneContext.VSphereDeploymentZone, + conditions.WithConditions( + infrav1.VCenterAvailableCondition, + infrav1.VSphereFailureDomainValidatedCondition, + infrav1.PlacementConstraintMetCondition, + ), + ) + + if err := v1beta2conditions.SetSummaryCondition(vsphereDeploymentZoneContext.VSphereDeploymentZone, vsphereDeploymentZoneContext.VSphereDeploymentZone, infrav1.VSphereDeploymentZoneReadyV1Beta2Condition, + v1beta2conditions.ForConditionTypes{ + infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition, + infrav1.VSphereDeploymentZoneVCenterAvailableV1Beta2Condition, + infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + }, + // Using a custom merge strategy to override reasons applied during merge. + v1beta2conditions.CustomMergeStrategy{ + MergeStrategy: v1beta2conditions.DefaultMergeStrategy( + // Use custom reasons. + v1beta2conditions.ComputeReasonFunc(v1beta2conditions.GetDefaultComputeMergeReasonFunc( + infrav1.VSphereDeploymentZoneNotReadyV1Beta2Reason, + infrav1.VSphereDeploymentZoneReadyUnknownV1Beta2Reason, + infrav1.VSphereDeploymentZoneReadyV1Beta2Reason, + )), + ), + }, + ); err != nil { + return errors.Wrapf(err, "failed to set %s condition", infrav1.VSphereDeploymentZoneReadyV1Beta2Condition) } - return ctrl.Result{}, r.reconcileNormal(ctx, vsphereDeploymentZoneContext) + return vsphereDeploymentZoneContext.PatchHelper.Patch(ctx, vsphereDeploymentZoneContext.VSphereDeploymentZone, + patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + clusterv1.PausedV1Beta2Condition, + infrav1.VSphereDeploymentZoneReadyV1Beta2Condition, + infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition, + infrav1.VSphereDeploymentZoneVCenterAvailableV1Beta2Condition, + infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + }}, + ) } func (r vsphereDeploymentZoneReconciler) reconcileNormal(ctx context.Context, deploymentZoneCtx *capvcontext.VSphereDeploymentZoneContext) error { @@ -146,17 +187,28 @@ func (r vsphereDeploymentZoneReconciler) reconcileNormal(ctx context.Context, de authSession, err := r.getVCenterSession(ctx, deploymentZoneCtx, failureDomain.Spec.Topology.Datacenter) if err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VCenterAvailableCondition, infrav1.VCenterUnreachableReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneVCenterUnreachableV1Beta2Reason, + Message: err.Error(), + }) deploymentZoneCtx.VSphereDeploymentZone.Status.Ready = ptr.To(false) return err } + deploymentZoneCtx.AuthSession = authSession conditions.MarkTrue(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VCenterAvailableCondition) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereDeploymentZoneVCenterAvailableV1Beta2Reason, + }) if err := r.reconcilePlacementConstraint(ctx, deploymentZoneCtx); err != nil { deploymentZoneCtx.VSphereDeploymentZone.Status.Ready = ptr.To(false) return err } - conditions.MarkTrue(deploymentZoneCtx.VSphereDeploymentZone, infrav1.PlacementConstraintMetCondition) // reconcile the failure domain if err := r.reconcileFailureDomain(ctx, deploymentZoneCtx, failureDomain); err != nil { @@ -175,6 +227,12 @@ func (r vsphereDeploymentZoneReconciler) reconcilePlacementConstraint(ctx contex if resourcePool := placementConstraint.ResourcePool; resourcePool != "" { if _, err := deploymentZoneCtx.AuthSession.Finder.ResourcePool(ctx, resourcePool); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.PlacementConstraintMetCondition, infrav1.ResourcePoolNotFoundReason, clusterv1.ConditionSeverityError, "resource pool %s is misconfigured", resourcePool) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZonePlacementConstraintResourcePoolNotFoundV1Beta2Reason, + Message: fmt.Sprintf("resource pool %s is misconfigured", resourcePool), + }) return errors.Wrapf(err, "failed to reconcile placement contraint: unable to find resource pool %s", resourcePool) } } @@ -182,9 +240,23 @@ func (r vsphereDeploymentZoneReconciler) reconcilePlacementConstraint(ctx contex if folder := placementConstraint.Folder; folder != "" { if _, err := deploymentZoneCtx.AuthSession.Finder.Folder(ctx, placementConstraint.Folder); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.PlacementConstraintMetCondition, infrav1.FolderNotFoundReason, clusterv1.ConditionSeverityError, "folder %s is misconfigured", folder) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZonePlacementConstraintFolderNotFoundV1Beta2Reason, + Message: fmt.Sprintf("folder %s is misconfigured", folder), + }) return errors.Wrapf(err, "failed to reconcile placement contraint: unable to find folder %s", folder) } } + + conditions.MarkTrue(deploymentZoneCtx.VSphereDeploymentZone, infrav1.PlacementConstraintMetCondition) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Reason, + }) + return nil } @@ -230,6 +302,22 @@ func (r vsphereDeploymentZoneReconciler) getVCenterSession(ctx context.Context, func (r vsphereDeploymentZoneReconciler) reconcileDelete(ctx context.Context, deploymentZoneCtx *capvcontext.VSphereDeploymentZoneContext) error { log := ctrl.LoggerFrom(ctx) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneVCenterAvailableDeletingV1Beta2Reason, + }) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZonePlacementConstraintReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZonePlacementConstraintDeletingV1Beta2Reason, + }) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainDeletingV1Beta2Reason, + }) + machines := &clusterv1.MachineList{} if err := r.Client.List(ctx, machines); err != nil { return errors.Wrapf(err, "failed to list Machines") diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller_domain.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller_domain.go index 32052bf12fb..5dc516d1984 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller_domain.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheredeploymentzone_controller_domain.go @@ -18,6 +18,7 @@ package controllers import ( "context" + "fmt" "github.com/pkg/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" @@ -25,6 +26,7 @@ import ( clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -38,12 +40,24 @@ func (r vsphereDeploymentZoneReconciler) reconcileFailureDomain(ctx context.Cont // verify the failure domain for the region if err := r.reconcileInfraFailureDomain(ctx, deploymentZoneCtx, vsphereFailureDomain, vsphereFailureDomain.Spec.Region); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.RegionMisconfiguredReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainRegionMisconfiguredV1Beta2Reason, + Message: err.Error(), + }) return errors.Wrapf(err, "failed to reconcile failure domain: region is not configured correctly") } // verify the failure domain for the zone if err := r.reconcileInfraFailureDomain(ctx, deploymentZoneCtx, vsphereFailureDomain, vsphereFailureDomain.Spec.Zone); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.ZoneMisconfiguredReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainZoneMisconfiguredV1Beta2Reason, + Message: err.Error(), + }) return errors.Wrapf(err, "failed to reconcile failure domain: zone is not configured correctly") } @@ -69,11 +83,22 @@ func (r vsphereDeploymentZoneReconciler) reconcileFailureDomain(ctx context.Cont UID: deploymentZoneCtx.VSphereDeploymentZone.UID, }) }); err != nil { + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainValidationFailedV1Beta2Reason, + Message: "failed to update owner references of failure domain", + }) return err } // Mark the VSphereDeploymentZone as having a valid VSphereFailureDomain. conditions.MarkTrue(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Reason, + }) return nil } @@ -89,6 +114,12 @@ func (r vsphereDeploymentZoneReconciler) reconcileTopology(ctx context.Context, if datastore := topology.Datastore; datastore != "" { if _, err := deploymentZoneCtx.AuthSession.Finder.Datastore(ctx, datastore); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.DatastoreNotFoundReason, clusterv1.ConditionSeverityError, "datastore %s is misconfigured", datastore) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainDatastoreNotFoundV1Beta2Reason, + Message: fmt.Sprintf("datastore %s is misconfigured", datastore), + }) return errors.Wrapf(err, "unable to find datastore %s", datastore) } } @@ -96,6 +127,12 @@ func (r vsphereDeploymentZoneReconciler) reconcileTopology(ctx context.Context, for _, network := range topology.Networks { if _, err := deploymentZoneCtx.AuthSession.Finder.Network(ctx, network); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.NetworkNotFoundReason, clusterv1.ConditionSeverityError, "network %s is not found", network) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainNetworkNotFoundV1Beta2Reason, + Message: fmt.Sprintf("network %s is not found", network), + }) return errors.Wrapf(err, "unable to find network %s", network) } } @@ -103,23 +140,34 @@ func (r vsphereDeploymentZoneReconciler) reconcileTopology(ctx context.Context, for _, networkConfig := range topology.NetworkConfigurations { if _, err := deploymentZoneCtx.AuthSession.Finder.Network(ctx, networkConfig.NetworkName); err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.NetworkNotFoundReason, clusterv1.ConditionSeverityError, "network %s is not found", networkConfig.NetworkName) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainNetworkNotFoundV1Beta2Reason, + Message: fmt.Sprintf("network %s is not found", networkConfig.NetworkName), + }) return errors.Wrapf(err, "unable to find network %s", networkConfig.NetworkName) } } if hostPlacementInfo := topology.Hosts; hostPlacementInfo != nil { rule, err := cluster.VerifyAffinityRule(ctx, deploymentZoneCtx, *topology.ComputeCluster, hostPlacementInfo.HostGroupName, hostPlacementInfo.VMGroupName) - switch { - case err != nil: + if err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.HostsMisconfiguredReason, clusterv1.ConditionSeverityError, "vm host affinity does not exist") + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainHostsMisconfiguredV1Beta2Reason, + Message: "vm host affinity rule does not exist", + }) return err - case rule.Disabled(): + } + + if rule.Disabled() { ctrl.LoggerFrom(ctx).V(4).Info("WARNING: vm-host rule for the failure domain is disabled", "hostGroup", hostPlacementInfo.HostGroupName, "vmGroup", hostPlacementInfo.VMGroupName) - conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.HostsAffinityMisconfiguredReason, clusterv1.ConditionSeverityWarning, "vm host affinity is disabled") - default: - conditions.MarkTrue(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition) } } + return nil } @@ -132,6 +180,12 @@ func (r vsphereDeploymentZoneReconciler) reconcileComputeCluster(ctx context.Con ccr, err := deploymentZoneCtx.AuthSession.Finder.ClusterComputeResource(ctx, *computeCluster) if err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.ComputeClusterNotFoundReason, clusterv1.ConditionSeverityError, "compute cluster %s not found", *computeCluster) + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainComputeClusterNotFoundV1Beta2Reason, + Message: fmt.Sprintf("compute cluster %s not found", *computeCluster), + }) return errors.Wrap(err, "compute cluster not found") } @@ -144,10 +198,22 @@ func (r vsphereDeploymentZoneReconciler) reconcileComputeCluster(ctx context.Con ref, err := rp.Owner(ctx) if err != nil { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.ComputeClusterNotFoundReason, clusterv1.ConditionSeverityError, "resource pool owner not found") + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainComputeClusterNotFoundV1Beta2Reason, + Message: "resource pool owner not found", + }) return errors.Wrap(err, "unable to find owner compute resource") } if ref.Reference() != ccr.Reference() { conditions.MarkFalse(deploymentZoneCtx.VSphereDeploymentZone, infrav1.VSphereFailureDomainValidatedCondition, infrav1.ResourcePoolNotFoundReason, clusterv1.ConditionSeverityError, "resource pool is not owned by compute cluster") + v1beta2conditions.Set(deploymentZoneCtx.VSphereDeploymentZone, metav1.Condition{ + Type: infrav1.VSphereDeploymentZoneFailureDomainValidatedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereDeploymentZoneFailureDomainResourcePoolNotFoundV1Beta2Reason, + Message: "resource pool is not owned by compute cluster", + }) return errors.Errorf("compute cluster %s does not own resource pool %s", *computeCluster, resourcePool) } } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheremachine_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheremachine_controller.go index ee2f1e0c719..3f40556959f 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheremachine_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspheremachine_controller.go @@ -34,10 +34,12 @@ import ( "k8s.io/klog/v2" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" - "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/finalizers" clog "sigs.k8s.io/cluster-api/util/log" "sigs.k8s.io/cluster-api/util/patch" + "sigs.k8s.io/cluster-api/util/paused" "sigs.k8s.io/cluster-api/util/predicates" ctrl "sigs.k8s.io/controller-runtime" ctrlbldr "sigs.k8s.io/controller-runtime/pkg/builder" @@ -111,7 +113,7 @@ func AddMachineControllerToManager(ctx context.Context, controllerManagerContext &clusterv1.Cluster{}, handler.EnqueueRequestsFromMapFunc(r.enqueueClusterToMachineRequests), ctrlbldr.WithPredicates( - predicates.ClusterUnpausedAndInfrastructureReady(mgr.GetScheme(), predicateLog), + predicates.ClusterPausedTransitionsOrInfrastructureReady(mgr.GetScheme(), predicateLog), ), ). // Watch a GenericEvent channel for the controlled resource. @@ -125,7 +127,7 @@ func AddMachineControllerToManager(ctx context.Context, controllerManagerContext &handler.EnqueueRequestForObject{}, ), ). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerContext.WatchFilterValue)). + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerContext.WatchFilterValue)). // Watch any VirtualMachine resources owned by this VSphereMachine Owns(&vmoprv1.VirtualMachine{}). Complete(r) @@ -151,7 +153,7 @@ func AddMachineControllerToManager(ctx context.Context, controllerManagerContext &handler.EnqueueRequestForObject{}, ), ). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerContext.WatchFilterValue)). + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerContext.WatchFilterValue)). // Watch any VSphereVM resources owned by the controlled type. Watches( &infrav1.VSphereVM{}, @@ -168,7 +170,7 @@ func AddMachineControllerToManager(ctx context.Context, controllerManagerContext &clusterv1.Cluster{}, handler.EnqueueRequestsFromMapFunc(r.enqueueClusterToMachineRequests), ctrlbldr.WithPredicates( - predicates.ClusterUnpausedAndInfrastructureReady(mgr.GetScheme(), predicateLog), + predicates.ClusterPausedTransitionsOrInfrastructureReady(mgr.GetScheme(), predicateLog), ), ).Complete(r) } @@ -194,6 +196,11 @@ func (r *machineReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, err } + // Add finalizer first if not set to avoid the race condition between init and delete. + if finalizerAdded, err := finalizers.EnsureFinalizer(ctx, r.Client, machineContext.GetVSphereMachine(), infrav1.MachineFinalizer); err != nil || finalizerAdded { + return ctrl.Result{}, err + } + // Fetch the CAPI Machine. machine, err := clusterutilv1.GetOwnerMachine(ctx, r.Client, machineContext.GetObjectMeta()) if err != nil { @@ -217,20 +224,13 @@ func (r *machineReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ if err != nil { log.Error(err, "Failed to get Cluster from VSphereCluster: Machine is missing cluster label or cluster does not exist") } + if cluster != nil { log = log.WithValues("Cluster", klog.KObj(cluster)) if cluster.Spec.InfrastructureRef != nil { log = log.WithValues("VSphereCluster", klog.KRef(cluster.Namespace, cluster.Spec.InfrastructureRef.Name)) } ctx = ctrl.LoggerInto(ctx, log) - - if annotations.IsPaused(cluster, machineContext.GetVSphereMachine()) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil - } - } else if annotations.HasPaused(machineContext.GetVSphereMachine()) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil } // Create the patch helper. @@ -238,6 +238,11 @@ func (r *machineReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ if err != nil { return reconcile.Result{}, err } + + if isPaused, requeue, err := paused.EnsurePausedCondition(ctx, r.Client, cluster, machineContext.GetVSphereMachine()); err != nil || isPaused || requeue { + return ctrl.Result{}, err + } + machineContext.SetBaseMachineContext(&capvcontext.BaseMachineContext{ Cluster: cluster, Machine: machine, @@ -245,6 +250,25 @@ func (r *machineReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ }) // always patch the VSphereMachine object defer func() { + // Before computing ready condition, make sure that VirtualMachineProvisioned is always set. + // NOTE: This is required because v1beta2 conditions comply to guideline requiring conditions to be set at the + // first reconcile. + if c := v1beta2conditions.Get(machineContext.GetVSphereMachine(), infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition); c == nil { + if machineContext.GetReady() { + v1beta2conditions.Set(machineContext.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Reason, + }) + } else { + v1beta2conditions.Set(machineContext.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineNotProvisionedV1Beta2Reason, + }) + } + } + // always update the readyCondition. conditions.SetSummary(machineContext.GetVSphereMachine(), conditions.WithConditions( @@ -252,6 +276,26 @@ func (r *machineReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ ), ) + if err := v1beta2conditions.SetSummaryCondition(machineContext.GetVSphereMachine(), machineContext.GetVSphereMachine(), infrav1.VSphereMachineReadyV1Beta2Condition, + v1beta2conditions.ForConditionTypes{ + infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + }, + // Using a custom merge strategy to override reasons applied during merge. + v1beta2conditions.CustomMergeStrategy{ + MergeStrategy: v1beta2conditions.DefaultMergeStrategy( + // Use custom reasons. + v1beta2conditions.ComputeReasonFunc(v1beta2conditions.GetDefaultComputeMergeReasonFunc( + infrav1.VSphereMachineNotReadyV1Beta2Reason, + infrav1.VSphereMachineReadyUnknownV1Beta2Reason, + infrav1.VSphereMachineReadyV1Beta2Reason, + )), + ), + }, + ); err != nil { + reterr = kerrors.NewAggregate([]error{reterr, errors.Wrapf(err, "failed to set %s condition", infrav1.VSphereMachineReadyV1Beta2Condition)}) + return + } + // Patch the VSphereMachine resource. if err := machineContext.Patch(ctx); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) @@ -294,13 +338,6 @@ func (r *machineReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ return reconcile.Result{}, errors.Wrapf(err, "failed to get VSphereCluster") } - // If the VSphereMachine doesn't have our finalizer, add it. - // Requeue immediately after adding finalizer to avoid the race condition between init and delete - if !ctrlutil.ContainsFinalizer(machineContext.GetVSphereMachine(), infrav1.MachineFinalizer) { - ctrlutil.AddFinalizer(machineContext.GetVSphereMachine(), infrav1.MachineFinalizer) - return reconcile.Result{}, nil - } - // Handle non-deleted machines return r.reconcileNormal(ctx, machineContext) } @@ -309,6 +346,11 @@ func (r *machineReconciler) reconcileDelete(ctx context.Context, machineCtx capv log := ctrl.LoggerFrom(ctx) conditions.MarkFalse(machineCtx.GetVSphereMachine(), infrav1.VMProvisionedCondition, clusterv1.DeletingReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(machineCtx.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineDeletingV1Beta2Reason, + }) if err := r.VMService.ReconcileDelete(ctx, machineCtx); err != nil { if apierrors.IsNotFound(err) { @@ -319,6 +361,13 @@ func (r *machineReconciler) reconcileDelete(ctx context.Context, machineCtx capv return reconcile.Result{}, nil } conditions.MarkFalse(machineCtx.GetVSphereMachine(), infrav1.VMProvisionedCondition, clusterv1.DeletionFailedReason, clusterv1.ConditionSeverityWarning, "") + v1beta2conditions.Set(machineCtx.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineDeletingV1Beta2Reason, + Message: "Please check controller logs for errors", + }) + return reconcile.Result{}, err } @@ -348,6 +397,11 @@ func (r *machineReconciler) reconcileNormal(ctx context.Context, machineCtx capv if !machineCtx.GetCluster().Status.InfrastructureReady { log.Info("Cluster infrastructure is not ready yet, skipping reconciliation") conditions.MarkFalse(machineCtx.GetVSphereMachine(), infrav1.VMProvisionedCondition, infrav1.WaitingForClusterInfrastructureReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(machineCtx.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineWaitingForClusterInfrastructureReadyV1Beta2Reason, + }) return reconcile.Result{}, nil } } else { @@ -361,10 +415,20 @@ func (r *machineReconciler) reconcileNormal(ctx context.Context, machineCtx capv if !util.IsControlPlaneMachine(machineCtx.GetVSphereMachine()) && !conditions.IsTrue(machineCtx.GetCluster(), clusterv1.ControlPlaneInitializedCondition) { log.Info("Waiting for the control plane to be initialized, skipping reconciliation") conditions.MarkFalse(machineCtx.GetVSphereMachine(), infrav1.VMProvisionedCondition, clusterv1.WaitingForControlPlaneAvailableReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(machineCtx.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineWaitingForControlPlaneInitializedV1Beta2Reason, + }) return ctrl.Result{}, nil } log.Info("Waiting for bootstrap data to be ready, skipping reconciliation") conditions.MarkFalse(machineCtx.GetVSphereMachine(), infrav1.VMProvisionedCondition, infrav1.WaitingForBootstrapDataReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(machineCtx.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineWaitingForBootstrapDataV1Beta2Reason, + }) return reconcile.Result{}, nil } @@ -384,6 +448,11 @@ func (r *machineReconciler) reconcileNormal(ctx context.Context, machineCtx capv } conditions.MarkTrue(machineCtx.GetVSphereMachine(), infrav1.VMProvisionedCondition) + v1beta2conditions.Set(machineCtx.GetVSphereMachine(), metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Reason, + }) return reconcile.Result{}, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_controller.go index 5a5dd0a89b4..0c0cef52c8a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_controller.go @@ -35,10 +35,12 @@ import ( "sigs.k8s.io/cluster-api/controllers/clustercache" ipamv1 "sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" - "sigs.k8s.io/cluster-api/util/annotations" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/finalizers" clog "sigs.k8s.io/cluster-api/util/log" "sigs.k8s.io/cluster-api/util/patch" + "sigs.k8s.io/cluster-api/util/paused" "sigs.k8s.io/cluster-api/util/predicates" ctrl "sigs.k8s.io/controller-runtime" ctrlbldr "sigs.k8s.io/controller-runtime/pkg/builder" @@ -95,23 +97,10 @@ func AddVMControllerToManager(ctx context.Context, controllerManagerCtx *capvcon &handler.EnqueueRequestForObject{}, ), ). - WithEventFilter(predicates.ResourceNotPausedAndHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). + WithEventFilter(predicates.ResourceHasFilterLabel(mgr.GetScheme(), predicateLog, controllerManagerCtx.WatchFilterValue)). Watches( &clusterv1.Cluster{}, handler.EnqueueRequestsFromMapFunc(r.clusterToVSphereVMs), - ctrlbldr.WithPredicates( - predicate.Funcs{ - UpdateFunc: func(e event.UpdateEvent) bool { - newCluster := e.ObjectNew.(*clusterv1.Cluster) - // check whether cluster has either spec.paused or pasued annotation - return !annotations.IsPaused(newCluster, newCluster) - }, - CreateFunc: func(e event.CreateEvent) bool { - cluster := e.Object.(*clusterv1.Cluster) - // check whether cluster has either spec.paused or pasued annotation - return annotations.IsPaused(cluster, cluster) - }, - }), ). Watches( &infrav1.VSphereCluster{}, @@ -156,21 +145,19 @@ func (r vmReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ ctrl.R return reconcile.Result{}, err } + // Add finalizer first if not set to avoid the race condition between init and delete. + if finalizerAdded, err := finalizers.EnsureFinalizer(ctx, r.Client, vsphereVM, infrav1.VMFinalizer); err != nil || finalizerAdded { + return ctrl.Result{}, err + } + cluster, err := clusterutilv1.GetClusterFromMetadata(ctx, r.Client, vsphereVM.ObjectMeta) if err != nil { log.Error(err, "Failed to get Cluster from VSphereVM: Machine is missing cluster label or cluster does not exist") } + if cluster != nil { log = log.WithValues("Cluster", klog.KObj(cluster)) ctx = ctrl.LoggerInto(ctx, log) - - if annotations.IsPaused(cluster, vsphereVM) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil - } - } else if annotations.HasPaused(vsphereVM) { - log.Info("Reconciliation is paused for this object") - return reconcile.Result{}, nil } // Create the patch helper. @@ -179,12 +166,27 @@ func (r vmReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ ctrl.R return reconcile.Result{}, err } + if isPaused, requeue, err := paused.EnsurePausedCondition(ctx, r.Client, cluster, vsphereVM); err != nil || isPaused || requeue { + return ctrl.Result{}, err + } + authSession, err := r.retrieveVcenterSession(ctx, vsphereVM) if err != nil { conditions.MarkFalse(vsphereVM, infrav1.VCenterAvailableCondition, infrav1.VCenterUnreachableReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(vsphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVCenterUnreachableV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, err } conditions.MarkTrue(vsphereVM, infrav1.VCenterAvailableCondition) + v1beta2conditions.Set(vsphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVCenterAvailableV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereVMVCenterAvailableV1Beta2Reason, + }) // Fetch the owner VSphereMachine. vsphereMachine, err := util.GetOwnerVSphereMachine(ctx, r.Client, vsphereVM.ObjectMeta) @@ -262,6 +264,25 @@ func (r vmReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ ctrl.R // Always issue a patch when exiting this function so changes to the // resource are patched back to the API server. defer func() { + // Before computing ready condition, make sure that VirtualMachineProvisioned is always set. + // NOTE: This is required because v1beta2 conditions comply to guideline requiring conditions to be set at the + // first reconcile. + if c := v1beta2conditions.Get(vmContext.VSphereVM, infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition); c != nil { + if vmContext.VSphereVM.Status.Ready { + v1beta2conditions.Set(vmContext.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Reason, + }) + } else { + v1beta2conditions.Set(vmContext.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineNotProvisionedV1Beta2Reason, + }) + } + } + // always update the readyCondition. conditions.SetSummary(vmContext.VSphereVM, conditions.WithConditions( @@ -271,6 +292,32 @@ func (r vmReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ ctrl.R ), ) + if err := v1beta2conditions.SetSummaryCondition(vmContext.VSphereVM, vmContext.VSphereVM, infrav1.VSphereVMReadyV1Beta2Condition, + v1beta2conditions.ForConditionTypes{ + infrav1.VSphereVMVCenterAvailableV1Beta2Condition, + infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + }, + v1beta2conditions.IgnoreTypesIfMissing{ + infrav1.VSphereVMVCenterAvailableV1Beta2Condition, + infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + }, + // Using a custom merge strategy to override reasons applied during merge. + v1beta2conditions.CustomMergeStrategy{ + MergeStrategy: v1beta2conditions.DefaultMergeStrategy( + // Use custom reasons. + v1beta2conditions.ComputeReasonFunc(v1beta2conditions.GetDefaultComputeMergeReasonFunc( + infrav1.VSphereVMNotReadyV1Beta2Reason, + infrav1.VSphereVMReadyUnknownV1Beta2Reason, + infrav1.VSphereVMReadyV1Beta2Reason, + )), + ), + }, + ); err != nil { + reterr = kerrors.NewAggregate([]error{reterr, errors.Wrapf(err, "failed to set %s condition", infrav1.VSphereVMReadyV1Beta2Condition)}) + return + } + // Patch the VSphereVM resource. if err := vmContext.Patch(ctx); err != nil { reterr = kerrors.NewAggregate([]error{reterr, err}) @@ -294,15 +341,6 @@ func (r vmReconciler) Reconcile(ctx context.Context, req ctrl.Request) (_ ctrl.R } }() - if vsphereVM.ObjectMeta.DeletionTimestamp.IsZero() { - // If the VSphereVM doesn't have our finalizer, add it. - // Requeue immediately to avoid the race condition between init and delete - if !ctrlutil.ContainsFinalizer(vsphereVM, infrav1.VMFinalizer) { - ctrlutil.AddFinalizer(vsphereVM, infrav1.VMFinalizer) - return reconcile.Result{}, nil - } - } - return r.reconcile(ctx, vmContext, fetchClusterModuleInput{ VSphereCluster: vsphereCluster, Machine: machine, @@ -339,9 +377,20 @@ func (r vmReconciler) reconcileDelete(ctx context.Context, vmCtx *capvcontext.VM log := ctrl.LoggerFrom(ctx) conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, clusterv1.DeletingReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineDeletingV1Beta2Reason, + }) result, vm, err := r.VMService.DestroyVM(ctx, vmCtx) if err != nil { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, "DeletionFailed", clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineDeletingV1Beta2Reason, + Message: err.Error(), + }) return reconcile.Result{}, errors.Wrapf(err, "failed to destroy VM") } @@ -420,6 +469,11 @@ func (r vmReconciler) reconcileNormal(ctx context.Context, vmCtx *capvcontext.VM if r.isWaitingForStaticIPAllocation(vmCtx) { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.WaitingForStaticIPAllocationReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineWaitingForStaticIPAllocationV1Beta2Reason, + }) log.Info("VM is waiting for static ip to be available") return reconcile.Result{}, nil } @@ -437,6 +491,9 @@ func (r vmReconciler) reconcileNormal(ctx context.Context, vmCtx *capvcontext.VM // Do not proceed until the backend VM is marked ready. if vm.State != infrav1.VirtualMachineStateReady { log.Info(fmt.Sprintf("VM state is %q, waiting for %q", vm.State, infrav1.VirtualMachineStateReady)) + if !vmCtx.VSphereVM.Status.RetryAfter.IsZero() { + return reconcile.Result{RequeueAfter: time.Until(vmCtx.VSphereVM.Status.RetryAfter.Time)}, nil + } return reconcile.Result{}, nil } @@ -463,12 +520,22 @@ func (r vmReconciler) reconcileNormal(ctx context.Context, vmCtx *capvcontext.VM // we didn't get any addresses, requeue if len(vmCtx.VSphereVM.Status.Addresses) == 0 { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.WaitingForIPAllocationReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineWaitingForIPAllocationV1Beta2Reason, + }) return reconcile.Result{RequeueAfter: 10 * time.Second}, nil } // Once the network is online the VM is considered ready. vmCtx.VSphereVM.Status.Ready = true conditions.MarkTrue(vmCtx.VSphereVM, infrav1.VMProvisionedCondition) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Reason, + }) log.Info("VSphereVM is ready") return reconcile.Result{}, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_ipaddress_reconciler.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_ipaddress_reconciler.go index e3916394605..3f3db49fa28 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_ipaddress_reconciler.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/controllers/vspherevm_ipaddress_reconciler.go @@ -30,6 +30,7 @@ import ( ipamv1 "sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -50,8 +51,9 @@ func (r vmReconciler) reconcileIPAddressClaims(ctx context.Context, vmCtx *capvc log := ctrl.LoggerFrom(ctx) var ( - claims []conditions.Getter - errList []error + claims []conditions.Getter + v1beta2Claims []v1beta2conditions.Getter + errList []error ) for devIdx, device := range vmCtx.VSphereVM.Spec.Network.Devices { @@ -88,6 +90,7 @@ func (r vmReconciler) reconcileIPAddressClaims(ctx context.Context, vmCtx *capvc // IPAddressClaimed condition for the VSphereVM object. if conditions.Has(ipAddrClaim, clusterv1.ReadyCondition) { claims = append(claims, ipAddrClaim) + v1beta2Claims = append(v1beta2Claims, ipAddrClaim) } } } @@ -99,6 +102,12 @@ func (r vmReconciler) reconcileIPAddressClaims(ctx context.Context, vmCtx *capvc infrav1.IPAddressClaimNotFoundReason, clusterv1.ConditionSeverityError, aggregatedErr.Error()) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMIPAddressClaimsNotFulfilledV1Beta2Reason, + Message: aggregatedErr.Error(), + }) return aggregatedErr } @@ -112,6 +121,18 @@ func (r vmReconciler) reconcileIPAddressClaims(ctx context.Context, vmCtx *capvc claims, conditions.AddSourceRef(), conditions.WithStepCounter()) + + if len(v1beta2Claims) > 0 { + if err := v1beta2conditions.SetAggregateCondition(v1beta2Claims, vmCtx.VSphereVM, clusterv1.ReadyV1Beta2Condition, v1beta2conditions.TargetConditionType(infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition)); err != nil { + return errors.Wrap(err, "failed to aggregate Ready condition from IPAddressClaims") + } + } else { + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereVMIPAddressClaimsNotFulfilledV1Beta2Reason, + }) + } return nil } @@ -119,14 +140,31 @@ func (r vmReconciler) reconcileIPAddressClaims(ctx context.Context, vmCtx *capvc switch { case totalClaims == claimsFulfilled: conditions.MarkTrue(vmCtx.VSphereVM, infrav1.IPAddressClaimedCondition) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Reason, + }) case claimsFulfilled < totalClaims && claimsCreated > 0: conditions.MarkFalse(vmCtx.VSphereVM, infrav1.IPAddressClaimedCondition, infrav1.IPAddressClaimsBeingCreatedReason, clusterv1.ConditionSeverityInfo, "%d/%d claims being created", claimsCreated, totalClaims) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMIPAddressClaimsBeingCreatedV1Beta2Reason, + Message: fmt.Sprintf("%d/%d claims being created", claimsCreated, totalClaims), + }) case claimsFulfilled < totalClaims && claimsCreated == 0: conditions.MarkFalse(vmCtx.VSphereVM, infrav1.IPAddressClaimedCondition, infrav1.WaitingForIPAddressReason, clusterv1.ConditionSeverityInfo, "%d/%d claims being processed", totalClaims-claimsFulfilled, totalClaims) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMIPAddressClaimsWaitingForIPAddressV1Beta2Reason, + Message: fmt.Sprintf("%d/%d claims being processed", totalClaims-claimsFulfilled, totalClaims), + }) } return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachine.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachine.go index 5114744a3d2..8e08305eb25 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachine.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachine.go @@ -35,13 +35,13 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/validate-vmware-infrastructure-cluster-x-k8s-io-v1beta1-vspheremachine,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=vmware.infrastructure.cluster.x-k8s.io,resources=vspheremachines,versions=v1beta1,name=validation.vspheremachine.vmware.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 // +kubebuilder:webhook:verbs=create;update,path=/mutate-vmware-infrastructure-cluster-x-k8s-io-v1beta1-vspheremachine,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=vmware.infrastructure.cluster.x-k8s.io,resources=vspheremachines,versions=v1beta1,name=default.vspheremachine.vmware.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereMachineWebhook implements a validation and defaulting webhook for VSphereMachine. -type VSphereMachineWebhook struct{} +// VSphereMachine implements a validation and defaulting webhook for VSphereMachine. +type VSphereMachine struct{} -var _ webhook.CustomValidator = &VSphereMachineWebhook{} -var _ webhook.CustomDefaulter = &VSphereMachineWebhook{} +var _ webhook.CustomValidator = &VSphereMachine{} +var _ webhook.CustomDefaulter = &VSphereMachine{} -func (webhook *VSphereMachineWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereMachine) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&vmwarev1.VSphereMachine{}). WithValidator(webhook). @@ -50,17 +50,17 @@ func (webhook *VSphereMachineWebhook) SetupWebhookWithManager(mgr ctrl.Manager) } // Default implements webhook.Defaulter so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) Default(_ context.Context, _ runtime.Object) error { +func (webhook *VSphereMachine) Default(_ context.Context, _ runtime.Object) error { return nil } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) ValidateCreate(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachine) ValidateCreate(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachine) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { var allErrs field.ErrorList newTyped, ok := newRaw.(*vmwarev1.VSphereMachine) @@ -100,6 +100,6 @@ func (webhook *VSphereMachineWebhook) ValidateUpdate(_ context.Context, oldRaw r } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachine) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachinetemplate.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachinetemplate.go index 51d4f9e4cc3..5c480fcbcd8 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachinetemplate.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware/vspheremachinetemplate.go @@ -35,12 +35,12 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/validate-vmware-infrastructure-cluster-x-k8s-io-v1beta1-vspheremachinetemplate,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=vmware.infrastructure.cluster.x-k8s.io,resources=vspheremachinetemplates,versions=v1beta1,name=validation.vspheremachinetemplate.vmware.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereMachineTemplateWebhook implements a validation webhook for VSphereMachineTemplate. -type VSphereMachineTemplateWebhook struct{} +// VSphereMachineTemplate implements a validation webhook for VSphereMachineTemplate. +type VSphereMachineTemplate struct{} -var _ webhook.CustomValidator = &VSphereMachineTemplateWebhook{} +var _ webhook.CustomValidator = &VSphereMachineTemplate{} -func (webhook *VSphereMachineTemplateWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereMachineTemplate) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&vmwarev1.VSphereMachineTemplate{}). WithValidator(webhook). @@ -48,7 +48,7 @@ func (webhook *VSphereMachineTemplateWebhook) SetupWebhookWithManager(mgr ctrl.M } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineTemplateWebhook) ValidateCreate(ctx context.Context, obj runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) ValidateCreate(ctx context.Context, obj runtime.Object) (admission.Warnings, error) { vSphereMachineTemplate, ok := obj.(*vmwarev1.VSphereMachineTemplate) if !ok { return nil, apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereMachineTemplate but got a %T", obj)) @@ -57,7 +57,7 @@ func (webhook *VSphereMachineTemplateWebhook) ValidateCreate(ctx context.Context } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineTemplateWebhook) ValidateUpdate(ctx context.Context, _, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) ValidateUpdate(ctx context.Context, _, newRaw runtime.Object) (admission.Warnings, error) { vSphereMachineTemplate, ok := newRaw.(*vmwarev1.VSphereMachineTemplate) if !ok { return nil, apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereMachineTemplate but got a %T", newRaw)) @@ -65,7 +65,7 @@ func (webhook *VSphereMachineTemplateWebhook) ValidateUpdate(ctx context.Context return webhook.validate(ctx, nil, vSphereMachineTemplate) } -func (webhook *VSphereMachineTemplateWebhook) validate(_ context.Context, _, newVSphereMachineTemplate *vmwarev1.VSphereMachineTemplate) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) validate(_ context.Context, _, newVSphereMachineTemplate *vmwarev1.VSphereMachineTemplate) (admission.Warnings, error) { var allErrs field.ErrorList // Validate namingStrategy @@ -103,6 +103,6 @@ func (webhook *VSphereMachineTemplateWebhook) validate(_ context.Context, _, new } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineTemplateWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vsphereclustertemplate.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vsphereclustertemplate.go index e7e6c1472c7..009c0eafd0e 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vsphereclustertemplate.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vsphereclustertemplate.go @@ -33,12 +33,12 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/validate-infrastructure-cluster-x-k8s-io-v1beta1-vsphereclustertemplate,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vsphereclustertemplates,versions=v1beta1,name=validation.vsphereclustertemplate.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereClusterTemplateWebhook implements a validation and defaulting webhook for VSphereClusterTemplate. -type VSphereClusterTemplateWebhook struct{} +// VSphereClusterTemplate implements a validation webhook for VSphereClusterTemplate. +type VSphereClusterTemplate struct{} -var _ webhook.CustomValidator = &VSphereClusterTemplateWebhook{} +var _ webhook.CustomValidator = &VSphereClusterTemplate{} -func (webhook *VSphereClusterTemplateWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereClusterTemplate) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&infrav1.VSphereClusterTemplate{}). WithValidator(webhook). @@ -46,12 +46,12 @@ func (webhook *VSphereClusterTemplateWebhook) SetupWebhookWithManager(mgr ctrl.M } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereClusterTemplateWebhook) ValidateCreate(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereClusterTemplate) ValidateCreate(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereClusterTemplateWebhook) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereClusterTemplate) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { oldTyped, ok := oldRaw.(*infrav1.VSphereClusterTemplate) if !ok { return nil, apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereClusterTemplate but got a %T", oldRaw)) @@ -67,6 +67,6 @@ func (webhook *VSphereClusterTemplateWebhook) ValidateUpdate(_ context.Context, } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereClusterTemplateWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereClusterTemplate) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheredeploymentzone.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheredeploymentzone.go index a33030f3de3..df460d38b68 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheredeploymentzone.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheredeploymentzone.go @@ -32,12 +32,12 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/mutate-infrastructure-cluster-x-k8s-io-v1beta1-vspheredeploymentzone,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspheredeploymentzones,versions=v1beta1,name=default.vspheredeploymentzone.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereDeploymentZoneWebhook implements a validation and defaulting webhook for VSphereDeploymentZone. -type VSphereDeploymentZoneWebhook struct{} +// VSphereDeploymentZone implements a defaulting webhook for VSphereDeploymentZone. +type VSphereDeploymentZone struct{} -var _ webhook.CustomDefaulter = &VSphereDeploymentZoneWebhook{} +var _ webhook.CustomDefaulter = &VSphereDeploymentZone{} -func (webhook *VSphereDeploymentZoneWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereDeploymentZone) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&infrav1.VSphereDeploymentZone{}). WithDefaulter(webhook, admission.DefaulterRemoveUnknownOrOmitableFields). @@ -45,7 +45,7 @@ func (webhook *VSphereDeploymentZoneWebhook) SetupWebhookWithManager(mgr ctrl.Ma } // Default implements webhook.Defaulter so a webhook will be registered for the type. -func (webhook *VSphereDeploymentZoneWebhook) Default(_ context.Context, obj runtime.Object) error { +func (webhook *VSphereDeploymentZone) Default(_ context.Context, obj runtime.Object) error { typedObj, ok := obj.(*infrav1.VSphereDeploymentZone) if !ok { return apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereDeploymentZone but got a %T", obj)) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherefailuredomain.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherefailuredomain.go index cfc88ecaa3e..c0234a59f48 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherefailuredomain.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherefailuredomain.go @@ -35,13 +35,13 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/validate-infrastructure-cluster-x-k8s-io-v1beta1-vspherefailuredomain,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspherefailuredomains,versions=v1beta1,name=validation.vspherefailuredomain.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 // +kubebuilder:webhook:path=/mutate-infrastructure-cluster-x-k8s-io-v1beta1-vspherefailuredomain,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspherefailuredomains,verbs=create;update,versions=v1beta1,name=default.vspherefailuredomain.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereFailureDomainWebhook implements a validation and defaulting webhook for VSphereFailureDomain. -type VSphereFailureDomainWebhook struct{} +// VSphereFailureDomain implements a validation and defaulting webhook for VSphereFailureDomain. +type VSphereFailureDomain struct{} -var _ webhook.CustomValidator = &VSphereFailureDomainWebhook{} -var _ webhook.CustomDefaulter = &VSphereFailureDomainWebhook{} +var _ webhook.CustomValidator = &VSphereFailureDomain{} +var _ webhook.CustomDefaulter = &VSphereFailureDomain{} -func (webhook *VSphereFailureDomainWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereFailureDomain) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&infrav1.VSphereFailureDomain{}). WithValidator(webhook). @@ -50,7 +50,7 @@ func (webhook *VSphereFailureDomainWebhook) SetupWebhookWithManager(mgr ctrl.Man } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereFailureDomainWebhook) ValidateCreate(_ context.Context, raw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereFailureDomain) ValidateCreate(_ context.Context, raw runtime.Object) (admission.Warnings, error) { var allErrs field.ErrorList obj, ok := raw.(*infrav1.VSphereFailureDomain) @@ -91,7 +91,7 @@ func (webhook *VSphereFailureDomainWebhook) ValidateCreate(_ context.Context, ra } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereFailureDomainWebhook) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereFailureDomain) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { oldTyped, ok := oldRaw.(*infrav1.VSphereFailureDomain) if !ok { return nil, apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereFailureDomain but got a %T", oldRaw)) @@ -107,12 +107,12 @@ func (webhook *VSphereFailureDomainWebhook) ValidateUpdate(_ context.Context, ol } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereFailureDomainWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereFailureDomain) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } // Default implements webhook.Defaulter so a webhook will be registered for the type. -func (webhook *VSphereFailureDomainWebhook) Default(_ context.Context, obj runtime.Object) error { +func (webhook *VSphereFailureDomain) Default(_ context.Context, obj runtime.Object) error { typedObj, ok := obj.(*infrav1.VSphereFailureDomain) if !ok { return apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereFailureDomain but got a %T", obj)) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachine.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachine.go index d7b6ff1e406..ab61baf648e 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachine.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachine.go @@ -36,13 +36,13 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/validate-infrastructure-cluster-x-k8s-io-v1beta1-vspheremachine,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspheremachines,versions=v1beta1,name=validation.vspheremachine.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 // +kubebuilder:webhook:verbs=create;update,path=/mutate-infrastructure-cluster-x-k8s-io-v1beta1-vspheremachine,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspheremachines,versions=v1beta1,name=default.vspheremachine.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereMachineWebhook implements a validation and defaulting webhook for VSphereMachine. -type VSphereMachineWebhook struct{} +// VSphereMachine implements a validation and defaulting webhook for VSphereMachine. +type VSphereMachine struct{} -var _ webhook.CustomValidator = &VSphereMachineWebhook{} -var _ webhook.CustomDefaulter = &VSphereMachineWebhook{} +var _ webhook.CustomValidator = &VSphereMachine{} +var _ webhook.CustomDefaulter = &VSphereMachine{} -func (webhook *VSphereMachineWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereMachine) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&infrav1.VSphereMachine{}). WithValidator(webhook). @@ -51,7 +51,7 @@ func (webhook *VSphereMachineWebhook) SetupWebhookWithManager(mgr ctrl.Manager) } // Default implements webhook.Defaulter so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) Default(_ context.Context, obj runtime.Object) error { +func (webhook *VSphereMachine) Default(_ context.Context, obj runtime.Object) error { objValue, ok := obj.(*infrav1.VSphereMachine) if !ok { return apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereMachine but got a %T", obj)) @@ -63,7 +63,7 @@ func (webhook *VSphereMachineWebhook) Default(_ context.Context, obj runtime.Obj } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) ValidateCreate(_ context.Context, raw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachine) ValidateCreate(_ context.Context, raw runtime.Object) (admission.Warnings, error) { var allErrs field.ErrorList obj, ok := raw.(*infrav1.VSphereMachine) @@ -99,7 +99,7 @@ func (webhook *VSphereMachineWebhook) ValidateCreate(_ context.Context, raw runt } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachine) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { var allErrs field.ErrorList newTyped, ok := newRaw.(*infrav1.VSphereMachine) @@ -159,7 +159,7 @@ func (webhook *VSphereMachineWebhook) ValidateUpdate(_ context.Context, oldRaw r } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachine) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachinetemplate.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachinetemplate.go index f344b3ebcf4..7031d7fb6d8 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachinetemplate.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspheremachinetemplate.go @@ -39,12 +39,12 @@ const machineTemplateImmutableMsg = "VSphereMachineTemplate spec.template.spec f // +kubebuilder:webhook:verbs=create;update,path=/validate-infrastructure-cluster-x-k8s-io-v1beta1-vspheremachinetemplate,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspheremachinetemplates,versions=v1beta1,name=validation.vspheremachinetemplate.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereMachineTemplateWebhook implements a validation and defaulting webhook for VSphereMachineTemplate. -type VSphereMachineTemplateWebhook struct{} +// VSphereMachineTemplate implements a validation webhook for VSphereMachineTemplate. +type VSphereMachineTemplate struct{} -var _ webhook.CustomValidator = &VSphereMachineTemplateWebhook{} +var _ webhook.CustomValidator = &VSphereMachineTemplate{} -func (webhook *VSphereMachineTemplateWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereMachineTemplate) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&infrav1.VSphereMachineTemplate{}). WithValidator(webhook). @@ -52,7 +52,7 @@ func (webhook *VSphereMachineTemplateWebhook) SetupWebhookWithManager(mgr ctrl.M } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineTemplateWebhook) ValidateCreate(ctx context.Context, raw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) ValidateCreate(ctx context.Context, raw runtime.Object) (admission.Warnings, error) { obj, ok := raw.(*infrav1.VSphereMachineTemplate) if !ok { return nil, apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereMachineTemplate but got a %T", raw)) @@ -97,7 +97,7 @@ func (webhook *VSphereMachineTemplateWebhook) ValidateCreate(ctx context.Context } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineTemplateWebhook) ValidateUpdate(ctx context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) ValidateUpdate(ctx context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { oldTyped, ok := oldRaw.(*infrav1.VSphereMachineTemplate) if !ok { return nil, apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereMachineTemplate but got a %T", oldRaw)) @@ -126,7 +126,7 @@ func (webhook *VSphereMachineTemplateWebhook) ValidateUpdate(ctx context.Context } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereMachineTemplateWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereMachineTemplate) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherevm.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherevm.go index 723300ec33d..3d2f849459c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherevm.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vspherevm.go @@ -36,13 +36,13 @@ import ( // +kubebuilder:webhook:verbs=create;update,path=/validate-infrastructure-cluster-x-k8s-io-v1beta1-vspherevm,mutating=false,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspherevms,versions=v1beta1,name=validation.vspherevm.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 // +kubebuilder:webhook:verbs=create;update,path=/mutate-infrastructure-cluster-x-k8s-io-v1beta1-vspherevm,mutating=true,failurePolicy=fail,matchPolicy=Equivalent,groups=infrastructure.cluster.x-k8s.io,resources=vspherevms,versions=v1beta1,name=default.vspherevm.infrastructure.cluster.x-k8s.io,sideEffects=None,admissionReviewVersions=v1beta1 -// VSphereVMWebhook implements a validation and defaulting webhook for VSphereVM. -type VSphereVMWebhook struct{} +// VSphereVM implements a validation and defaulting webhook for VSphereVM. +type VSphereVM struct{} -var _ webhook.CustomValidator = &VSphereVMWebhook{} -var _ webhook.CustomDefaulter = &VSphereVMWebhook{} +var _ webhook.CustomValidator = &VSphereVM{} +var _ webhook.CustomDefaulter = &VSphereVM{} -func (webhook *VSphereVMWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error { +func (webhook *VSphereVM) SetupWebhookWithManager(mgr ctrl.Manager) error { return ctrl.NewWebhookManagedBy(mgr). For(&infrav1.VSphereVM{}). WithValidator(webhook). @@ -51,7 +51,7 @@ func (webhook *VSphereVMWebhook) SetupWebhookWithManager(mgr ctrl.Manager) error } // Default implements webhook.Defaulter so a webhook will be registered for the type. -func (webhook *VSphereVMWebhook) Default(_ context.Context, obj runtime.Object) error { +func (webhook *VSphereVM) Default(_ context.Context, obj runtime.Object) error { typedObj, ok := obj.(*infrav1.VSphereVM) if !ok { return apierrors.NewBadRequest(fmt.Sprintf("expected a VSphereVM but got a %T", obj)) @@ -64,7 +64,7 @@ func (webhook *VSphereVMWebhook) Default(_ context.Context, obj runtime.Object) } // ValidateCreate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereVMWebhook) ValidateCreate(_ context.Context, raw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereVM) ValidateCreate(_ context.Context, raw runtime.Object) (admission.Warnings, error) { var allErrs field.ErrorList objValue, ok := raw.(*infrav1.VSphereVM) if !ok { @@ -99,7 +99,7 @@ func (webhook *VSphereVMWebhook) ValidateCreate(_ context.Context, raw runtime.O } // ValidateUpdate implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereVMWebhook) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereVM) ValidateUpdate(_ context.Context, oldRaw runtime.Object, newRaw runtime.Object) (admission.Warnings, error) { var allErrs field.ErrorList oldTyped, ok := oldRaw.(*infrav1.VSphereVM) @@ -160,11 +160,11 @@ func (webhook *VSphereVMWebhook) ValidateUpdate(_ context.Context, oldRaw runtim } // ValidateDelete implements webhook.Validator so a webhook will be registered for the type. -func (webhook *VSphereVMWebhook) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { +func (webhook *VSphereVM) ValidateDelete(_ context.Context, _ runtime.Object) (admission.Warnings, error) { return nil, nil } -func (webhook *VSphereVMWebhook) deleteSpecKeys(spec map[string]interface{}, keys []string) { +func (webhook *VSphereVM) deleteSpecKeys(spec map[string]interface{}, keys []string) { if len(spec) == 0 || len(keys) == 0 { return } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/main.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/main.go index fedb48e25cc..dff262efa97 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/main.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/main.go @@ -42,6 +42,7 @@ import ( "k8s.io/utils/ptr" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/controllers/clustercache" + "sigs.k8s.io/cluster-api/controllers/crdmigrator" "sigs.k8s.io/cluster-api/controllers/remote" "sigs.k8s.io/cluster-api/util/apiwarnings" capiflags "sigs.k8s.io/cluster-api/util/flags" @@ -58,12 +59,12 @@ import ( "sigs.k8s.io/cluster-api-provider-vsphere/controllers" "sigs.k8s.io/cluster-api-provider-vsphere/controllers/vmware" "sigs.k8s.io/cluster-api-provider-vsphere/feature" - "sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks" - vmwarewebhooks "sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware" capvcontext "sigs.k8s.io/cluster-api-provider-vsphere/pkg/context" "sigs.k8s.io/cluster-api-provider-vsphere/pkg/manager" "sigs.k8s.io/cluster-api-provider-vsphere/pkg/session" "sigs.k8s.io/cluster-api-provider-vsphere/pkg/version" + "sigs.k8s.io/cluster-api-provider-vsphere/webhooks" + vmwarewebhooks "sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware" ) var ( @@ -93,6 +94,7 @@ var ( vSphereVMConcurrency int vSphereClusterIdentityConcurrency int vSphereDeploymentZoneConcurrency int + skipCRDMigrationPhases []string managerOptions = capiflags.ManagerOptions{} @@ -187,6 +189,9 @@ func InitFlags(fs *pflag.FlagSet) { fs.BoolVar(&enableContentionProfiling, "contention-profiling", false, "Enable block profiling.") + fs.StringSliceVar(&skipCRDMigrationPhases, "skip-crd-migration-phases", []string{}, + "List of CRD migration phases to skip. Valid values are: StorageVersionMigration, CleanupManagedFields.") + fs.DurationVar(&syncPeriod, "sync-period", defaultSyncPeriod, "The minimum interval at which watched resources are reconciled (e.g. 15m)") @@ -225,8 +230,18 @@ func InitFlags(fs *pflag.FlagSet) { // Add RBAC for the authorized diagnostics endpoint. // +kubebuilder:rbac:groups=authentication.k8s.io,resources=tokenreviews,verbs=create // +kubebuilder:rbac:groups=authorization.k8s.io,resources=subjectaccessreviews,verbs=create +// ADD CRD RBAC for CRD Migrator. +// +kubebuilder:rbac:groups=apiextensions.k8s.io,resources=customresourcedefinitions,verbs=get;list;watch +// govmomi +// +kubebuilder:rbac:groups=apiextensions.k8s.io,resources=customresourcedefinitions;customresourcedefinitions/status,verbs=update;patch,resourceNames=vsphereclusters.infrastructure.cluster.x-k8s.io;vsphereclustertemplates.infrastructure.cluster.x-k8s.io;vspheremachines.infrastructure.cluster.x-k8s.io;vspheremachinetemplates.infrastructure.cluster.x-k8s.io;vspherevms.infrastructure.cluster.x-k8s.io;vsphereclusteridentities.infrastructure.cluster.x-k8s.io;vspheredeploymentzones.infrastructure.cluster.x-k8s.io;vspherefailuredomains.infrastructure.cluster.x-k8s.io +// supervisor +// +kubebuilder:rbac:groups=apiextensions.k8s.io,resources=customresourcedefinitions;customresourcedefinitions/status,verbs=update;patch,resourceNames=vsphereclusters.vmware.infrastructure.cluster.x-k8s.io;vsphereclustertemplates.vmware.infrastructure.cluster.x-k8s.io;vspheremachines.vmware.infrastructure.cluster.x-k8s.io;vspheremachinetemplates.vmware.infrastructure.cluster.x-k8s.io;providerserviceaccounts.vmware.infrastructure.cluster.x-k8s.io +// govmomi CRs +// +kubebuilder:rbac:groups=infrastructure.cluster.x-k8s.io,resources=vspheremachinetemplates;vsphereclustertemplates,verbs=get;list;watch;patch;update func main() { + setupLog.Info(fmt.Sprintf("Version: %+v", version.Get().String())) + InitFlags(pflag.CommandLine) pflag.CommandLine.SetNormalizeFunc(cliflag.WordSepNormalizeFunc) pflag.CommandLine.AddGoFlagSet(flag.CommandLine) @@ -317,6 +332,43 @@ func main() { setupLog.Info(fmt.Sprintf("CRD for %s not loaded, skipping.", supervisorGVR.String())) } + // Note: The kubebuilder RBAC markers above has to be kept in sync + // with the CRDs that should be migrated by this provider. + crdMigratorConfig := map[client.Object]crdmigrator.ByObjectConfig{} + if isGovmomiCRDLoaded { + crdMigratorConfig[&infrav1.VSphereCluster{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&infrav1.VSphereClusterTemplate{}] = crdmigrator.ByObjectConfig{UseCache: false} + crdMigratorConfig[&infrav1.VSphereMachine{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&infrav1.VSphereMachineTemplate{}] = crdmigrator.ByObjectConfig{UseCache: true} + crdMigratorConfig[&infrav1.VSphereVM{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&infrav1.VSphereClusterIdentity{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&infrav1.VSphereDeploymentZone{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&infrav1.VSphereFailureDomain{}] = crdmigrator.ByObjectConfig{UseCache: true} + } + if isSupervisorCRDLoaded { + crdMigratorConfig[&vmwarev1.VSphereCluster{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&vmwarev1.VSphereClusterTemplate{}] = crdmigrator.ByObjectConfig{UseCache: false} + crdMigratorConfig[&vmwarev1.VSphereMachine{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&vmwarev1.VSphereMachineTemplate{}] = crdmigrator.ByObjectConfig{UseCache: true, UseStatusForStorageVersionMigration: true} + crdMigratorConfig[&vmwarev1.ProviderServiceAccount{}] = crdmigrator.ByObjectConfig{UseCache: true} + } + + crdMigratorSkipPhases := []crdmigrator.Phase{} + for _, p := range skipCRDMigrationPhases { + crdMigratorSkipPhases = append(crdMigratorSkipPhases, crdmigrator.Phase(p)) + } + if err := (&crdmigrator.CRDMigrator{ + Client: mgr.GetClient(), + APIReader: mgr.GetAPIReader(), + SkipCRDMigrationPhases: crdMigratorSkipPhases, + Config: crdMigratorConfig, + // The CRDMigrator is run with only concurrency 1 to ensure we don't overwhelm the apiserver by patching a + // lot of CRs concurrently. + }).SetupWithManager(ctx, mgr, concurrency(1)); err != nil { + setupLog.Error(err, "Unable to create controller", "controller", "CRDMigrator") + os.Exit(1) + } + return nil } @@ -363,27 +415,27 @@ func main() { } func setupVAPIControllers(ctx context.Context, controllerCtx *capvcontext.ControllerManagerContext, mgr ctrlmgr.Manager, clusterCache clustercache.ClusterCache) error { - if err := (&webhooks.VSphereClusterTemplateWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&webhooks.VSphereClusterTemplate{}).SetupWebhookWithManager(mgr); err != nil { return err } - if err := (&webhooks.VSphereMachineWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&webhooks.VSphereMachine{}).SetupWebhookWithManager(mgr); err != nil { return err } - if err := (&webhooks.VSphereMachineTemplateWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&webhooks.VSphereMachineTemplate{}).SetupWebhookWithManager(mgr); err != nil { return err } - if err := (&webhooks.VSphereVMWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&webhooks.VSphereVM{}).SetupWebhookWithManager(mgr); err != nil { return err } - if err := (&webhooks.VSphereDeploymentZoneWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&webhooks.VSphereDeploymentZone{}).SetupWebhookWithManager(mgr); err != nil { return err } - if err := (&webhooks.VSphereFailureDomainWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&webhooks.VSphereFailureDomain{}).SetupWebhookWithManager(mgr); err != nil { return err } @@ -404,10 +456,10 @@ func setupVAPIControllers(ctx context.Context, controllerCtx *capvcontext.Contro } func setupSupervisorControllers(ctx context.Context, controllerCtx *capvcontext.ControllerManagerContext, mgr ctrlmgr.Manager, clusterCache clustercache.ClusterCache) error { - if err := (&vmwarewebhooks.VSphereMachineTemplateWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&vmwarewebhooks.VSphereMachineTemplate{}).SetupWebhookWithManager(mgr); err != nil { return err } - if err := (&vmwarewebhooks.VSphereMachineWebhook{}).SetupWebhookWithManager(mgr); err != nil { + if err := (&vmwarewebhooks.VSphereMachine{}).SetupWebhookWithManager(mgr); err != nil { return err } if err := controllers.AddClusterControllerToManager(ctx, controllerCtx, mgr, true, concurrency(vSphereClusterConcurrency)); err != nil { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/cluster_context.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/cluster_context.go index 2b3faf6bcbc..79d24cb78d1 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/cluster_context.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/cluster_context.go @@ -17,11 +17,9 @@ limitations under the License. package context import ( - "context" "fmt" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" - "sigs.k8s.io/cluster-api/util/conditions" "sigs.k8s.io/cluster-api/util/patch" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -38,15 +36,3 @@ type ClusterContext struct { func (c *ClusterContext) String() string { return fmt.Sprintf("%s %s/%s", c.VSphereCluster.GroupVersionKind(), c.VSphereCluster.Namespace, c.VSphereCluster.Name) } - -// Patch updates the object and its status on the API server. -func (c *ClusterContext) Patch(ctx context.Context) error { - // always update the readyCondition. - conditions.SetSummary(c.VSphereCluster, - conditions.WithConditions( - infrav1.VCenterAvailableCondition, - ), - ) - - return c.PatchHelper.Patch(ctx, c.VSphereCluster) -} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/interfaces.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/interfaces.go index 83c8b520269..0fac9252aee 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/interfaces.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/interfaces.go @@ -22,6 +22,7 @@ import ( metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" "sigs.k8s.io/controller-runtime/pkg/client" ) @@ -30,6 +31,7 @@ type MachineContext interface { String() string Patch(ctx context.Context) error GetVSphereMachine() VSphereMachine + GetReady() bool GetObjectMeta() metav1.ObjectMeta GetCluster() *clusterv1.Cluster GetMachine() *clusterv1.Machine @@ -40,4 +42,5 @@ type MachineContext interface { type VSphereMachine interface { client.Object conditions.Setter + v1beta2conditions.Setter } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/machine_context.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/machine_context.go index 14b3823ab96..300f7c0f02b 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/machine_context.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/machine_context.go @@ -59,7 +59,11 @@ func (c *VIMMachineContext) String() string { // Patch updates the object and its status on the API server. func (c *VIMMachineContext) Patch(ctx context.Context) error { - return c.PatchHelper.Patch(ctx, c.VSphereMachine) + return c.PatchHelper.Patch(ctx, c.VSphereMachine, patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + infrav1.VSphereMachineReadyV1Beta2Condition, + infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + clusterv1.PausedV1Beta2Condition, + }}) } // GetVSphereMachine sets the VSphereMachine for the VIMMachineContext. @@ -67,6 +71,11 @@ func (c *VIMMachineContext) GetVSphereMachine() VSphereMachine { return c.VSphereMachine } +// GetReady return when the VSphereMachine is ready. +func (c *VIMMachineContext) GetReady() bool { + return c.VSphereMachine.Status.Ready +} + // GetObjectMeta returns the ObjectMeta for the VSphereMachine in the VIMMachineContext. func (c *VIMMachineContext) GetObjectMeta() metav1.ObjectMeta { return c.VSphereMachine.ObjectMeta diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vm_context.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vm_context.go index 2b8c115a3eb..f789e35fb4f 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vm_context.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vm_context.go @@ -21,6 +21,7 @@ import ( "context" "fmt" + clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/patch" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -44,7 +45,15 @@ func (c *VMContext) String() string { // Patch updates the object and its status on the API server. func (c *VMContext) Patch(ctx context.Context) error { - return c.PatchHelper.Patch(ctx, c.VSphereVM) + return c.PatchHelper.Patch(ctx, c.VSphereVM, patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + infrav1.VSphereVMReadyV1Beta2Condition, + infrav1.VSphereVMVCenterAvailableV1Beta2Condition, + infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + infrav1.VSphereVMIPAddressClaimsFulfilledV1Beta2Condition, + infrav1.VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition, + infrav1.VSphereVMPCIDevicesDetachedV1Beta2Condition, + clusterv1.PausedV1Beta2Condition, + }}) } // GetSession returns this context's session. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/cluster_context.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/cluster_context.go index 9fed67d04f3..cced6c0a812 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/cluster_context.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/cluster_context.go @@ -18,11 +18,9 @@ limitations under the License. package vmware import ( - "context" "fmt" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" - "sigs.k8s.io/cluster-api/util/conditions" "sigs.k8s.io/cluster-api/util/patch" vmwarev1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1" @@ -39,16 +37,3 @@ type ClusterContext struct { func (c *ClusterContext) String() string { return fmt.Sprintf("%s %s/%s", c.VSphereCluster.GroupVersionKind(), c.VSphereCluster.Namespace, c.VSphereCluster.Name) } - -// Patch updates the object and its status on the API server. -func (c *ClusterContext) Patch(ctx context.Context) error { - // always update the readyCondition. - conditions.SetSummary(c.VSphereCluster, - conditions.WithConditions( - vmwarev1.ResourcePolicyReadyCondition, - vmwarev1.ClusterNetworkReadyCondition, - vmwarev1.LoadBalancerReadyCondition, - ), - ) - return c.PatchHelper.Patch(ctx, c.VSphereCluster) -} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/machine_context.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/machine_context.go index f460bbb95b1..de5fc53e2cf 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/machine_context.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware/machine_context.go @@ -22,7 +22,10 @@ import ( metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" + "sigs.k8s.io/cluster-api/util/patch" + infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" vmwarev1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1" capvcontext "sigs.k8s.io/cluster-api-provider-vsphere/pkg/context" ) @@ -46,7 +49,11 @@ func (c *SupervisorMachineContext) String() string { // Patch updates the object and its status on the API server. func (c *SupervisorMachineContext) Patch(ctx context.Context) error { - return c.PatchHelper.Patch(ctx, c.VSphereMachine) + return c.PatchHelper.Patch(ctx, c.VSphereMachine, patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + infrav1.VSphereMachineReadyV1Beta2Condition, + infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + clusterv1.PausedV1Beta2Condition, + }}) } // GetVSphereMachine returns the VSphereMachine from the SupervisorMachineContext. @@ -54,6 +61,11 @@ func (c *SupervisorMachineContext) GetVSphereMachine() capvcontext.VSphereMachin return c.VSphereMachine } +// GetReady return when the VSphereMachine is ready. +func (c *SupervisorMachineContext) GetReady() bool { + return c.VSphereMachine.Status.Ready +} + // GetObjectMeta returns the metadata for the VSphereMachine from the SupervisorMachineContext. func (c *SupervisorMachineContext) GetObjectMeta() metav1.ObjectMeta { return c.VSphereMachine.ObjectMeta diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vspheredeploymentzone_context.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vspheredeploymentzone_context.go index a2ec0923734..3e84cc4760b 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vspheredeploymentzone_context.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vspheredeploymentzone_context.go @@ -17,10 +17,8 @@ limitations under the License. package context import ( - "context" "fmt" - "sigs.k8s.io/cluster-api/util/conditions" "sigs.k8s.io/cluster-api/util/patch" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -35,18 +33,6 @@ type VSphereDeploymentZoneContext struct { AuthSession *session.Session } -// Patch patches the VSphereDeploymentZone. -func (c *VSphereDeploymentZoneContext) Patch(ctx context.Context) error { - conditions.SetSummary(c.VSphereDeploymentZone, - conditions.WithConditions( - infrav1.VCenterAvailableCondition, - infrav1.VSphereFailureDomainValidatedCondition, - infrav1.PlacementConstraintMetCondition, - ), - ) - return c.PatchHelper.Patch(ctx, c.VSphereDeploymentZone) -} - // String returns a string with the GroupVersionKind and name of the VSphereDeploymentZone. func (c *VSphereDeploymentZoneContext) String() string { return fmt.Sprintf("%s %s", c.VSphereDeploymentZone.GroupVersionKind(), c.VSphereDeploymentZone.Name) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/manager/manager.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/manager/manager.go index a5e8a229902..09b3c57cd3a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/manager/manager.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/manager/manager.go @@ -26,6 +26,7 @@ import ( vmoprv1 "github.com/vmware-tanzu/vm-operator/api/v1alpha2" ncpv1 "github.com/vmware-tanzu/vm-operator/external/ncp/api/v1alpha1" "gopkg.in/fsnotify.v1" + apiextensionsv1 "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1" clientgoscheme "k8s.io/client-go/kubernetes/scheme" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" bootstrapv1 "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1" @@ -54,6 +55,7 @@ func New(ctx context.Context, opts Options) (Manager, error) { // Ensure the default options are set. opts.defaults() + _ = apiextensionsv1.AddToScheme(opts.Scheme) _ = clientgoscheme.AddToScheme(opts.Scheme) _ = clusterv1.AddToScheme(opts.Scheme) _ = infrav1alpha3.AddToScheme(opts.Scheme) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/power.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/power.go index 9b69616f250..8170c71aad4 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/power.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/power.go @@ -18,13 +18,16 @@ package govmomi import ( "context" + "fmt" "time" "github.com/pkg/errors" "github.com/vmware/govmomi/vim25/mo" "github.com/vmware/govmomi/vim25/types" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" "sigs.k8s.io/controller-runtime/pkg/client" infrav1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/v1beta1" @@ -101,6 +104,12 @@ func (vms *VMService) triggerSoftPowerOff(ctx context.Context, virtualMachineCtx conditions.MarkFalse(virtualMachineCtx.VSphereVM, infrav1.GuestSoftPowerOffSucceededCondition, infrav1.GuestSoftPowerOffFailedReason, clusterv1.ConditionSeverityWarning, "VMware Tools not installed on VM %s", client.ObjectKeyFromObject(virtualMachineCtx.VSphereVM)) + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMGuestSoftPowerOffFailedV1Beta2Reason, + Message: fmt.Sprintf("VMware Tools not installed on VM %s", client.ObjectKeyFromObject(virtualMachineCtx.VSphereVM)), + }) // we are not able to trigger the soft power off so returning true to wait infinitely return true, nil } @@ -118,6 +127,12 @@ func (vms *VMService) triggerSoftPowerOff(ctx context.Context, virtualMachineCtx conditions.MarkFalse(virtualMachineCtx.VSphereVM, infrav1.GuestSoftPowerOffSucceededCondition, infrav1.GuestSoftPowerOffFailedReason, clusterv1.ConditionSeverityWarning, "unable to trigger soft power off because guest state change is not supported on VM %s.", client.ObjectKeyFromObject(virtualMachineCtx.VSphereVM)) + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMGuestSoftPowerOffFailedV1Beta2Reason, + Message: fmt.Sprintf("Unable to trigger soft power off because guest state change is not supported on VM %s.", client.ObjectKeyFromObject(virtualMachineCtx.VSphereVM)), + }) // we are not able to trigger the soft power off so returning true to wait infinitely return true, nil } @@ -129,5 +144,11 @@ func (vms *VMService) triggerSoftPowerOff(ctx context.Context, virtualMachineCtx conditions.MarkFalse(virtualMachineCtx.VSphereVM, infrav1.GuestSoftPowerOffSucceededCondition, infrav1.GuestSoftPowerOffInProgressReason, clusterv1.ConditionSeverityInfo, "guest soft power off initiated on VM %s", client.ObjectKeyFromObject(virtualMachineCtx.VSphereVM)) + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMGuestSoftPowerOffInProgressV1Beta2Reason, + Message: fmt.Sprintf("guest soft power off initiated on VM %s", client.ObjectKeyFromObject(virtualMachineCtx.VSphereVM)), + }) return true, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/service.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/service.go index 8393317fd22..6cb7793c14c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/service.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/service.go @@ -32,10 +32,12 @@ import ( "github.com/vmware/govmomi/vim25/mo" "github.com/vmware/govmomi/vim25/types" corev1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" apitypes "k8s.io/apimachinery/pkg/types" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" bootstrapv1 "sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/reconcile" @@ -89,6 +91,12 @@ func (vms *VMService) ReconcileVM(ctx context.Context, vmCtx *capvcontext.VMCont // later recovered, the machine will recover from this error. if wasNotFoundByBIOSUUID(err) { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.NotFoundByBIOSUUIDReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineNotFoundByBIOSUUIDV1Beta2Reason, + Message: err.Error(), + }) vm.State = infrav1.VirtualMachineStateNotFound return vm, err } @@ -98,12 +106,23 @@ func (vms *VMService) ReconcileVM(ctx context.Context, vmCtx *capvcontext.VMCont // in case of cloning errors or powering on errors. if !conditions.Has(vmCtx.VSphereVM, infrav1.VMProvisionedCondition) { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.CloningReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineWaitingForCloneV1Beta2Reason, + }) } // Get the bootstrap data. bootstrapData, format, err := vms.getBootstrapData(ctx, vmCtx) if err != nil { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.CloningFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineNotProvisionedV1Beta2Reason, + Message: err.Error(), + }) return vm, err } @@ -111,6 +130,12 @@ func (vms *VMService) ReconcileVM(ctx context.Context, vmCtx *capvcontext.VMCont err = createVM(ctx, vmCtx, bootstrapData, format) if err != nil { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.CloningFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineNotProvisionedV1Beta2Reason, + Message: err.Error(), + }) return vm, err } return vm, nil @@ -173,6 +198,12 @@ func (vms *VMService) ReconcileVM(ctx context.Context, vmCtx *capvcontext.VMCont if err := vms.reconcileTags(ctx, virtualMachineCtx); err != nil { conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.TagsAttachmentFailedReason, clusterv1.ConditionSeverityError, err.Error()) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineNotProvisionedV1Beta2Reason, + Message: err.Error(), + }) return vm, err } @@ -261,6 +292,11 @@ func (vms *VMService) DestroyVM(ctx context.Context, vmCtx *capvcontext.VMContex // Only set the GuestPowerOffCondition to true when the guest shutdown has been initiated. if conditions.Has(virtualMachineCtx.VSphereVM, infrav1.GuestSoftPowerOffSucceededCondition) { conditions.MarkTrue(virtualMachineCtx.VSphereVM, infrav1.GuestSoftPowerOffSucceededCondition) + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMGuestSoftPowerOffSucceededV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereVMGuestSoftPowerOffSucceededV1Beta2Reason, + }) } log.Info("VM is powered off") @@ -308,6 +344,12 @@ func (vms *VMService) reconcileIPAddresses(ctx context.Context, virtualMachineCt } if errors.Is(err, ipam.ErrWaitingForIPAddr) { conditions.MarkFalse(virtualMachineCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.WaitingForIPAddressReason, clusterv1.ConditionSeverityInfo, err.Error()) + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineWaitingForIPAddressV1Beta2Reason, + Message: err.Error(), + }) return false, nil } virtualMachineCtx.IPAMState = ipamState @@ -356,9 +398,20 @@ func (vms *VMService) reconcilePowerState(ctx context.Context, virtualMachineCtx task, err := virtualMachineCtx.Obj.PowerOn(ctx) if err != nil { conditions.MarkFalse(virtualMachineCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.PoweringOnFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineNotProvisionedV1Beta2Reason, + Message: err.Error(), + }) return false, errors.Wrapf(err, "failed to trigger power on op for vm %s", virtualMachineCtx) } conditions.MarkFalse(virtualMachineCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.PoweringOnReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachinePoweringOnV1Beta2Reason, + }) // Update the VSphereVM.Status.TaskRef to track the power-on task. virtualMachineCtx.VSphereVM.Status.TaskRef = task.Reference().Value @@ -513,6 +566,8 @@ func (vms *VMService) reconcilePCIDevices(ctx context.Context, virtualMachineCtx if len(specsToBeAdded) == 0 { if conditions.Has(virtualMachineCtx.VSphereVM, infrav1.PCIDevicesDetachedCondition) { conditions.Delete(virtualMachineCtx.VSphereVM, infrav1.PCIDevicesDetachedCondition) + + v1beta2conditions.Delete(virtualMachineCtx.VSphereVM, infrav1.VSphereVMPCIDevicesDetachedV1Beta2Condition) } log.V(5).Info("No new PCI devices to be added") return nil @@ -531,6 +586,13 @@ func (vms *VMService) reconcilePCIDevices(ctx context.Context, virtualMachineCtx infrav1.NotFoundReason, clusterv1.ConditionSeverityWarning, "PCI devices removed after VM was powered on") + + v1beta2conditions.Set(virtualMachineCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMPCIDevicesDetachedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMPCIDevicesDetachedNotFoundV1Beta2Reason, + Message: "PCI devices removed after VM was powered on", + }) return errors.Errorf("missing PCI devices") } log.Info("PCI devices to be added", "number", len(specsToBeAdded)) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/util.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/util.go index ee7927c9c84..fb196ba855b 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/util.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/util.go @@ -30,6 +30,7 @@ import ( metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/event" @@ -161,16 +162,28 @@ func checkAndRetryTask(ctx context.Context, vmCtx *capvcontext.VMContext, task * vmCtx.VSphereVM.Status.TaskRef = "" return false, nil case types.TaskInfoStateError: - log.Info("Task found: Task failed") - // NOTE: When a task fails there is no simple way to understand which operation is failing (e.g. cloning or powering on) // so we are reporting failures using a dedicated reason until we find a better solution. var errorMessage string if task.Info.Error != nil { + // If the result is InvalidPowerState and the VM's current and expected state are the same, it means the VM already + // was in the state we wanted it to be. + if isInvalidPowerStateAndExpectedPowerState(task.Info.Error.Fault) { + log.Info("Task found: Task failed to power vm, but VM is already in expected state") + vmCtx.VSphereVM.Status.TaskRef = "" + return false, nil + } errorMessage = task.Info.Error.LocalizedMessage } + + log.Info("Task found: Task failed") conditions.MarkFalse(vmCtx.VSphereVM, infrav1.VMProvisionedCondition, infrav1.TaskFailure, clusterv1.ConditionSeverityInfo, errorMessage) + v1beta2conditions.Set(vmCtx.VSphereVM, metav1.Condition{ + Type: infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereVMVirtualMachineTaskFailedV1Beta2Reason, + }) // Instead of directly requeuing the failed task, wait for the RetryAfter duration to pass // before resetting the taskRef from the VSphereVM status. @@ -186,6 +199,15 @@ func checkAndRetryTask(ctx context.Context, vmCtx *capvcontext.VMContext, task * } } +func isInvalidPowerStateAndExpectedPowerState(f types.BaseMethodFault) bool { + invalidPowerState, ok := f.(*types.InvalidPowerState) + if !ok { + return false + } + + return invalidPowerState.ExistingState == invalidPowerState.RequestedState +} + func reconcileVSphereVMWhenNetworkIsReady(ctx context.Context, virtualMachineCtx *virtualMachineContext, powerOnTask *object.Task) { reconcileVSphereVMOnChannel( ctx, diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/vcenter/clone.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/vcenter/clone.go index 23c9594c27c..ed184c5b3c4 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/vcenter/clone.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/govmomi/vcenter/clone.go @@ -27,6 +27,7 @@ import ( "github.com/vmware/govmomi/object" "github.com/vmware/govmomi/pbm" pbmTypes "github.com/vmware/govmomi/pbm/types" + "github.com/vmware/govmomi/property" "github.com/vmware/govmomi/vim25/mo" "github.com/vmware/govmomi/vim25/types" "k8s.io/utils/ptr" @@ -254,12 +255,28 @@ func Clone(ctx context.Context, vmCtx *capvcontext.VMContext, bootstrapData []by if err != nil { return errors.Wrapf(err, "failed to get owning cluster of resourcepool %q to calculate datastore based on storage policy", pool) } - dsGetter := object.NewComputeResource(vmCtx.Session.Client.Client, cluster.Reference()) - datastores, err := dsGetter.Datastores(ctx) + + dsList, err := object.NewComputeResource(vmCtx.Session.Client.Client, cluster.Reference()).Datastores(ctx) if err != nil { return errors.Wrapf(err, "unable to list datastores from owning cluster of requested resourcepool") } + + var refs []types.ManagedObjectReference + for i := range dsList { + refs = append(refs, dsList[i].Reference()) + } + + var datastores []mo.Datastore + if err := property.DefaultCollector(vmCtx.Session.Client.Client).Retrieve(ctx, refs, []string{"summary"}, &datastores); err != nil { + return errors.Wrapf(err, "unable to collect datastore properties to validate maintenance mode") + } + for _, ds := range datastores { + if ds.Summary.MaintenanceMode != string(types.DatastoreSummaryMaintenanceModeStateNormal) { + log.V(4).Info("datastore is in maintenance mode, skipping", "datastore", ds.Summary.Name) + continue + } + hubs = append(hubs, pbmTypes.PbmPlacementHub{ HubType: ds.Reference().Type, HubId: ds.Reference().Value, @@ -441,8 +458,6 @@ func createDataDisks(ctx context.Context, dataDiskDefs []infrav1.VSphereDisk, de } // Set provisioning type for the new data disk. - // Currently, if ThinProvisioned is not set, GOVC will set default to false. We may want to change this behavior - // to match what template image OS disk has configured to make them match if not set. switch dataDisk.ProvisioningMode { case infrav1.ThinProvisioningMode: backing.ThinProvisioned = types.NewBool(true) @@ -452,7 +467,7 @@ func createDataDisks(ctx context.Context, dataDiskDefs []infrav1.VSphereDisk, de backing.ThinProvisioned = types.NewBool(false) backing.EagerlyScrub = types.NewBool(true) default: - log.V(2).Info("No provisioning type detected. Leaving configuration empty.") + log.V(2).Info("No provisioning type detected. Leaving configuration empty.") } dev := &types.VirtualDisk{ diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/dummy_provider.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/dummy_provider.go index ef6578ffc34..5274a210a37 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/dummy_provider.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/dummy_provider.go @@ -20,8 +20,11 @@ import ( "context" vmoprv1 "github.com/vmware-tanzu/vm-operator/api/v1alpha2" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + vmwarev1 "sigs.k8s.io/cluster-api-provider-vsphere/apis/vmware/v1beta1" "sigs.k8s.io/cluster-api-provider-vsphere/pkg/context/vmware" "sigs.k8s.io/cluster-api-provider-vsphere/pkg/services" ) @@ -42,7 +45,12 @@ func (np *dummyNetworkProvider) SupportsVMReadinessProbe() bool { return true } -func (np *dummyNetworkProvider) ProvisionClusterNetwork(_ context.Context, _ *vmware.ClusterContext) error { +func (np *dummyNetworkProvider) ProvisionClusterNetwork(_ context.Context, clusterCtx *vmware.ClusterContext) error { + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterNetworkReadyV1Beta2Reason, + }) return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/netop_provider.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/netop_provider.go index f4f6757bf83..13a6d93b9a5 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/netop_provider.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/netop_provider.go @@ -26,6 +26,7 @@ import ( metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" @@ -57,6 +58,12 @@ func (np *netopNetworkProvider) SupportsVMReadinessProbe() bool { // ProvisionClusterNetwork marks the ClusterNetworkReadyCondition true. func (np *netopNetworkProvider) ProvisionClusterNetwork(_ context.Context, clusterCtx *vmware.ClusterContext) error { conditions.MarkTrue(clusterCtx.VSphereCluster, vmwarev1.ClusterNetworkReadyCondition) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterNetworkReadyV1Beta2Reason, + }) + return nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_provider.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_provider.go index 5a15d896055..0c77c8c2a16 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_provider.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_provider.go @@ -29,6 +29,7 @@ import ( "k8s.io/apimachinery/pkg/types" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -78,6 +79,12 @@ func (np *nsxtNetworkProvider) verifyNSXTVirtualNetworkStatus(vspherecluster *vm hasReadyCondition = true if condition.Status != "True" { conditions.MarkFalse(vspherecluster, vmwarev1.ClusterNetworkReadyCondition, vmwarev1.ClusterNetworkProvisionFailedReason, clusterv1.ConditionSeverityWarning, condition.Message) + v1beta2conditions.Set(vspherecluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkNotReadyV1Beta2Reason, + Message: condition.Message, + }) return errors.Errorf("virtual network ready status is: '%s' in cluster %s. reason: %s, message: %s", condition.Status, types.NamespacedName{Namespace: namespace, Name: clusterName}, condition.Reason, condition.Message) } @@ -85,10 +92,21 @@ func (np *nsxtNetworkProvider) verifyNSXTVirtualNetworkStatus(vspherecluster *vm if !hasReadyCondition { conditions.MarkFalse(vspherecluster, vmwarev1.ClusterNetworkReadyCondition, vmwarev1.ClusterNetworkProvisionFailedReason, clusterv1.ConditionSeverityWarning, "No Ready status for virtual network") + v1beta2conditions.Set(vspherecluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkNotReadyV1Beta2Reason, + Message: "No Ready status for virtual network", + }) return errors.Errorf("virtual network ready status in cluster %s has not been set", types.NamespacedName{Namespace: namespace, Name: clusterName}) } conditions.MarkTrue(vspherecluster, vmwarev1.ClusterNetworkReadyCondition) + v1beta2conditions.Set(vspherecluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterNetworkReadyV1Beta2Reason, + }) return nil } @@ -156,6 +174,12 @@ func (np *nsxtNetworkProvider) ProvisionClusterNetwork(ctx context.Context, clus }) if err != nil { conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.ClusterNetworkReadyCondition, vmwarev1.ClusterNetworkProvisionFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkNotReadyV1Beta2Reason, + Message: err.Error(), + }) return errors.Wrap(err, "Failed to provision network") } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_vpc_provider.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_vpc_provider.go index 926e7d7b3e0..3d871006b0c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_vpc_provider.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/network/nsxt_vpc_provider.go @@ -31,6 +31,7 @@ import ( "k8s.io/klog/v2" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -78,6 +79,12 @@ func (vp *nsxtVPCNetworkProvider) verifyNsxtVpcSubnetSetStatus(vspherecluster *v hasReadyCondition = true if condition.Status != corev1.ConditionTrue { conditions.MarkFalse(vspherecluster, vmwarev1.ClusterNetworkReadyCondition, vmwarev1.ClusterNetworkProvisionFailedReason, clusterv1.ConditionSeverityWarning, condition.Message) + v1beta2conditions.Set(vspherecluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkNotReadyV1Beta2Reason, + Message: condition.Message, + }) return errors.Errorf("subnetset ready status is: '%s' in cluster %s. reason: %s, message: %s", condition.Status, types.NamespacedName{Namespace: namespace, Name: clusterName}, condition.Reason, condition.Message) } @@ -85,10 +92,21 @@ func (vp *nsxtVPCNetworkProvider) verifyNsxtVpcSubnetSetStatus(vspherecluster *v if !hasReadyCondition { conditions.MarkFalse(vspherecluster, vmwarev1.ClusterNetworkReadyCondition, vmwarev1.ClusterNetworkProvisionFailedReason, clusterv1.ConditionSeverityWarning, "No Ready status for SubnetSet") + v1beta2conditions.Set(vspherecluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkNotReadyV1Beta2Reason, + Message: "No Ready status for SubnetSet", + }) return errors.Errorf("subnetset ready status in cluster %s has not been set", types.NamespacedName{Namespace: namespace, Name: clusterName}) } conditions.MarkTrue(vspherecluster, vmwarev1.ClusterNetworkReadyCondition) + v1beta2conditions.Set(vspherecluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterNetworkReadyV1Beta2Reason, + }) return nil } @@ -140,6 +158,12 @@ func (vp *nsxtVPCNetworkProvider) ProvisionClusterNetwork(ctx context.Context, c }) if err != nil { conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.ClusterNetworkReadyCondition, vmwarev1.ClusterNetworkProvisionFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterNetworkReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterNetworkNotReadyV1Beta2Reason, + Message: err.Error(), + }) return errors.Wrap(err, "Failed to provision network") } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vimmachine.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vimmachine.go index 330b0f5b3b1..5270df9750d 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vimmachine.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vimmachine.go @@ -32,6 +32,7 @@ import ( clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" clusterutilv1 "sigs.k8s.io/cluster-api/util" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -117,6 +118,8 @@ func (v *VimMachineService) ReconcileDelete(ctx context.Context, machineCtx capv // VSphereMachine wraps a VMSphereVM, so we are mirroring status from the underlying VMSphereVM // in order to provide evidences about machine deletion. conditions.SetMirror(vimMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vm) + v1beta2conditions.SetMirrorCondition(vm, vimMachineCtx.VSphereMachine, infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + v1beta2conditions.TargetConditionType(infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition)) return nil } @@ -165,6 +168,8 @@ func (v *VimMachineService) ReconcileNormal(ctx context.Context, machineCtx capv // VSphereMachine wraps a VMSphereVM, so we are mirroring status from the underlying VMSphereVM // in order to provide evidences about machine provisioning while provisioning is actually happening. conditions.SetMirror(vimMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vm) + v1beta2conditions.SetMirrorCondition(vm, vimMachineCtx.VSphereMachine, infrav1.VSphereVMVirtualMachineProvisionedV1Beta2Condition, + v1beta2conditions.TargetConditionType(infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition)) return true, nil } @@ -182,6 +187,11 @@ func (v *VimMachineService) ReconcileNormal(ctx context.Context, machineCtx capv return false, errors.Wrapf(err, "unexpected error while reconciling network for %s", vimMachineCtx) } conditions.MarkFalse(vimMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, infrav1.WaitingForNetworkAddressesReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(vimMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineWaitingForNetworkAddressV1Beta2Reason, + }) return true, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/control_plane_endpoint.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/control_plane_endpoint.go index e3ed22b27b9..c2655663725 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/control_plane_endpoint.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/control_plane_endpoint.go @@ -27,6 +27,7 @@ import ( "k8s.io/klog/v2" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -80,6 +81,12 @@ func (s *CPService) ReconcileControlPlaneEndpointService(ctx context.Context, cl if !apierrors.IsNotFound(err) { err = errors.Wrapf(err, "failed to check if VirtualMachineService exists") conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition, vmwarev1.LoadBalancerCreationFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterLoadBalancerNotReadyV1Beta2Reason, + Message: err.Error(), + }) return nil, err } @@ -88,6 +95,12 @@ func (s *CPService) ReconcileControlPlaneEndpointService(ctx context.Context, cl if err != nil { err = errors.Wrapf(err, "failed to get provider VirtualMachineService annotations") conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition, vmwarev1.LoadBalancerCreationFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterLoadBalancerNotReadyV1Beta2Reason, + Message: err.Error(), + }) return nil, err } @@ -95,6 +108,12 @@ func (s *CPService) ReconcileControlPlaneEndpointService(ctx context.Context, cl if err != nil { err = errors.Wrapf(err, "failed to create VirtualMachineService") conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition, vmwarev1.LoadBalancerCreationFailedReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterLoadBalancerNotReadyV1Beta2Reason, + Message: err.Error(), + }) return nil, err } } @@ -104,6 +123,12 @@ func (s *CPService) ReconcileControlPlaneEndpointService(ctx context.Context, cl if err != nil { err = errors.Wrapf(err, "VirtualMachineService LB does not yet have VIP assigned") conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition, vmwarev1.WaitingForLoadBalancerIPReason, clusterv1.ConditionSeverityInfo, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterLoadBalancerWaitingForIPV1Beta2Reason, + Message: err.Error(), + }) return nil, err } @@ -111,15 +136,32 @@ func (s *CPService) ReconcileControlPlaneEndpointService(ctx context.Context, cl if err != nil { err = errors.Wrapf(err, "VirtualMachineService LB does not have an apiserver endpoint") conditions.MarkFalse(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition, vmwarev1.WaitingForLoadBalancerIPReason, clusterv1.ConditionSeverityWarning, err.Error()) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: vmwarev1.VSphereClusterLoadBalancerWaitingForIPV1Beta2Reason, + Message: err.Error(), + }) return nil, err } conditions.MarkTrue(clusterCtx.VSphereCluster, vmwarev1.LoadBalancerReadyCondition) + v1beta2conditions.Set(clusterCtx.VSphereCluster, metav1.Condition{ + Type: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: vmwarev1.VSphereClusterLoadBalancerReadyV1Beta2Reason, + }) return cpEndpoint, nil } -func controlPlaneVMServiceName(ctx *vmware.ClusterContext) string { - return fmt.Sprintf("%s-control-plane-service", ctx.Cluster.Name) +func controlPlaneVMServiceName(clusterName string) string { + return clusterName +} + +// legacyControlPlaneVMServiceName was used for creating the ControlPlane VirtualMachineService prior to +// v1.13.0. It resulted in limiting the name of a Cluster to 41 characters (besides other places). +func legacyControlPlaneVMServiceName(clusterName string) string { + return fmt.Sprintf("%s-control-plane-service", clusterName) } // ClusterRoleVMLabels returns labels applied to a VirtualMachine in the cluster. The Control Plane @@ -143,7 +185,7 @@ func clusterRoleVMLabels(ctx *vmware.ClusterContext, controlPlane bool) map[stri func newVirtualMachineService(ctx *vmware.ClusterContext) *vmoprv1.VirtualMachineService { return &vmoprv1.VirtualMachineService{ ObjectMeta: metav1.ObjectMeta{ - Name: controlPlaneVMServiceName(ctx), + Name: controlPlaneVMServiceName(ctx.Cluster.Name), Namespace: ctx.Cluster.Namespace, }, TypeMeta: metav1.TypeMeta{ @@ -211,15 +253,26 @@ func (s *CPService) getVMControlPlaneService(ctx context.Context, clusterCtx *vm vmService := &vmoprv1.VirtualMachineService{} vmServiceKey := client.ObjectKey{ Namespace: clusterCtx.Cluster.Namespace, - Name: controlPlaneVMServiceName(clusterCtx), + Name: controlPlaneVMServiceName(clusterCtx.Cluster.Name), } if err := s.Client.Get(ctx, vmServiceKey, vmService); err != nil { if !apierrors.IsNotFound(err) { return nil, fmt.Errorf("failed to get VirtualMachineService %s: %v", vmServiceKey.Name, err) } - log.Info("VirtualMachineService was not found", "VirtualMachineService", klog.KRef(vmServiceKey.Namespace, vmServiceKey.Name)) - return nil, err + // In case of not finding the ControlPlane VirtualMachineService: fallback to try the legacy name. + fallbackVMServiceKey := client.ObjectKey{ + Namespace: vmServiceKey.Namespace, + Name: legacyControlPlaneVMServiceName(clusterCtx.Cluster.Name), + } + if fallbackErr := s.Client.Get(ctx, fallbackVMServiceKey, vmService); fallbackErr != nil { + if !apierrors.IsNotFound(fallbackErr) { + return nil, fmt.Errorf("failed to get VirtualMachineService %s: %v", fallbackVMServiceKey.Name, fallbackErr) + } + + log.Info("VirtualMachineService was not found", "VirtualMachineService", klog.KRef(vmServiceKey.Namespace, vmServiceKey.Name)) + return nil, err + } } return vmService, nil diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/vmopmachine.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/vmopmachine.go index be336f598e9..4f04868d495 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/vmopmachine.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/services/vmoperator/vmopmachine.go @@ -32,6 +32,7 @@ import ( "k8s.io/apimachinery/pkg/util/intstr" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" "sigs.k8s.io/cluster-api/util/conditions" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" ctrlutil "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" @@ -206,6 +207,12 @@ func (v *VmopMachineService) ReconcileNormal(ctx context.Context, machineCtx cap if err := v.reconcileVMOperatorVM(ctx, supervisorMachineCtx, vmOperatorVM); err != nil { conditions.MarkFalse(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vmwarev1.VMCreationFailedReason, clusterv1.ConditionSeverityWarning, fmt.Sprintf("failed to create or update VirtualMachine: %v", err)) + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineNotProvisionedV1Beta2Reason, + Message: fmt.Sprintf("failed to create or update VirtualMachine: %v", err), + }) // TODO: what to do if AlreadyExists error return false, err } @@ -240,11 +247,22 @@ func (v *VmopMachineService) ReconcileNormal(ctx context.Context, machineCtx cap continue } conditions.MarkFalse(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, c.Reason, clusterv1.ConditionSeverityError, c.Message) + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: c.Reason, + Message: c.Message, + }) return false, errors.Errorf("vm prerequisites check failed for condition %s: %s", condition, supervisorMachineCtx) } // All the pre-requisites are in place but the machines is not yet created, report it. conditions.MarkFalse(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vmwarev1.VMProvisionStartedReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineProvisioningV1Beta2Reason, + }) log.Info(fmt.Sprintf("VM is not yet created: %s", supervisorMachineCtx)) return true, nil } @@ -253,6 +271,11 @@ func (v *VmopMachineService) ReconcileNormal(ctx context.Context, machineCtx cap if vmOperatorVM.Status.PowerState != vmoprv1.VirtualMachinePowerStateOn { conditions.MarkFalse(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vmwarev1.PoweringOnReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachinePoweringOnV1Beta2Reason, + }) log.Info(fmt.Sprintf("VM is not yet powered on: %s", supervisorMachineCtx)) return true, nil } @@ -261,12 +284,22 @@ func (v *VmopMachineService) ReconcileNormal(ctx context.Context, machineCtx cap if vmOperatorVM.Status.Network == nil || (vmOperatorVM.Status.Network.PrimaryIP4 == "" && vmOperatorVM.Status.Network.PrimaryIP6 == "") { conditions.MarkFalse(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vmwarev1.WaitingForNetworkAddressReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineWaitingForNetworkAddressV1Beta2Reason, + }) log.Info(fmt.Sprintf("VM does not have an IP address: %s", supervisorMachineCtx)) return true, nil } if vmOperatorVM.Status.BiosUUID == "" { conditions.MarkFalse(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition, vmwarev1.WaitingForBIOSUUIDReason, clusterv1.ConditionSeverityInfo, "") + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionFalse, + Reason: infrav1.VSphereMachineVirtualMachineWaitingForBIOSUUIDV1Beta2Reason, + }) log.Info(fmt.Sprintf("VM does not have a BIOS UUID: %s", supervisorMachineCtx)) return true, nil } @@ -284,6 +317,11 @@ func (v *VmopMachineService) ReconcileNormal(ctx context.Context, machineCtx cap // Mark the VSphereMachine as Ready supervisorMachineCtx.VSphereMachine.Status.Ready = true conditions.MarkTrue(supervisorMachineCtx.VSphereMachine, infrav1.VMProvisionedCondition) + v1beta2conditions.Set(supervisorMachineCtx.VSphereMachine, metav1.Condition{ + Type: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Condition, + Status: metav1.ConditionTrue, + Reason: infrav1.VSphereMachineVirtualMachineProvisionedV1Beta2Reason, + }) return false, nil } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/error.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/error.go deleted file mode 100644 index f53fb5b49e8..00000000000 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/error.go +++ /dev/null @@ -1,40 +0,0 @@ -/* -Copyright 2022 The Kubernetes Authors. - -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 session - -import ( - "fmt" - "strings" -) - -const ( - errString = "vCenter version cannot be identified" -) - -// TODO (srm09): figure out a common place for custom errors. -type unidentifiedVCenterVersion struct { - version string -} - -func (e unidentifiedVCenterVersion) Error() string { - return fmt.Sprintf("%s: %s", errString, e.version) -} - -// IsUnidentifiedVCenterVersion identies an error as an unidentifiedVCenterVersion error. -func IsUnidentifiedVCenterVersion(err error) bool { - return strings.HasPrefix(err.Error(), errString) -} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/session.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/session.go index efc8885d06b..0f12d6964c6 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/session.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/pkg/session/session.go @@ -268,13 +268,13 @@ func (s *Session) GetVersion() (infrav1.VCenterVersion, error) { svcVersion := s.ServiceContent.About.Version version, err := semver.New(svcVersion) if err != nil { - return "", err + return "", errors.Wrapf(err, "failed to parse version %q", svcVersion) } if version.Major >= 6 { return infrav1.NewVCenterVersion(svcVersion), nil } - return "", unidentifiedVCenterVersion{version: svcVersion} + return "", errors.Errorf("version %q lower than 6", svcVersion) } // Clear is meant to destroy all the cached sessions. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/alias.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/alias.go new file mode 100644 index 00000000000..b67904608e6 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/alias.go @@ -0,0 +1,71 @@ +/* +Copyright 2025 The Kubernetes Authors. + +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 webhooks + +import ( + ctrl "sigs.k8s.io/controller-runtime" + + "sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks" +) + +// VSphereClusterTemplate implements a validation webhook for VSphereClusterTemplate. +type VSphereClusterTemplate struct{} + +// SetupWebhookWithManager sets up VSphereClusterTemplate webhooks. +func (webhook *VSphereClusterTemplate) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&webhooks.VSphereClusterTemplate{}).SetupWebhookWithManager(mgr) +} + +// VSphereDeploymentZone implements a defaulting webhook for VSphereDeploymentZone. +type VSphereDeploymentZone struct{} + +// SetupWebhookWithManager sets up VSphereDeploymentZone webhooks. +func (webhook *VSphereDeploymentZone) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&webhooks.VSphereDeploymentZone{}).SetupWebhookWithManager(mgr) +} + +// VSphereFailureDomain implements a validation and defaulting webhook for VSphereFailureDomain. +type VSphereFailureDomain struct{} + +// SetupWebhookWithManager sets up VSphereFailureDomain webhooks. +func (webhook *VSphereFailureDomain) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&webhooks.VSphereFailureDomain{}).SetupWebhookWithManager(mgr) +} + +// VSphereMachine implements a validation and defaulting webhook for VSphereMachine. +type VSphereMachine struct{} + +// SetupWebhookWithManager sets up VSphereMachine webhooks. +func (webhook *VSphereMachine) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&webhooks.VSphereMachine{}).SetupWebhookWithManager(mgr) +} + +// VSphereMachineTemplate implements a validation webhook for VSphereMachineTemplate. +type VSphereMachineTemplate struct{} + +// SetupWebhookWithManager sets up VSphereMachineTemplate webhooks. +func (webhook *VSphereMachineTemplate) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&webhooks.VSphereMachineTemplate{}).SetupWebhookWithManager(mgr) +} + +// VSphereVM implements a validation and defaulting webhook for VSphereVM. +type VSphereVM struct{} + +// SetupWebhookWithManager sets up VSphereVM webhooks. +func (webhook *VSphereVM) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&webhooks.VSphereVM{}).SetupWebhookWithManager(mgr) +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/doc.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/doc.go new file mode 100644 index 00000000000..d5942d4d103 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/doc.go @@ -0,0 +1,18 @@ +/* +Copyright 2025 The Kubernetes Authors. + +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 webhooks contains webhooks for the infrastructure v1beta1 API group. +package webhooks diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/alias.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/alias.go new file mode 100644 index 00000000000..fa0cf3edbfb --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/alias.go @@ -0,0 +1,39 @@ +/* +Copyright 2025 The Kubernetes Authors. + +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 vmware + +import ( + ctrl "sigs.k8s.io/controller-runtime" + + "sigs.k8s.io/cluster-api-provider-vsphere/internal/webhooks/vmware" +) + +// VSphereMachine implements a validation and defaulting webhook for VSphereMachine. +type VSphereMachine struct{} + +// SetupWebhookWithManager sets up VSphereMachine webhooks. +func (webhook *VSphereMachine) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&vmware.VSphereMachine{}).SetupWebhookWithManager(mgr) +} + +// VSphereMachineTemplate implements a validation webhook for VSphereMachineTemplate. +type VSphereMachineTemplate struct{} + +// SetupWebhookWithManager sets up VSphereMachineTemplate webhooks. +func (webhook *VSphereMachineTemplate) SetupWebhookWithManager(mgr ctrl.Manager) error { + return (&vmware.VSphereMachineTemplate{}).SetupWebhookWithManager(mgr) +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/doc.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/doc.go new file mode 100644 index 00000000000..db4a42b4e43 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api-provider-vsphere/webhooks/vmware/doc.go @@ -0,0 +1,18 @@ +/* +Copyright 2025 The Kubernetes Authors. + +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 vmware contains webhooks for the infrastructure vmware v1beta1 API group. +package vmware diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/cluster_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/cluster_types.go index bbce8f18131..de6fba2843e 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/cluster_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/cluster_types.go @@ -17,6 +17,7 @@ limitations under the License. package v1beta1 import ( + "cmp" "fmt" "net" "strings" @@ -465,7 +466,7 @@ type ClusterSpec struct { // +optional Paused bool `json:"paused,omitempty"` - // Cluster network configuration. + // clusterNetwork represents the cluster network configuration. // +optional ClusterNetwork *ClusterNetwork `json:"clusterNetwork,omitempty"` @@ -483,7 +484,7 @@ type ClusterSpec struct { // +optional InfrastructureRef *corev1.ObjectReference `json:"infrastructureRef,omitempty"` - // This encapsulates the topology for the cluster. + // topology encapsulates the topology for the cluster. // NOTE: It is required to enable the ClusterTopology // feature gate flag to activate managed topologies support; // this feature is highly experimental, and parts of it might still be not implemented. @@ -492,6 +493,9 @@ type ClusterSpec struct { // availabilityGates specifies additional conditions to include when evaluating Cluster Available condition. // + // If this field is not defined and the Cluster implements a managed topology, availabilityGates + // from the corresponding ClusterClass will be used, if any. + // // NOTE: this field is considered only for computing v1beta2 conditions. // +optional // +listType=map @@ -500,24 +504,61 @@ type ClusterSpec struct { AvailabilityGates []ClusterAvailabilityGate `json:"availabilityGates,omitempty"` } +// ConditionPolarity defines the polarity for a metav1.Condition. +type ConditionPolarity string + +const ( + // PositivePolarityCondition describe a condition with positive polarity, a condition + // where the normal state is True. e.g. NetworkReady. + PositivePolarityCondition ConditionPolarity = "Positive" + + // NegativePolarityCondition describe a condition with negative polarity, a condition + // where the normal state is False. e.g. MemoryPressure. + NegativePolarityCondition ConditionPolarity = "Negative" +) + // ClusterAvailabilityGate contains the type of a Cluster condition to be used as availability gate. type ClusterAvailabilityGate struct { - // conditionType refers to a positive polarity condition (status true means good) with matching type in the Cluster's condition list. + // conditionType refers to a condition with matching type in the Cluster's condition list. // If the conditions doesn't exist, it will be treated as unknown. // Note: Both Cluster API conditions or conditions added by 3rd party controllers can be used as availability gates. // +required // +kubebuilder:validation:Pattern=`^([a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*/)?(([A-Za-z0-9][-A-Za-z0-9_.]*)?[A-Za-z0-9])$` - // +kubebuilder:validation:MaxLength=316 // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=316 ConditionType string `json:"conditionType"` + + // polarity of the conditionType specified in this availabilityGate. + // Valid values are Positive, Negative and omitted. + // When omitted, the default behaviour will be Positive. + // A positive polarity means that the condition should report a true status under normal conditions. + // A negative polarity means that the condition should report a false status under normal conditions. + // +kubebuilder:validation:Enum=Positive;Negative + // +optional + Polarity ConditionPolarity `json:"polarity,omitempty"` } // Topology encapsulates the information of the managed resources. type Topology struct { - // The name of the ClusterClass object to create the topology. + // class is the name of the ClusterClass object to create the topology. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 Class string `json:"class"` - // The Kubernetes version of the cluster. + // classNamespace is the namespace of the ClusterClass object to create the topology. + // If the namespace is empty or not set, it is defaulted to the namespace of the cluster object. + // Value must follow the DNS1123Subdomain syntax. + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 + // +kubebuilder:validation:Pattern=`^[a-z0-9](?:[-a-z0-9]*[a-z0-9])?(?:\.[a-z0-9](?:[-a-z0-9]*[a-z0-9])?)*$` + ClassNamespace string `json:"classNamespace,omitempty"` + + // version is the Kubernetes version of the cluster. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Version string `json:"version"` // rolloutAfter performs a rollout of the entire cluster one component at a time, @@ -543,6 +584,7 @@ type Topology struct { // +optional // +listType=map // +listMapKey=name + // +kubebuilder:validation:MaxItems=1000 Variables []ClusterVariable `json:"variables,omitempty"` } @@ -584,6 +626,22 @@ type ControlPlaneTopology struct { // +optional NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"` + // readinessGates specifies additional conditions to include when evaluating Machine Ready condition. + // + // This field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready + // computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine. + // + // If this field is not defined, readinessGates from the corresponding ControlPlaneClass will be used, if any. + // + // NOTE: This field is considered only for computing v1beta2 conditions. + // NOTE: Specific control plane provider implementations might automatically extend the list of readinessGates; + // e.g. the kubeadm control provider adds ReadinessGates for the APIServerPodHealthy, SchedulerPodHealthy conditions, etc. + // +optional + // +listType=map + // +listMapKey=conditionType + // +kubebuilder:validation:MaxItems=32 + ReadinessGates []MachineReadinessGate `json:"readinessGates,omitempty"` + // variables can be used to customize the ControlPlane through patches. // +optional Variables *ControlPlaneVariables `json:"variables,omitempty"` @@ -595,12 +653,14 @@ type WorkersTopology struct { // +optional // +listType=map // +listMapKey=name + // +kubebuilder:validation:MaxItems=2000 MachineDeployments []MachineDeploymentTopology `json:"machineDeployments,omitempty"` // machinePools is a list of machine pools in the cluster. // +optional // +listType=map // +listMapKey=name + // +kubebuilder:validation:MaxItems=2000 MachinePools []MachinePoolTopology `json:"machinePools,omitempty"` } @@ -615,17 +675,25 @@ type MachineDeploymentTopology struct { // class is the name of the MachineDeploymentClass used to create the set of worker nodes. // This should match one of the deployment classes defined in the ClusterClass object // mentioned in the `Cluster.Spec.Class` field. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Class string `json:"class"` // name is the unique identifier for this MachineDeploymentTopology. // The value is used with other unique identifiers to create a MachineDeployment's Name // (e.g. cluster's name, etc). In case the name is greater than the allowed maximum length, // the values are hashed together. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 Name string `json:"name"` // failureDomain is the failure domain the machines will be created in. // Must match a key in the FailureDomains map stored on the cluster object. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 FailureDomain *string `json:"failureDomain,omitempty"` // replicas is the number of worker nodes belonging to this set. @@ -657,14 +725,28 @@ type MachineDeploymentTopology struct { // +optional NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"` - // Minimum number of seconds for which a newly created machine should + // minReadySeconds is the minimum number of seconds for which a newly created machine should // be ready. // Defaults to 0 (machine will be considered available as soon as it // is ready) // +optional MinReadySeconds *int32 `json:"minReadySeconds,omitempty"` - // The deployment strategy to use to replace existing machines with + // readinessGates specifies additional conditions to include when evaluating Machine Ready condition. + // + // This field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready + // computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine. + // + // If this field is not defined, readinessGates from the corresponding MachineDeploymentClass will be used, if any. + // + // NOTE: This field is considered only for computing v1beta2 conditions. + // +optional + // +listType=map + // +listMapKey=conditionType + // +kubebuilder:validation:MaxItems=32 + ReadinessGates []MachineReadinessGate `json:"readinessGates,omitempty"` + + // strategy is the deployment strategy to use to replace existing machines with // new ones. // +optional Strategy *MachineDeploymentStrategy `json:"strategy,omitempty"` @@ -704,17 +786,26 @@ type MachinePoolTopology struct { // class is the name of the MachinePoolClass used to create the pool of worker nodes. // This should match one of the deployment classes defined in the ClusterClass object // mentioned in the `Cluster.Spec.Class` field. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Class string `json:"class"` // name is the unique identifier for this MachinePoolTopology. // The value is used with other unique identifiers to create a MachinePool's Name // (e.g. cluster's name, etc). In case the name is greater than the allowed maximum length, // the values are hashed together. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 Name string `json:"name"` // failureDomains is the list of failure domains the machine pool will be created in. // Must match a key in the FailureDomains map stored on the cluster object. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 FailureDomains []string `json:"failureDomains,omitempty"` // nodeDrainTimeout is the total amount of time that the controller will spend on draining a node. @@ -734,7 +825,7 @@ type MachinePoolTopology struct { // +optional NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"` - // Minimum number of seconds for which a newly created machine pool should + // minReadySeconds is the minimum number of seconds for which a newly created machine pool should // be ready. // Defaults to 0 (machine will be considered available as soon as it // is ready) @@ -757,6 +848,9 @@ type MachinePoolTopology struct { // Variable definition in the ClusterClass `status` variables. type ClusterVariable struct { // name of the variable. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Name string `json:"name"` // definitionFrom specifies where the definition of this Variable is from. @@ -764,6 +858,7 @@ type ClusterVariable struct { // Deprecated: This field is deprecated, must not be set anymore and is going to be removed in the next apiVersion. // // +optional + // +kubebuilder:validation:MaxLength=256 DefinitionFrom string `json:"definitionFrom,omitempty"` // value of the variable. @@ -773,6 +868,7 @@ type ClusterVariable struct { // hard-coded schema for apiextensionsv1.JSON which cannot be produced by another type via controller-tools, // i.e. it is not possible to have no type field. // Ref: https://github.com/kubernetes-sigs/controller-tools/blob/d0e03a142d0ecdd5491593e941ee1d6b5d91dba6/pkg/crd/known_types.go#L106-L111 + // +required Value apiextensionsv1.JSON `json:"value"` } @@ -782,6 +878,7 @@ type ControlPlaneVariables struct { // +optional // +listType=map // +listMapKey=name + // +kubebuilder:validation:MaxItems=1000 Overrides []ClusterVariable `json:"overrides,omitempty"` } @@ -791,6 +888,7 @@ type MachineDeploymentVariables struct { // +optional // +listType=map // +listMapKey=name + // +kubebuilder:validation:MaxItems=1000 Overrides []ClusterVariable `json:"overrides,omitempty"` } @@ -800,6 +898,7 @@ type MachinePoolVariables struct { // +optional // +listType=map // +listMapKey=name + // +kubebuilder:validation:MaxItems=1000 Overrides []ClusterVariable `json:"overrides,omitempty"` } @@ -815,16 +914,18 @@ type ClusterNetwork struct { // +optional APIServerPort *int32 `json:"apiServerPort,omitempty"` - // The network ranges from which service VIPs are allocated. + // services is the network ranges from which service VIPs are allocated. // +optional Services *NetworkRanges `json:"services,omitempty"` - // The network ranges from which Pod networks are allocated. + // pods is the network ranges from which Pod networks are allocated. // +optional Pods *NetworkRanges `json:"pods,omitempty"` - // Domain name for services. + // serviceDomain is the domain name for services. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 ServiceDomain string `json:"serviceDomain,omitempty"` } @@ -834,6 +935,11 @@ type ClusterNetwork struct { // NetworkRanges represents ranges of network addresses. type NetworkRanges struct { + // cidrBlocks is a list of CIDR blocks. + // +required + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=43 CIDRBlocks []string `json:"cidrBlocks"` } @@ -869,11 +975,13 @@ type ClusterStatus struct { // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 FailureMessage *string `json:"failureMessage,omitempty"` // phase represents the current phase of cluster actuation. - // E.g. Pending, Running, Terminating, Failed etc. // +optional + // +kubebuilder:validation:Enum=Pending;Provisioning;Provisioned;Deleting;Failed;Unknown Phase string `json:"phase,omitempty"` // infrastructureReady is the state of the infrastructure provider. @@ -998,10 +1106,14 @@ func (c *ClusterStatus) GetTypedPhase() ClusterPhase { // APIEndpoint represents a reachable Kubernetes API endpoint. type APIEndpoint struct { - // The hostname on which the API server is serving. + // host is the hostname on which the API server is serving. + // TODO: Can't set MinLength=1 for now, because this struct is not always used in pointer fields so today we have cases where host is set to an empty string. + // +required + // +kubebuilder:validation:MaxLength=512 Host string `json:"host"` - // The port on which the API server is serving. + // port is the port on which the API server is serving. + // +required Port int32 `json:"port"` } @@ -1033,10 +1145,17 @@ func (v APIEndpoint) String() string { // Cluster is the Schema for the clusters API. type Cluster struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec ClusterSpec `json:"spec,omitempty"` + // spec is the desired state of Cluster. + // +optional + Spec ClusterSpec `json:"spec,omitempty"` + // status is the observed state of Cluster. + // +optional Status ClusterStatus `json:"status,omitempty"` } @@ -1045,7 +1164,9 @@ func (c *Cluster) GetClassKey() types.NamespacedName { if c.Spec.Topology == nil { return types.NamespacedName{} } - return types.NamespacedName{Namespace: c.GetNamespace(), Name: c.Spec.Topology.Class} + + namespace := cmp.Or(c.Spec.Topology.ClassNamespace, c.Namespace) + return types.NamespacedName{Namespace: namespace, Name: c.Spec.Topology.Class} } // GetConditions returns the set of conditions for this object. @@ -1166,8 +1287,12 @@ func (f ClusterIPFamily) String() string { // ClusterList contains a list of Cluster. type ClusterList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []Cluster `json:"items"` + // items is the list of Clusters. + Items []Cluster `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/clusterclass_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/clusterclass_types.go index 1f7984fd00f..4d62dbf7246 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/clusterclass_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/clusterclass_types.go @@ -72,15 +72,33 @@ const ( // ClusterClass is a template which can be used to create managed topologies. type ClusterClass struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec ClusterClassSpec `json:"spec,omitempty"` + // spec is the desired state of ClusterClass. + // +optional + Spec ClusterClassSpec `json:"spec,omitempty"` + // status is the observed state of ClusterClass. + // +optional Status ClusterClassStatus `json:"status,omitempty"` } // ClusterClassSpec describes the desired state of the ClusterClass. type ClusterClassSpec struct { + // availabilityGates specifies additional conditions to include when evaluating Cluster Available condition. + // + // NOTE: this field is considered only for computing v1beta2 conditions. + // NOTE: If a Cluster is using this ClusterClass, and this Cluster defines a custom list of availabilityGates, + // such list overrides availabilityGates defined in this field. + // +optional + // +listType=map + // +listMapKey=conditionType + // +kubebuilder:validation:MaxItems=32 + AvailabilityGates []ClusterAvailabilityGate `json:"availabilityGates,omitempty"` + // infrastructure is a reference to a provider-specific template that holds // the details for provisioning infrastructure specific cluster // for the underlying provider. @@ -89,6 +107,10 @@ type ClusterClassSpec struct { // +optional Infrastructure LocalObjectTemplate `json:"infrastructure,omitempty"` + // infrastructureNamingStrategy allows changing the naming pattern used when creating the infrastructure object. + // +optional + InfrastructureNamingStrategy *InfrastructureNamingStrategy `json:"infrastructureNamingStrategy,omitempty"` + // controlPlane is a reference to a local struct that holds the details // for provisioning the Control Plane for the Cluster. // +optional @@ -103,12 +125,14 @@ type ClusterClassSpec struct { // variables defines the variables which can be configured // in the Cluster topology and are then used in patches. // +optional + // +kubebuilder:validation:MaxItems=1000 Variables []ClusterClassVariable `json:"variables,omitempty"` // patches defines the patches which are applied to customize // referenced templates of a ClusterClass. // Note: Patches will be applied in the order of the array. // +optional + // +kubebuilder:validation:MaxItems=1000 Patches []ClusterClassPatch `json:"patches,omitempty"` } @@ -165,6 +189,22 @@ type ControlPlaneClass struct { // NOTE: This value can be overridden while defining a Cluster.Topology. // +optional NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"` + + // readinessGates specifies additional conditions to include when evaluating Machine Ready condition. + // + // This field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready + // computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine. + // + // NOTE: This field is considered only for computing v1beta2 conditions. + // NOTE: If a Cluster defines a custom list of readinessGates for the control plane, + // such list overrides readinessGates defined in this field. + // NOTE: Specific control plane provider implementations might automatically extend the list of readinessGates; + // e.g. the kubeadm control provider adds ReadinessGates for the APIServerPodHealthy, SchedulerPodHealthy conditions, etc. + // +optional + // +listType=map + // +listMapKey=conditionType + // +kubebuilder:validation:MaxItems=32 + ReadinessGates []MachineReadinessGate `json:"readinessGates,omitempty"` } // ControlPlaneClassNamingStrategy defines the naming strategy for control plane objects. @@ -177,6 +217,23 @@ type ControlPlaneClassNamingStrategy struct { // * `.cluster.name`: The name of the cluster object. // * `.random`: A random alphanumeric string, without vowels, of length 5. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 + Template *string `json:"template,omitempty"` +} + +// InfrastructureNamingStrategy defines the naming strategy for infrastructure objects. +type InfrastructureNamingStrategy struct { + // template defines the template to use for generating the name of the Infrastructure object. + // If not defined, it will fallback to `{{ .cluster.name }}-{{ .random }}`. + // If the templated string exceeds 63 characters, it will be trimmed to 58 characters and will + // get concatenated with a random suffix of length 5. + // The templating mechanism provides the following arguments: + // * `.cluster.name`: The name of the cluster object. + // * `.random`: A random alphanumeric string, without vowels, of length 5. + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 Template *string `json:"template,omitempty"` } @@ -187,6 +244,7 @@ type WorkersClass struct { // +optional // +listType=map // +listMapKey=class + // +kubebuilder:validation:MaxItems=100 MachineDeployments []MachineDeploymentClass `json:"machineDeployments,omitempty"` // machinePools is a list of machine pool classes that can be used to create @@ -194,6 +252,7 @@ type WorkersClass struct { // +optional // +listType=map // +listMapKey=class + // +kubebuilder:validation:MaxItems=100 MachinePools []MachinePoolClass `json:"machinePools,omitempty"` } @@ -203,10 +262,14 @@ type MachineDeploymentClass struct { // class denotes a type of worker node present in the cluster, // this name MUST be unique within a ClusterClass and can be referenced // in the Cluster to create a managed MachineDeployment. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Class string `json:"class"` // template is a local struct containing a collection of templates for creation of // MachineDeployment objects representing a set of worker nodes. + // +required Template MachineDeploymentClassTemplate `json:"template"` // machineHealthCheck defines a MachineHealthCheck for this MachineDeploymentClass. @@ -217,6 +280,8 @@ type MachineDeploymentClass struct { // Must match a key in the FailureDomains map stored on the cluster object. // NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 FailureDomain *string `json:"failureDomain,omitempty"` // namingStrategy allows changing the naming pattern used when creating the MachineDeployment. @@ -243,16 +308,32 @@ type MachineDeploymentClass struct { // +optional NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"` - // Minimum number of seconds for which a newly created machine should + // minReadySeconds is the minimum number of seconds for which a newly created machine should // be ready. // Defaults to 0 (machine will be considered available as soon as it // is ready) // NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass. + // +optional MinReadySeconds *int32 `json:"minReadySeconds,omitempty"` - // The deployment strategy to use to replace existing machines with + // readinessGates specifies additional conditions to include when evaluating Machine Ready condition. + // + // This field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready + // computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine. + // + // NOTE: This field is considered only for computing v1beta2 conditions. + // NOTE: If a Cluster defines a custom list of readinessGates for a MachineDeployment using this MachineDeploymentClass, + // such list overrides readinessGates defined in this field. + // +optional + // +listType=map + // +listMapKey=conditionType + // +kubebuilder:validation:MaxItems=32 + ReadinessGates []MachineReadinessGate `json:"readinessGates,omitempty"` + + // strategy is the deployment strategy to use to replace existing machines with // new ones. // NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass. + // +optional Strategy *MachineDeploymentStrategy `json:"strategy,omitempty"` } @@ -266,10 +347,12 @@ type MachineDeploymentClassTemplate struct { // bootstrap contains the bootstrap template reference to be used // for the creation of worker Machines. + // +required Bootstrap LocalObjectTemplate `json:"bootstrap"` // infrastructure contains the infrastructure template reference to be used // for the creation of worker Machines. + // +required Infrastructure LocalObjectTemplate `json:"infrastructure"` } @@ -284,6 +367,8 @@ type MachineDeploymentClassNamingStrategy struct { // * `.random`: A random alphanumeric string, without vowels, of length 5. // * `.machineDeployment.topologyName`: The name of the MachineDeployment topology (Cluster.spec.topology.workers.machineDeployments[].name). // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 Template *string `json:"template,omitempty"` } @@ -294,20 +379,25 @@ type MachineHealthCheckClass struct { // logical OR, i.e. if any of the conditions is met, the node is unhealthy. // // +optional + // +kubebuilder:validation:MaxItems=100 UnhealthyConditions []UnhealthyCondition `json:"unhealthyConditions,omitempty"` - // Any further remediation is only allowed if at most "MaxUnhealthy" machines selected by + // maxUnhealthy specifies the maximum number of unhealthy machines allowed. + // Any further remediation is only allowed if at most "maxUnhealthy" machines selected by // "selector" are not healthy. // +optional MaxUnhealthy *intstr.IntOrString `json:"maxUnhealthy,omitempty"` + // unhealthyRange specifies the range of unhealthy machines allowed. // Any further remediation is only allowed if the number of machines selected by "selector" as not healthy - // is within the range of "UnhealthyRange". Takes precedence over MaxUnhealthy. + // is within the range of "unhealthyRange". Takes precedence over maxUnhealthy. // Eg. "[3-5]" - This means that remediation will be allowed only when: // (a) there are at least 3 unhealthy machines (and) // (b) there are at most 5 unhealthy machines // +optional // +kubebuilder:validation:Pattern=^\[[0-9]+-[0-9]+\]$ + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=32 UnhealthyRange *string `json:"unhealthyRange,omitempty"` // nodeStartupTimeout allows to set the maximum time for MachineHealthCheck @@ -341,16 +431,23 @@ type MachinePoolClass struct { // class denotes a type of machine pool present in the cluster, // this name MUST be unique within a ClusterClass and can be referenced // in the Cluster to create a managed MachinePool. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Class string `json:"class"` // template is a local struct containing a collection of templates for creation of // MachinePools objects representing a pool of worker nodes. + // +required Template MachinePoolClassTemplate `json:"template"` // failureDomains is the list of failure domains the MachinePool should be attached to. // Must match a key in the FailureDomains map stored on the cluster object. // NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 FailureDomains []string `json:"failureDomains,omitempty"` // namingStrategy allows changing the naming pattern used when creating the MachinePool. @@ -377,11 +474,12 @@ type MachinePoolClass struct { // +optional NodeDeletionTimeout *metav1.Duration `json:"nodeDeletionTimeout,omitempty"` - // Minimum number of seconds for which a newly created machine pool should + // minReadySeconds is the minimum number of seconds for which a newly created machine pool should // be ready. // Defaults to 0 (machine will be considered available as soon as it // is ready) // NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass. + // +optional MinReadySeconds *int32 `json:"minReadySeconds,omitempty"` } @@ -395,10 +493,12 @@ type MachinePoolClassTemplate struct { // bootstrap contains the bootstrap template reference to be used // for the creation of the Machines in the MachinePool. + // +required Bootstrap LocalObjectTemplate `json:"bootstrap"` // infrastructure contains the infrastructure template reference to be used // for the creation of the MachinePool. + // +required Infrastructure LocalObjectTemplate `json:"infrastructure"` } @@ -413,6 +513,8 @@ type MachinePoolClassNamingStrategy struct { // * `.random`: A random alphanumeric string, without vowels, of length 5. // * `.machinePool.topologyName`: The name of the MachinePool topology (Cluster.spec.topology.workers.machinePools[].name). // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 Template *string `json:"template,omitempty"` } @@ -425,12 +527,16 @@ func (m MachineHealthCheckClass) IsZero() bool { // be configured in the Cluster topology and used in patches. type ClusterClassVariable struct { // name of the variable. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Name string `json:"name"` // required specifies if the variable is required. // Note: this applies to the variable as a whole and thus the // top-level object defined in the schema. If nested fields are // required, this will be specified inside the schema. + // +required Required bool `json:"required"` // metadata is the metadata of a variable. @@ -443,6 +549,7 @@ type ClusterClassVariable struct { Metadata ClusterClassVariableMetadata `json:"metadata,omitempty"` // schema defines the schema of the variable. + // +required Schema VariableSchema `json:"schema"` } @@ -452,7 +559,7 @@ type ClusterClassVariable struct { // // Deprecated: This struct is deprecated and is going to be removed in the next apiVersion. type ClusterClassVariableMetadata struct { - // Map of string keys and values that can be used to organize and categorize + // labels is a map of string keys and values that can be used to organize and categorize // (scope and select) variables. // +optional Labels map[string]string `json:"labels,omitempty"` @@ -469,6 +576,7 @@ type VariableSchema struct { // openAPIV3Schema defines the schema of a variable via OpenAPI v3 // schema. The schema is a subset of the schema used in // Kubernetes CRDs. + // +required OpenAPIV3Schema JSONSchemaProps `json:"openAPIV3Schema"` } @@ -479,14 +587,19 @@ type VariableSchema struct { // which are not supported in CAPI have been removed. type JSONSchemaProps struct { // description is a human-readable description of this variable. + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=4096 Description string `json:"description,omitempty"` // example is an example for this variable. + // +optional Example *apiextensionsv1.JSON `json:"example,omitempty"` // type is the type of the variable. // Valid values are: object, array, string, integer, number or boolean. // +optional + // +kubebuilder:validation:Enum=object;array;string;integer;number;boolean Type string `json:"type,omitempty"` // properties specifies fields of an object. @@ -522,6 +635,9 @@ type JSONSchemaProps struct { // required specifies which fields of an object are required. // NOTE: Can only be set if type is object. // +optional + // +kubebuilder:validation:MaxItems=1000 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 Required []string `json:"required,omitempty"` // items specifies fields of an array. @@ -553,6 +669,8 @@ type JSONSchemaProps struct { // https://github.com/kubernetes/apiextensions-apiserver/blob/master/pkg/apiserver/validation/formats.go // NOTE: Can only be set if type is string. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=32 Format string `json:"format,omitempty"` // maxLength is the max length of a string variable. @@ -568,6 +686,8 @@ type JSONSchemaProps struct { // pattern is the regex which a string variable must match. // NOTE: Can only be set if type is string. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Pattern string `json:"pattern,omitempty"` // maximum is the maximum of an integer or number variable. @@ -603,6 +723,7 @@ type JSONSchemaProps struct { // enum is the list of valid values of the variable. // NOTE: Can be set for all types. // +optional + // +kubebuilder:validation:MaxItems=100 Enum []apiextensionsv1.JSON `json:"enum,omitempty"` // default is the default value of the variable. @@ -614,6 +735,7 @@ type JSONSchemaProps struct { // +optional // +listType=map // +listMapKey=rule + // +kubebuilder:validation:MaxItems=100 XValidations []ValidationRule `json:"x-kubernetes-validations,omitempty"` // x-metadata is the metadata of a variable or a nested field within a variable. @@ -673,7 +795,7 @@ type JSONSchemaProps struct { // VariableSchemaMetadata is the metadata of a variable or a nested field within a variable. // It can be used to add additional data for higher level tools. type VariableSchemaMetadata struct { - // Map of string keys and values that can be used to organize and categorize + // labels is a map of string keys and values that can be used to organize and categorize // (scope and select) variables. // +optional Labels map[string]string `json:"labels,omitempty"` @@ -736,12 +858,16 @@ type ValidationRule struct { // skipped if an old value could not be found. // // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=4096 Rule string `json:"rule"` // message represents the message displayed when validation fails. The message is required if the Rule contains // line breaks. The message must not contain line breaks. // If unset, the message is "failed rule: {Rule}". // e.g. "must be a URL with the host matching spec.host" // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Message string `json:"message,omitempty"` // messageExpression declares a CEL expression that evaluates to the validation failure message that is returned when this rule fails. // Since messageExpression is used as a failure message, it must evaluate to a string. @@ -753,6 +879,8 @@ type ValidationRule struct { // Example: // "x must be less than max ("+string(self.max)+")" // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 MessageExpression string `json:"messageExpression,omitempty"` // reason provides a machine-readable validation failure reason that is returned to the caller when a request fails this validation rule. // The currently supported reasons are: "FieldValueInvalid", "FieldValueForbidden", "FieldValueRequired", "FieldValueDuplicate". @@ -773,6 +901,8 @@ type ValidationRule struct { // For field name which contains special characters, use `['specialName']` to refer the field name. // e.g. for attribute `foo.34$` appears in a list `testList`, the fieldPath could be set to `.testList['foo.34$']` // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 FieldPath string `json:"fieldPath,omitempty"` } @@ -798,9 +928,15 @@ const ( // ClusterClassPatch defines a patch which is applied to customize the referenced templates. type ClusterClassPatch struct { // name of the patch. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Name string `json:"name"` // description is a human-readable description of this patch. + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 Description string `json:"description,omitempty"` // enabledIf is a Go template to be used to calculate if a patch should be enabled. @@ -809,12 +945,15 @@ type ClusterClassPatch struct { // be disabled. // If EnabledIf is not set, the patch will be enabled per default. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 EnabledIf *string `json:"enabledIf,omitempty"` // definitions define inline patches. // Note: Patches will be applied in the order of the array. // Note: Exactly one of Definitions or External must be set. // +optional + // +kubebuilder:validation:MaxItems=100 Definitions []PatchDefinition `json:"definitions,omitempty"` // external defines an external patch. @@ -826,11 +965,14 @@ type ClusterClassPatch struct { // PatchDefinition defines a patch which is applied to customize the referenced templates. type PatchDefinition struct { // selector defines on which templates the patch should be applied. + // +required Selector PatchSelector `json:"selector"` // jsonPatches defines the patches which should be applied on the templates // matching the selector. // Note: Patches will be applied in the order of the array. + // +kubebuilder:validation:MaxItems=100 + // +required JSONPatches []JSONPatch `json:"jsonPatches"` } @@ -841,12 +983,19 @@ type PatchDefinition struct { // Note: The results of selection based on the individual fields are ANDed. type PatchSelector struct { // apiVersion filters templates by apiVersion. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 APIVersion string `json:"apiVersion"` // kind filters templates by kind. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Kind string `json:"kind"` // matchResources selects templates based on where they are referenced. + // +required MatchResources PatchSelectorMatch `json:"matchResources"` } @@ -880,6 +1029,9 @@ type PatchSelectorMatch struct { type PatchSelectorMatchMachineDeploymentClass struct { // names selects templates by class names. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 Names []string `json:"names,omitempty"` } @@ -888,6 +1040,9 @@ type PatchSelectorMatchMachineDeploymentClass struct { type PatchSelectorMatchMachinePoolClass struct { // names selects templates by class names. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 Names []string `json:"names,omitempty"` } @@ -895,6 +1050,8 @@ type PatchSelectorMatchMachinePoolClass struct { type JSONPatch struct { // op defines the operation of the patch. // Note: Only `add`, `replace` and `remove` are supported. + // +required + // +kubebuilder:validation:Enum=add;replace;remove Op string `json:"op"` // path defines the path of the patch. @@ -902,6 +1059,9 @@ type JSONPatch struct { // Note: For now the only allowed array modifications are `append` and `prepend`, i.e.: // * for op: `add`: only index 0 (prepend) and - (append) are allowed // * for op: `replace` or `remove`: no indexes are allowed + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Path string `json:"path"` // value defines the value of the patch. @@ -927,12 +1087,16 @@ type JSONPatchValue struct { // variable is the variable to be used as value. // Variable can be one of the variables defined in .spec.variables or a builtin variable. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Variable *string `json:"variable,omitempty"` // template is the Go template to be used to calculate the value. // A template can reference variables defined in .spec.variables and builtin variables. // Note: The template must evaluate to a valid YAML or JSON value. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 Template *string `json:"template,omitempty"` } @@ -941,14 +1105,20 @@ type JSONPatchValue struct { type ExternalPatchDefinition struct { // generateExtension references an extension which is called to generate patches. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 GenerateExtension *string `json:"generateExtension,omitempty"` // validateExtension references an extension which is called to validate the topology. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 ValidateExtension *string `json:"validateExtension,omitempty"` // discoverVariablesExtension references an extension which is called to discover variables. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 DiscoverVariablesExtension *string `json:"discoverVariablesExtension,omitempty"` // settings defines key value pairs to be passed to the extensions. @@ -962,6 +1132,7 @@ type ExternalPatchDefinition struct { type LocalObjectTemplate struct { // ref is a required reference to a custom resource // offered by a provider. + // +required Ref *corev1.ObjectReference `json:"ref"` } @@ -971,6 +1142,7 @@ type LocalObjectTemplate struct { type ClusterClassStatus struct { // variables is a list of ClusterClassStatusVariable that are defined for the ClusterClass. // +optional + // +kubebuilder:validation:MaxItems=1000 Variables []ClusterClassStatusVariable `json:"variables,omitempty"` // conditions defines current observed state of the ClusterClass. @@ -1001,6 +1173,9 @@ type ClusterClassV1Beta2Status struct { // ClusterClassStatusVariable defines a variable which appears in the status of a ClusterClass. type ClusterClassStatusVariable struct { // name is the name of the variable. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Name string `json:"name"` // definitionsConflict specifies whether or not there are conflicting definitions for a single variable name. @@ -1008,6 +1183,8 @@ type ClusterClassStatusVariable struct { DefinitionsConflict bool `json:"definitionsConflict"` // definitions is a list of definitions for a variable. + // +kubebuilder:validation:MaxItems=100 + // +required Definitions []ClusterClassStatusVariableDefinition `json:"definitions"` } @@ -1016,12 +1193,16 @@ type ClusterClassStatusVariableDefinition struct { // from specifies the origin of the variable definition. // This will be `inline` for variables defined in the ClusterClass or the name of a patch defined in the ClusterClass // for variables discovered from a DiscoverVariables runtime extensions. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 From string `json:"from"` // required specifies if the variable is required. // Note: this applies to the variable as a whole and thus the // top-level object defined in the schema. If nested fields are // required, this will be specified inside the schema. + // +required Required bool `json:"required"` // metadata is the metadata of a variable. @@ -1034,6 +1215,7 @@ type ClusterClassStatusVariableDefinition struct { Metadata ClusterClassVariableMetadata `json:"metadata,omitempty"` // schema defines the schema of the variable. + // +required Schema VariableSchema `json:"schema"` } @@ -1070,8 +1252,12 @@ func (c *ClusterClass) SetV1Beta2Conditions(conditions []metav1.Condition) { // ClusterClassList contains a list of Cluster. type ClusterClassList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []ClusterClass `json:"items"` + // items is the list of ClusterClasses. + Items []ClusterClass `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/common_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/common_types.go index f70b0f3e4a3..2006bb88ce9 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/common_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/common_types.go @@ -92,6 +92,9 @@ const ( // LabelsFromMachineAnnotation is the annotation set on nodes to track the labels originated from machines. LabelsFromMachineAnnotation = "cluster.x-k8s.io/labels-from-machine" + // AnnotationsFromMachineAnnotation is the annotation set on nodes to track the annotations that originated from machines. + AnnotationsFromMachineAnnotation = "cluster.x-k8s.io/annotations-from-machine" + // OwnerNameAnnotation is the annotation set on nodes identifying the owner name. OwnerNameAnnotation = "cluster.x-k8s.io/owner-name" @@ -128,7 +131,7 @@ const ( // MachineSkipRemediationAnnotation is the annotation used to mark the machines that should not be considered for remediation by MachineHealthCheck reconciler. MachineSkipRemediationAnnotation = "cluster.x-k8s.io/skip-remediation" - // RemediateMachineAnnotation is the annotation used to mark machines that should be remediated by MachineHealthCheck reconciler. + // RemediateMachineAnnotation request the MachineHealthCheck reconciler to mark a Machine as unhealthy. CAPI builtin remediation will prioritize Machines with the annotation to be remediated. RemediateMachineAnnotation = "cluster.x-k8s.io/remediate-machine" // MachineSetSkipPreflightChecksAnnotation is the annotation used to provide a comma-separated list of @@ -197,6 +200,16 @@ const ( // VariableDefinitionFromInline indicates a patch or variable was defined in the `.spec` of a ClusterClass // rather than from an external patch extension. VariableDefinitionFromInline = "inline" + + // CRDMigrationObservedGenerationAnnotation indicates on a CRD for which generation CRD migration is completed. + CRDMigrationObservedGenerationAnnotation = "crd-migration.cluster.x-k8s.io/observed-generation" + + // BeforeClusterUpgradeHookAnnotationPrefix annotation specifies the prefix we search each annotation + // for during the before-upgrade lifecycle hook to block propagating the new version to the control plane. + // This hook can be used to execute pre-upgrade add-on tasks and block upgrades of the ControlPlane and Workers. + // Note: While the upgrade is blocked changes made to the Cluster Topology will be delayed propagating to the underlying + // objects while the object is waiting for upgrade. + BeforeClusterUpgradeHookAnnotationPrefix = "before-upgrade.hook.cluster.cluster.x-k8s.io" ) // MachineSetPreflightCheck defines a valid MachineSet preflight check. @@ -208,10 +221,7 @@ const ( // MachineSetPreflightCheckKubeadmVersionSkew is the name of the preflight check // that verifies if the machine being created or remediated for the MachineSet conforms to the kubeadm version - // skew policy that requires the machine to be at the same version as the control plane. - // Note: This is a stopgap while the root cause of the problem is fixed in kubeadm; this check will become - // a no-op when this check will be available in kubeadm, and then eventually be dropped when all the - // supported Kuberenetes/kubeadm versions have implemented the fix. + // skew policy that requires the machine to be at the same minor version as the control plane. // The preflight check is only run if a ControlPlane is used (controlPlaneRef must exist in the Cluster), // the ControlPlane has a version, the MachineSet has a version and the MachineSet uses the Kubeadm bootstrap // provider. @@ -219,16 +229,27 @@ const ( // MachineSetPreflightCheckKubernetesVersionSkew is the name of the preflight check that verifies // if the machines being created or remediated for the MachineSet conform to the Kubernetes version skew policy - // that requires the machines to be at a version that is not more than 2 minor lower than the ControlPlane version. + // that requires the machines to be at a version that is not more than 2 (< v1.28) or 3 (>= v1.28) minor + // lower than the ControlPlane version. // The preflight check is only run if a ControlPlane is used (controlPlaneRef must exist in the Cluster), // the ControlPlane has a version and the MachineSet has a version. MachineSetPreflightCheckKubernetesVersionSkew MachineSetPreflightCheck = "KubernetesVersionSkew" // MachineSetPreflightCheckControlPlaneIsStable is the name of the preflight check // that verifies if the control plane is not provisioning and not upgrading. + // For Clusters with a managed topology it also checks if a control plane upgrade is pending. // The preflight check is only run if a ControlPlane is used (controlPlaneRef must exist in the Cluster) // and the ControlPlane has a version. MachineSetPreflightCheckControlPlaneIsStable MachineSetPreflightCheck = "ControlPlaneIsStable" + + // MachineSetPreflightCheckControlPlaneVersionSkew is the name of the preflight check + // that verifies if the machine being created or remediated for the MachineSet has exactly the same version + // as the control plane. + // The idea behind this check is that it doesn't make sense to create a Machine with an old version, if we already + // know based on the control plane version that the Machine has to be replaced soon. + // The preflight check is only run if the Cluster has a managed topology, a ControlPlane is used (controlPlaneRef + // must exist in the Cluster), the ControlPlane has a version and the MachineSet has a version. + MachineSetPreflightCheckControlPlaneVersionSkew MachineSetPreflightCheck = "ControlPlaneVersionSkew" ) // NodeOutdatedRevisionTaint can be added to Nodes at rolling updates in general triggered by updating MachineDeployment @@ -260,6 +281,7 @@ var ( ) // MachineAddressType describes a valid MachineAddress type. +// +kubebuilder:validation:Enum=Hostname;ExternalIP;InternalIP;ExternalDNS;InternalDNS type MachineAddressType string // Define the MachineAddressType constants. @@ -273,10 +295,14 @@ const ( // MachineAddress contains information for the node's address. type MachineAddress struct { - // Machine address type, one of Hostname, ExternalIP, InternalIP, ExternalDNS or InternalDNS. + // type is the machine address type, one of Hostname, ExternalIP, InternalIP, ExternalDNS or InternalDNS. + // +required Type MachineAddressType `json:"type"` - // The machine address. + // address is the machine address. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Address string `json:"address"` } @@ -305,7 +331,7 @@ type MachineAddresses []MachineAddress // In future versions, controller-tools@v2 might allow overriding the type and validation for embedded // types. When that happens, this hack should be revisited. type ObjectMeta struct { - // Map of string keys and values that can be used to organize and categorize + // labels is a map of string keys and values that can be used to organize and categorize // (scope and select) objects. May match selectors of replication controllers // and services. // More info: http://kubernetes.io/docs/user-guide/labels diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/condition_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/condition_types.go index e647f89a2d7..d9e0f44f252 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/condition_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/condition_types.go @@ -24,6 +24,7 @@ import ( // ANCHOR: ConditionSeverity // ConditionSeverity expresses the severity of a Condition Type failing. +// +kubebuilder:validation:MaxLength=32 type ConditionSeverity string const ( @@ -45,6 +46,8 @@ const ( // ANCHOR: ConditionType // ConditionType is a valid value for Condition.Type. +// +kubebuilder:validation:MinLength=1 +// +kubebuilder:validation:MaxLength=256 type ConditionType string // ANCHOR_END: ConditionType @@ -56,9 +59,11 @@ type Condition struct { // type of condition in CamelCase or in foo.example.com/CamelCase. // Many .condition.type values are consistent across resources like Available, but because arbitrary conditions // can be useful (see .node.status.conditions), the ability to deconflict is important. + // +required Type ConditionType `json:"type"` // status of the condition, one of True, False, Unknown. + // +required Status corev1.ConditionStatus `json:"status"` // severity provides an explicit classification of Reason code, so the users or machines can immediately @@ -67,20 +72,25 @@ type Condition struct { // +optional Severity ConditionSeverity `json:"severity,omitempty"` - // Last time the condition transitioned from one status to another. + // lastTransitionTime is the last time the condition transitioned from one status to another. // This should be when the underlying condition changed. If that is not known, then using the time when // the API field changed is acceptable. + // +required LastTransitionTime metav1.Time `json:"lastTransitionTime"` - // The reason for the condition's last transition in CamelCase. + // reason is the reason for the condition's last transition in CamelCase. // The specific API may choose whether or not this field is considered a guaranteed API. // This field may be empty. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Reason string `json:"reason,omitempty"` - // A human readable message indicating details about the transition. + // message is a human readable message indicating details about the transition. // This field may be empty. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 Message string `json:"message,omitempty"` } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/cluster.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/cluster.go index d61d8c36f90..417abbcb915 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/cluster.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/cluster.go @@ -29,11 +29,51 @@ import ( const ( // ClusterClassNameField is used by the Cluster controller to index Clusters by ClusterClass name. + // + // Deprecated: This constant will be removed in an upcoming release, please use ClusterClassRefPath instead. ClusterClassNameField = "spec.topology.class" + + // ClusterClassRefPath is used by the Cluster controller to index Clusters by ClusterClass name and namespace. + ClusterClassRefPath = "spec.topology.classRef" + + // clusterClassRefFmt is used to correctly format class ref index key. + clusterClassRefFmt = "%s/%s" ) +// ByClusterClassRef adds the cluster class name index to the +// managers cache. +func ByClusterClassRef(ctx context.Context, mgr ctrl.Manager) error { + if err := mgr.GetCache().IndexField(ctx, &clusterv1.Cluster{}, + ClusterClassRefPath, + ClusterByClusterClassRef, + ); err != nil { + return errors.Wrap(err, "error setting index field") + } + return nil +} + +// ClusterByClusterClassRef contains the logic to index Clusters by ClusterClass name and namespace. +func ClusterByClusterClassRef(o client.Object) []string { + cluster, ok := o.(*clusterv1.Cluster) + if !ok { + panic(fmt.Sprintf("Expected Cluster but got a %T", o)) + } + if cluster.Spec.Topology != nil { + key := cluster.GetClassKey() + return []string{fmt.Sprintf(clusterClassRefFmt, key.Namespace, key.Name)} + } + return nil +} + +// ClusterClassRef returns ClusterClass index key to be used for search. +func ClusterClassRef(cc *clusterv1.ClusterClass) string { + return fmt.Sprintf(clusterClassRefFmt, cc.GetNamespace(), cc.GetName()) +} + // ByClusterClassName adds the cluster class name index to the // managers cache. +// +// Deprecated: This func will be removed in an upcoming release, please use ByClusterClassRef instead. func ByClusterClassName(ctx context.Context, mgr ctrl.Manager) error { if err := mgr.GetCache().IndexField(ctx, &clusterv1.Cluster{}, ClusterClassNameField, @@ -45,6 +85,8 @@ func ByClusterClassName(ctx context.Context, mgr ctrl.Manager) error { } // ClusterByClusterClassClassName contains the logic to index Clusters by ClusterClass name. +// +// Deprecated: This func will be removed in an upcoming release, please use ClusterByClusterClassRef instead. func ClusterByClusterClassClassName(o client.Object) []string { cluster, ok := o.(*clusterv1.Cluster) if !ok { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/index.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/index.go index c6a17bf175b..818e1283dab 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/index.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/index/index.go @@ -36,7 +36,7 @@ func AddDefaultIndexes(ctx context.Context, mgr ctrl.Manager) error { } if feature.Gates.Enabled(feature.ClusterTopology) { - if err := ByClusterClassName(ctx, mgr); err != nil { + if err := ByClusterClassRef(ctx, mgr); err != nil { return err } } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machine_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machine_types.go index fccc584fe5a..504bc807d85 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machine_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machine_types.go @@ -84,6 +84,9 @@ const ( NodeRestrictionLabelDomain = "node-restriction.kubernetes.io" // ManagedNodeLabelDomain is one of the CAPI managed Node label domains. ManagedNodeLabelDomain = "node.cluster.x-k8s.io" + + // ManagedNodeAnnotationDomain is one of the CAPI managed Node annotation domains. + ManagedNodeAnnotationDomain = "node.cluster.x-k8s.io" ) // Machine's Available condition and corresponding reasons that will be used in v1Beta2 API version. @@ -377,20 +380,26 @@ const ( // MachineSpec defines the desired state of Machine. type MachineSpec struct { // clusterName is the name of the Cluster this object belongs to. + // +required // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName"` // bootstrap is a reference to a local struct which encapsulates // fields to configure the Machine’s bootstrapping mechanism. + // +required Bootstrap Bootstrap `json:"bootstrap"` // infrastructureRef is a required reference to a custom resource // offered by an infrastructure provider. + // +required InfrastructureRef corev1.ObjectReference `json:"infrastructureRef"` // version defines the desired Kubernetes version. // This field is meant to be optionally used by bootstrap providers. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Version *string `json:"version,omitempty"` // providerID is the identification ID of the machine provided by the provider. @@ -404,11 +413,15 @@ type MachineSpec struct { // This field will be set by the actuators and consumed by higher level entities like autoscaler that will // be interfacing with cluster-api as generic provider. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 ProviderID *string `json:"providerID,omitempty"` // failureDomain is the failure domain the machine will be created in. // Must match a key in the FailureDomains map stored on the cluster object. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 FailureDomain *string `json:"failureDomain,omitempty"` // The minimum number of seconds for which a Machine should be ready before considering it available. @@ -459,14 +472,23 @@ type MachineSpec struct { // MachineReadinessGate contains the type of a Machine condition to be used as a readiness gate. type MachineReadinessGate struct { - // conditionType refers to a positive polarity condition (status true means good) with matching type in the Machine's condition list. + // conditionType refers to a condition with matching type in the Machine's condition list. // If the conditions doesn't exist, it will be treated as unknown. // Note: Both Cluster API conditions or conditions added by 3rd party controllers can be used as readiness gates. // +required // +kubebuilder:validation:Pattern=`^([a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*/)?(([A-Za-z0-9][-A-Za-z0-9_.]*)?[A-Za-z0-9])$` - // +kubebuilder:validation:MaxLength=316 // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=316 ConditionType string `json:"conditionType"` + + // polarity of the conditionType specified in this readinessGate. + // Valid values are Positive, Negative and omitted. + // When omitted, the default behaviour will be Positive. + // A positive polarity means that the condition should report a true status under normal conditions. + // A negative polarity means that the condition should report a false status under normal conditions. + // +kubebuilder:validation:Enum=Positive;Negative + // +optional + Polarity ConditionPolarity `json:"polarity,omitempty"` } // ANCHOR_END: MachineSpec @@ -530,6 +552,8 @@ type MachineStatus struct { // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 FailureMessage *string `json:"failureMessage,omitempty"` // addresses is a list of addresses assigned to the machine. @@ -538,8 +562,8 @@ type MachineStatus struct { Addresses MachineAddresses `json:"addresses,omitempty"` // phase represents the current phase of machine actuation. - // E.g. Pending, Running, Terminating, Failed etc. // +optional + // +kubebuilder:validation:Enum=Pending;Provisioning;Provisioned;Running;Deleting;Deleted;Failed;Unknown Phase string `json:"phase,omitempty"` // certificatesExpiryDate is the expiry date of the machine certificates. @@ -645,6 +669,8 @@ type Bootstrap struct { // dataSecretName is the name of the secret that stores the bootstrap data script. // If nil, the Machine should remain in the Pending state. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 DataSecretName *string `json:"dataSecretName,omitempty"` } @@ -663,10 +689,17 @@ type Bootstrap struct { // Machine is the Schema for the machines API. type Machine struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec MachineSpec `json:"spec,omitempty"` + // spec is the desired state of Machine. + // +optional + Spec MachineSpec `json:"spec,omitempty"` + // status is the observed state of Machine. + // +optional Status MachineStatus `json:"status,omitempty"` } @@ -701,8 +734,12 @@ func (m *Machine) SetV1Beta2Conditions(conditions []metav1.Condition) { // MachineList contains a list of Machine. type MachineList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []Machine `json:"items"` + // items is the list of Machines. + Items []Machine `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedeployment_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedeployment_types.go index 2828550efd6..80307605d5a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedeployment_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedeployment_types.go @@ -241,10 +241,12 @@ const ( // MachineDeploymentSpec defines the desired state of MachineDeployment. type MachineDeploymentSpec struct { // clusterName is the name of the Cluster this object belongs to. + // +required // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName"` - // Number of desired machines. + // replicas is the number of desired machines. // This is a pointer to distinguish between explicit zero and not specified. // // Defaults to: @@ -273,25 +275,32 @@ type MachineDeploymentSpec struct { // +optional RolloutAfter *metav1.Time `json:"rolloutAfter,omitempty"` - // Label selector for machines. Existing MachineSets whose machines are + // selector is the label selector for machines. Existing MachineSets whose machines are // selected by this will be the ones affected by this deployment. // It must match the machine template's labels. + // +required Selector metav1.LabelSelector `json:"selector"` // template describes the machines that will be created. + // +required Template MachineTemplateSpec `json:"template"` - // The deployment strategy to use to replace existing machines with + // strategy is the deployment strategy to use to replace existing machines with // new ones. // +optional Strategy *MachineDeploymentStrategy `json:"strategy,omitempty"` + // machineNamingStrategy allows changing the naming pattern used when creating Machines. + // Note: InfraMachines & BootstrapConfigs will use the same name as the corresponding Machines. + // +optional + MachineNamingStrategy *MachineNamingStrategy `json:"machineNamingStrategy,omitempty"` + // minReadySeconds is the minimum number of seconds for which a Node for a newly created machine should be ready before considering the replica available. // Defaults to 0 (machine will be considered available as soon as the Node is ready) // +optional MinReadySeconds *int32 `json:"minReadySeconds,omitempty"` - // The number of old MachineSets to retain to allow rollback. + // revisionHistoryLimit is the number of old MachineSets to retain to allow rollback. // This is a pointer to distinguish between explicit zero and not specified. // Defaults to 1. // @@ -300,11 +309,11 @@ type MachineDeploymentSpec struct { // +optional RevisionHistoryLimit *int32 `json:"revisionHistoryLimit,omitempty"` - // Indicates that the deployment is paused. + // paused indicates that the deployment is paused. // +optional Paused bool `json:"paused,omitempty"` - // The maximum time in seconds for a deployment to make progress before it + // progressDeadlineSeconds is the maximum time in seconds for a deployment to make progress before it // is considered to be failed. The deployment controller will continue to // process failed deployments and a condition with a ProgressDeadlineExceeded // reason will be surfaced in the deployment status. Note that progress will @@ -329,7 +338,7 @@ type MachineDeploymentStrategy struct { // +optional Type MachineDeploymentStrategyType `json:"type,omitempty"` - // Rolling update config params. Present only if + // rollingUpdate is the rolling update config params. Present only if // MachineDeploymentStrategyType = RollingUpdate. // +optional RollingUpdate *MachineRollingUpdateDeployment `json:"rollingUpdate,omitempty"` @@ -346,7 +355,7 @@ type MachineDeploymentStrategy struct { // MachineRollingUpdateDeployment is used to control the desired behavior of rolling update. type MachineRollingUpdateDeployment struct { - // The maximum number of machines that can be unavailable during the update. + // maxUnavailable is the maximum number of machines that can be unavailable during the update. // Value can be an absolute number (ex: 5) or a percentage of desired // machines (ex: 10%). // Absolute number is calculated from percentage by rounding down. @@ -361,7 +370,7 @@ type MachineRollingUpdateDeployment struct { // +optional MaxUnavailable *intstr.IntOrString `json:"maxUnavailable,omitempty"` - // The maximum number of machines that can be scheduled above the + // maxSurge is the maximum number of machines that can be scheduled above the // desired number of machines. // Value can be an absolute number (ex: 5) or a percentage of // desired machines (ex: 10%). @@ -412,11 +421,37 @@ type RemediationStrategy struct { // ANCHOR_END: RemediationStrategy +// MachineNamingStrategy allows changing the naming pattern used when creating +// Machines. +// Note: InfraMachines & BootstrapConfigs will use the same name as the corresponding Machines. +type MachineNamingStrategy struct { + // template defines the template to use for generating the names of the + // Machine objects. + // If not defined, it will fallback to `{{ .machineSet.name }}-{{ .random }}`. + // If the generated name string exceeds 63 characters, it will be trimmed to + // 58 characters and will + // get concatenated with a random suffix of length 5. + // Length of the template string must not exceed 256 characters. + // The template allows the following variables `.cluster.name`, + // `.machineSet.name` and `.random`. + // The variable `.cluster.name` retrieves the name of the cluster object + // that owns the Machines being created. + // The variable `.machineSet.name` retrieves the name of the MachineSet + // object that owns the Machines being created. + // The variable `.random` is substituted with random alphanumeric string, + // without vowels, of length 5. This variable is required part of the + // template. If not provided, validation will fail. + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 + Template string `json:"template,omitempty"` +} + // ANCHOR: MachineDeploymentStatus // MachineDeploymentStatus defines the observed state of MachineDeployment. type MachineDeploymentStatus struct { - // The generation observed by the deployment controller. + // observedGeneration is the generation observed by the deployment controller. // +optional ObservedGeneration int64 `json:"observedGeneration,omitempty"` @@ -424,28 +459,30 @@ type MachineDeploymentStatus struct { // by clients. The string will be in the same format as the query-param syntax. // More info about label selectors: http://kubernetes.io/docs/user-guide/labels#label-selectors // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=4096 Selector string `json:"selector,omitempty"` - // Total number of non-terminated machines targeted by this deployment + // replicas is the total number of non-terminated machines targeted by this deployment // (their labels match the selector). // +optional Replicas int32 `json:"replicas"` - // Total number of non-terminated machines targeted by this deployment + // updatedReplicas is the total number of non-terminated machines targeted by this deployment // that have the desired template spec. // +optional UpdatedReplicas int32 `json:"updatedReplicas"` - // Total number of ready machines targeted by this deployment. + // readyReplicas is the total number of ready machines targeted by this deployment. // +optional ReadyReplicas int32 `json:"readyReplicas"` - // Total number of available machines (ready for at least minReadySeconds) + // availableReplicas is the total number of available machines (ready for at least minReadySeconds) // targeted by this deployment. // +optional AvailableReplicas int32 `json:"availableReplicas"` - // Total number of unavailable machines targeted by this deployment. + // unavailableReplicas is the total number of unavailable machines targeted by this deployment. // This is the total number of machines that are still required for // the deployment to have 100% available capacity. They may either // be machines that are running but not yet available or machines @@ -458,6 +495,7 @@ type MachineDeploymentStatus struct { // phase represents the current phase of a MachineDeployment (ScalingUp, ScalingDown, Running, Failed, or Unknown). // +optional + // +kubebuilder:validation:Enum=ScalingUp;ScalingDown;Running;Failed;Unknown Phase string `json:"phase,omitempty"` // conditions defines current service state of the MachineDeployment. @@ -552,10 +590,17 @@ func (md *MachineDeploymentStatus) GetTypedPhase() MachineDeploymentPhase { // MachineDeployment is the Schema for the machinedeployments API. type MachineDeployment struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec MachineDeploymentSpec `json:"spec,omitempty"` + // spec is the desired state of MachineDeployment. + // +optional + Spec MachineDeploymentSpec `json:"spec,omitempty"` + // status is the observed state of MachineDeployment. + // +optional Status MachineDeploymentStatus `json:"status,omitempty"` } @@ -564,8 +609,12 @@ type MachineDeployment struct { // MachineDeploymentList contains a list of MachineDeployment. type MachineDeploymentList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []MachineDeployment `json:"items"` + // items is the list of MachineDeployments. + Items []MachineDeployment `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedrainrules_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedrainrules_types.go index b5e0916b663..ac9aeb415e0 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedrainrules_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinedrainrules_types.go @@ -22,13 +22,13 @@ import ( const ( // PodDrainLabel is the label that can be set on Pods in workload clusters to ensure a Pod is not drained. - // The only valid value is "skip". + // The only valid values are "skip" and "wait-completed". // This label takes precedence over MachineDrainRules defined in the management cluster. PodDrainLabel = "cluster.x-k8s.io/drain" ) -// MachineDrainRuleDrainBehavior defines the drain behavior. Can be either "Drain" or "Skip". -// +kubebuilder:validation:Enum=Drain;Skip +// MachineDrainRuleDrainBehavior defines the drain behavior. Can be either "Drain", "Skip", or "WaitCompleted". +// +kubebuilder:validation:Enum=Drain;Skip;WaitCompleted type MachineDrainRuleDrainBehavior string const ( @@ -37,6 +37,10 @@ const ( // MachineDrainRuleDrainBehaviorSkip means the drain for a Pod should be skipped. MachineDrainRuleDrainBehaviorSkip MachineDrainRuleDrainBehavior = "Skip" + + // MachineDrainRuleDrainBehaviorWaitCompleted means the Pod should not be evicted, + // but overall drain should wait until the Pod completes. + MachineDrainRuleDrainBehaviorWaitCompleted MachineDrainRuleDrainBehavior = "WaitCompleted" ) // MachineDrainRuleSpec defines the spec of a MachineDrainRule. @@ -75,6 +79,7 @@ type MachineDrainRuleSpec struct { // +listType=atomic // +kubebuilder:validation:MinItems=1 // +kubebuilder:validation:MaxItems=32 + // +kubebuilder:validation:XValidation:rule="self.all(x, self.exists_one(y, x == y))",message="entries in machines must be unique" Machines []MachineDrainRuleMachineSelector `json:"machines,omitempty"` // pods defines to which Pods this MachineDrainRule should be applied. @@ -106,13 +111,14 @@ type MachineDrainRuleSpec struct { // +listType=atomic // +kubebuilder:validation:MinItems=1 // +kubebuilder:validation:MaxItems=32 + // +kubebuilder:validation:XValidation:rule="self.all(x, self.exists_one(y, x == y))",message="entries in pods must be unique" Pods []MachineDrainRulePodSelector `json:"pods,omitempty"` } // MachineDrainRuleDrainConfig configures if and how Pods are drained. type MachineDrainRuleDrainConfig struct { // behavior defines the drain behavior. - // Can be either "Drain" or "Skip". + // Can be either "Drain", "Skip", or "WaitCompleted". // "Drain" means that the Pods to which this MachineDrainRule applies will be drained. // If behavior is set to "Drain" the order in which Pods are drained can be configured // with the order field. When draining Pods of a Node the Pods will be grouped by order @@ -120,6 +126,8 @@ type MachineDrainRuleDrainConfig struct { // wait until all Pods of a group are terminated / removed from the Node before starting // with the next group. // "Skip" means that the Pods to which this MachineDrainRule applies will be skipped during drain. + // "WaitCompleted" means that the pods to which this MachineDrainRule applies will never be evicted + // and we wait for them to be completed, it is enforced that pods marked with this behavior always have Order=0. // +required Behavior MachineDrainRuleDrainBehavior `json:"behavior"` @@ -197,6 +205,8 @@ type MachineDrainRulePodSelector struct { type MachineDrainRule struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata // +required metav1.ObjectMeta `json:"metadata"` @@ -211,11 +221,12 @@ type MachineDrainRule struct { type MachineDrainRuleList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds // +required metav1.ListMeta `json:"metadata"` // items contains the items of the MachineDrainRuleList. - // +required Items []MachineDrainRule `json:"items"` } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinehealthcheck_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinehealthcheck_types.go index 42c4817f0f1..0646bad1169 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinehealthcheck_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machinehealthcheck_types.go @@ -52,10 +52,13 @@ var ( // MachineHealthCheckSpec defines the desired state of MachineHealthCheck. type MachineHealthCheckSpec struct { // clusterName is the name of the Cluster this object belongs to. + // +required // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName"` - // Label selector to match machines whose health will be exercised + // selector is a label selector to match machines whose health will be exercised + // +required Selector metav1.LabelSelector `json:"selector"` // unhealthyConditions contains a list of the conditions that determine @@ -63,9 +66,11 @@ type MachineHealthCheckSpec struct { // logical OR, i.e. if any of the conditions is met, the node is unhealthy. // // +optional + // +kubebuilder:validation:MaxItems=100 UnhealthyConditions []UnhealthyCondition `json:"unhealthyConditions,omitempty"` - // Any further remediation is only allowed if at most "MaxUnhealthy" machines selected by + // maxUnhealthy specifies the maximum number of unhealthy machines allowed. + // Any further remediation is only allowed if at most "maxUnhealthy" machines selected by // "selector" are not healthy. // // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10722 for more details. @@ -73,8 +78,9 @@ type MachineHealthCheckSpec struct { // +optional MaxUnhealthy *intstr.IntOrString `json:"maxUnhealthy,omitempty"` + // unhealthyRange specifies the range of unhealthy machines allowed. // Any further remediation is only allowed if the number of machines selected by "selector" as not healthy - // is within the range of "UnhealthyRange". Takes precedence over MaxUnhealthy. + // is within the range of "unhealthyRange". Takes precedence over maxUnhealthy. // Eg. "[3-5]" - This means that remediation will be allowed only when: // (a) there are at least 3 unhealthy machines (and) // (b) there are at most 5 unhealthy machines @@ -83,6 +89,8 @@ type MachineHealthCheckSpec struct { // // +optional // +kubebuilder:validation:Pattern=^\[[0-9]+-[0-9]+\]$ + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=32 UnhealthyRange *string `json:"unhealthyRange,omitempty"` // nodeStartupTimeout allows to set the maximum time for MachineHealthCheck @@ -118,14 +126,23 @@ type MachineHealthCheckSpec struct { // specified as a duration. When the named condition has been in the given // status for at least the timeout value, a node is considered unhealthy. type UnhealthyCondition struct { + // type of Node condition // +kubebuilder:validation:Type=string // +kubebuilder:validation:MinLength=1 + // +required Type corev1.NodeConditionType `json:"type"` + // status of the condition, one of True, False, Unknown. // +kubebuilder:validation:Type=string // +kubebuilder:validation:MinLength=1 + // +required Status corev1.ConditionStatus `json:"status"` + // timeout is the duration that a node must be in a given status for, + // after which the node is considered unhealthy. + // For example, with a value of "1h", the node must match the status + // for at least 1 hour before being considered unhealthy. + // +required Timeout metav1.Duration `json:"timeout"` } @@ -135,12 +152,12 @@ type UnhealthyCondition struct { // MachineHealthCheckStatus defines the observed state of MachineHealthCheck. type MachineHealthCheckStatus struct { - // total number of machines counted by this machine health check + // expectedMachines is the total number of machines counted by this machine health check // +kubebuilder:validation:Minimum=0 // +optional ExpectedMachines int32 `json:"expectedMachines"` - // total number of healthy machines counted by this machine health check + // currentHealthy is the total number of healthy machines counted by this machine health check // +kubebuilder:validation:Minimum=0 // +optional CurrentHealthy int32 `json:"currentHealthy"` @@ -157,6 +174,9 @@ type MachineHealthCheckStatus struct { // targets shows the current list of machines the machine health check is watching // +optional + // +kubebuilder:validation:MaxItems=10000 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=253 Targets []string `json:"targets,omitempty"` // conditions defines current service state of the MachineHealthCheck. @@ -194,13 +214,18 @@ type MachineHealthCheckV1Beta2Status struct { // MachineHealthCheck is the Schema for the machinehealthchecks API. type MachineHealthCheck struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - // Specification of machine health check policy + // spec is the specification of machine health check policy + // +optional Spec MachineHealthCheckSpec `json:"spec,omitempty"` - // Most recently observed status of MachineHealthCheck resource + // status is the most recently observed status of MachineHealthCheck resource + // +optional Status MachineHealthCheckStatus `json:"status,omitempty"` } @@ -235,8 +260,12 @@ func (m *MachineHealthCheck) SetV1Beta2Conditions(conditions []metav1.Condition) // MachineHealthCheckList contains a list of MachineHealthCheck. type MachineHealthCheckList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []MachineHealthCheck `json:"items"` + // items is the list of MachineHealthChecks. + Items []MachineHealthCheck `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machineset_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machineset_types.go index 1abbd906cd4..cf52f70a168 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machineset_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/machineset_types.go @@ -40,7 +40,9 @@ const ( // MachineSetSpec defines the desired state of MachineSet. type MachineSetSpec struct { // clusterName is the name of the Cluster this object belongs to. + // +required // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName"` // replicas is the number of desired replicas. @@ -78,6 +80,7 @@ type MachineSetSpec struct { // Label keys and values that must match in order to be controlled by this MachineSet. // It must match the machine template's labels. // More info: https://kubernetes.io/docs/concepts/overview/working-with-objects/labels/#label-selectors + // +required Selector metav1.LabelSelector `json:"selector"` // template is the object that describes the machine that will be created if @@ -85,6 +88,11 @@ type MachineSetSpec struct { // Object references to custom resources are treated as templates. // +optional Template MachineTemplateSpec `json:"template,omitempty"` + + // machineNamingStrategy allows changing the naming pattern used when creating Machines. + // Note: InfraMachines & BootstrapConfigs will use the same name as the corresponding Machines. + // +optional + MachineNamingStrategy *MachineNamingStrategy `json:"machineNamingStrategy,omitempty"` } // MachineSet's ScalingUp condition and corresponding reasons that will be used in v1Beta2 API version. @@ -231,12 +239,12 @@ const ( // MachineTemplateSpec describes the data needed to create a Machine from a template. type MachineTemplateSpec struct { - // Standard object's metadata. + // metadata is the standard object's metadata. // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata // +optional ObjectMeta `json:"metadata,omitempty"` - // Specification of the desired behavior of the machine. + // spec is the specification of the desired behavior of the machine. // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#spec-and-status // +optional Spec MachineSpec `json:"spec,omitempty"` @@ -279,24 +287,26 @@ type MachineSetStatus struct { // by clients. The string will be in the same format as the query-param syntax. // More info about label selectors: http://kubernetes.io/docs/user-guide/labels#label-selectors // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=4096 Selector string `json:"selector,omitempty"` // replicas is the most recently observed number of replicas. // +optional Replicas int32 `json:"replicas"` - // The number of replicas that have labels matching the labels of the machine template of the MachineSet. + // fullyLabeledReplicas is the number of replicas that have labels matching the labels of the machine template of the MachineSet. // // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional FullyLabeledReplicas int32 `json:"fullyLabeledReplicas"` - // The number of ready replicas for this MachineSet. A machine is considered ready when the node has been created and is "Ready". + // readyReplicas is the number of ready replicas for this MachineSet. A machine is considered ready when the node has been created and is "Ready". // +optional ReadyReplicas int32 `json:"readyReplicas"` - // The number of available replicas (ready for at least minReadySeconds) for this MachineSet. + // availableReplicas is the number of available replicas (ready for at least minReadySeconds) for this MachineSet. // +optional AvailableReplicas int32 `json:"availableReplicas"` @@ -304,6 +314,10 @@ type MachineSetStatus struct { // +optional ObservedGeneration int64 `json:"observedGeneration,omitempty"` + // failureReason will be set in the event that there is a terminal problem + // reconciling the Machine and will contain a succinct value suitable + // for machine interpretation. + // // In the event that there is a terminal problem reconciling the // replicas, both FailureReason and FailureMessage will be set. FailureReason // will be populated with a succinct value suitable for machine @@ -327,10 +341,18 @@ type MachineSetStatus struct { // // +optional FailureReason *capierrors.MachineSetStatusError `json:"failureReason,omitempty"` + + // failureMessage will be set in the event that there is a terminal problem + // reconciling the Machine and will contain a more verbose string suitable + // for logging and human consumption. + // // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 FailureMessage *string `json:"failureMessage,omitempty"` + // conditions defines current service state of the MachineSet. // +optional Conditions Conditions `json:"conditions,omitempty"` @@ -404,10 +426,17 @@ func (m *MachineSet) Validate() field.ErrorList { // MachineSet is the Schema for the machinesets API. type MachineSet struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec MachineSetSpec `json:"spec,omitempty"` + // spec is the desired state of MachineSet. + // +optional + Spec MachineSetSpec `json:"spec,omitempty"` + // status is the observed state of MachineSet. + // +optional Status MachineSetStatus `json:"status,omitempty"` } @@ -442,8 +471,12 @@ func (m *MachineSet) SetV1Beta2Conditions(conditions []metav1.Condition) { // MachineSetList contains a list of MachineSet. type MachineSetList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []MachineSet `json:"items"` + // items is the list of MachineSets. + Items []MachineSet `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/v1beta2_condition_consts.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/v1beta2_condition_consts.go index b9e36987a8a..c00c0fc4cd6 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/v1beta2_condition_consts.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/v1beta2_condition_consts.go @@ -157,10 +157,6 @@ const ( // (e.g. its status is missing). InvalidConditionReportedV1Beta2Reason = "InvalidConditionReported" - // NoReasonReportedV1Beta2Reason applies to a condition, usually read from an external object, that reports no reason. - // Note: this could happen e.g. when an external object still uses Cluster API v1beta1 Conditions. - NoReasonReportedV1Beta2Reason = "NoReasonReported" - // InternalErrorV1Beta2Reason surfaces unexpected errors reporting by controllers. // In most cases, it will be required to look at controllers logs to properly triage those issues. InternalErrorV1Beta2Reason = "InternalError" @@ -198,4 +194,22 @@ const ( // InspectionFailedV1Beta2Reason applies to a condition when inspection of the underlying object failed. InspectionFailedV1Beta2Reason = "InspectionFailed" + + // WaitingForClusterInfrastructureReadyV1Beta2Reason documents an infra Machine waiting for the cluster + // infrastructure to be ready. + WaitingForClusterInfrastructureReadyV1Beta2Reason = "WaitingForClusterInfrastructureReady" + + // WaitingForControlPlaneInitializedV1Beta2Reason documents an infra Machine waiting + // for the control plane to be initialized. + WaitingForControlPlaneInitializedV1Beta2Reason = "WaitingForControlPlaneInitialized" + + // WaitingForBootstrapDataV1Beta2Reason documents an infra Machine waiting for the bootstrap + // data to be ready before starting to create the Machine's infrastructure. + WaitingForBootstrapDataV1Beta2Reason = "WaitingForBootstrapData" + + // ProvisionedV1Beta2Reason documents an object or a piece of infrastructure being provisioned. + ProvisionedV1Beta2Reason = "Provisioned" + + // NotProvisionedV1Beta2Reason documents an object or a piece of infrastructure is not provisioned. + NotProvisionedV1Beta2Reason = "NotProvisioned" ) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.deepcopy.go index 2f1db80c468..ec25c1dfb00 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.deepcopy.go @@ -205,7 +205,17 @@ func (in *ClusterClassPatch) DeepCopy() *ClusterClassPatch { // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ClusterClassSpec) DeepCopyInto(out *ClusterClassSpec) { *out = *in + if in.AvailabilityGates != nil { + in, out := &in.AvailabilityGates, &out.AvailabilityGates + *out = make([]ClusterAvailabilityGate, len(*in)) + copy(*out, *in) + } in.Infrastructure.DeepCopyInto(&out.Infrastructure) + if in.InfrastructureNamingStrategy != nil { + in, out := &in.InfrastructureNamingStrategy, &out.InfrastructureNamingStrategy + *out = new(InfrastructureNamingStrategy) + (*in).DeepCopyInto(*out) + } in.ControlPlane.DeepCopyInto(&out.ControlPlane) in.Workers.DeepCopyInto(&out.Workers) if in.Variables != nil { @@ -682,6 +692,11 @@ func (in *ControlPlaneClass) DeepCopyInto(out *ControlPlaneClass) { *out = new(metav1.Duration) **out = **in } + if in.ReadinessGates != nil { + in, out := &in.ReadinessGates, &out.ReadinessGates + *out = make([]MachineReadinessGate, len(*in)) + copy(*out, *in) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ControlPlaneClass. @@ -743,6 +758,11 @@ func (in *ControlPlaneTopology) DeepCopyInto(out *ControlPlaneTopology) { *out = new(metav1.Duration) **out = **in } + if in.ReadinessGates != nil { + in, out := &in.ReadinessGates, &out.ReadinessGates + *out = make([]MachineReadinessGate, len(*in)) + copy(*out, *in) + } if in.Variables != nil { in, out := &in.Variables, &out.Variables *out = new(ControlPlaneVariables) @@ -862,6 +882,26 @@ func (in FailureDomains) DeepCopy() FailureDomains { return *out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *InfrastructureNamingStrategy) DeepCopyInto(out *InfrastructureNamingStrategy) { + *out = *in + if in.Template != nil { + in, out := &in.Template, &out.Template + *out = new(string) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new InfrastructureNamingStrategy. +func (in *InfrastructureNamingStrategy) DeepCopy() *InfrastructureNamingStrategy { + if in == nil { + return nil + } + out := new(InfrastructureNamingStrategy) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *JSONPatch) DeepCopyInto(out *JSONPatch) { *out = *in @@ -1212,6 +1252,11 @@ func (in *MachineDeploymentClass) DeepCopyInto(out *MachineDeploymentClass) { *out = new(int32) **out = **in } + if in.ReadinessGates != nil { + in, out := &in.ReadinessGates, &out.ReadinessGates + *out = make([]MachineReadinessGate, len(*in)) + copy(*out, *in) + } if in.Strategy != nil { in, out := &in.Strategy, &out.Strategy *out = new(MachineDeploymentStrategy) @@ -1318,6 +1363,11 @@ func (in *MachineDeploymentSpec) DeepCopyInto(out *MachineDeploymentSpec) { *out = new(MachineDeploymentStrategy) (*in).DeepCopyInto(*out) } + if in.MachineNamingStrategy != nil { + in, out := &in.MachineNamingStrategy, &out.MachineNamingStrategy + *out = new(MachineNamingStrategy) + **out = **in + } if in.MinReadySeconds != nil { in, out := &in.MinReadySeconds, &out.MinReadySeconds *out = new(int32) @@ -1436,6 +1486,11 @@ func (in *MachineDeploymentTopology) DeepCopyInto(out *MachineDeploymentTopology *out = new(int32) **out = **in } + if in.ReadinessGates != nil { + in, out := &in.ReadinessGates, &out.ReadinessGates + *out = make([]MachineReadinessGate, len(*in)) + copy(*out, *in) + } if in.Strategy != nil { in, out := &in.Strategy, &out.Strategy *out = new(MachineDeploymentStrategy) @@ -1922,6 +1977,21 @@ func (in *MachineList) DeepCopyObject() runtime.Object { return nil } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *MachineNamingStrategy) DeepCopyInto(out *MachineNamingStrategy) { + *out = *in +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new MachineNamingStrategy. +func (in *MachineNamingStrategy) DeepCopy() *MachineNamingStrategy { + if in == nil { + return nil + } + out := new(MachineNamingStrategy) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *MachinePoolClass) DeepCopyInto(out *MachinePoolClass) { *out = *in @@ -2193,6 +2263,11 @@ func (in *MachineSetSpec) DeepCopyInto(out *MachineSetSpec) { } in.Selector.DeepCopyInto(&out.Selector) in.Template.DeepCopyInto(&out.Template) + if in.MachineNamingStrategy != nil { + in, out := &in.MachineNamingStrategy, &out.MachineNamingStrategy + *out = new(MachineNamingStrategy) + **out = **in + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new MachineSetSpec. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.openapi.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.openapi.go index 3167c70da4e..7793d65eb87 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.openapi.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/api/v1beta1/zz_generated.openapi.go @@ -56,6 +56,7 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneVariables": schema_sigsk8sio_cluster_api_api_v1beta1_ControlPlaneVariables(ref), "sigs.k8s.io/cluster-api/api/v1beta1.ExternalPatchDefinition": schema_sigsk8sio_cluster_api_api_v1beta1_ExternalPatchDefinition(ref), "sigs.k8s.io/cluster-api/api/v1beta1.FailureDomainSpec": schema_sigsk8sio_cluster_api_api_v1beta1_FailureDomainSpec(ref), + "sigs.k8s.io/cluster-api/api/v1beta1.InfrastructureNamingStrategy": schema_sigsk8sio_cluster_api_api_v1beta1_InfrastructureNamingStrategy(ref), "sigs.k8s.io/cluster-api/api/v1beta1.JSONPatch": schema_sigsk8sio_cluster_api_api_v1beta1_JSONPatch(ref), "sigs.k8s.io/cluster-api/api/v1beta1.JSONPatchValue": schema_sigsk8sio_cluster_api_api_v1beta1_JSONPatchValue(ref), "sigs.k8s.io/cluster-api/api/v1beta1.JSONSchemaProps": schema_sigsk8sio_cluster_api_api_v1beta1_JSONSchemaProps(ref), @@ -88,6 +89,7 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckTopology": schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckTopology(ref), "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckV1Beta2Status": schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckV1Beta2Status(ref), "sigs.k8s.io/cluster-api/api/v1beta1.MachineList": schema_sigsk8sio_cluster_api_api_v1beta1_MachineList(ref), + "sigs.k8s.io/cluster-api/api/v1beta1.MachineNamingStrategy": schema_sigsk8sio_cluster_api_api_v1beta1_MachineNamingStrategy(ref), "sigs.k8s.io/cluster-api/api/v1beta1.MachinePoolClass": schema_sigsk8sio_cluster_api_api_v1beta1_MachinePoolClass(ref), "sigs.k8s.io/cluster-api/api/v1beta1.MachinePoolClassNamingStrategy": schema_sigsk8sio_cluster_api_api_v1beta1_MachinePoolClassNamingStrategy(ref), "sigs.k8s.io/cluster-api/api/v1beta1.MachinePoolClassTemplate": schema_sigsk8sio_cluster_api_api_v1beta1_MachinePoolClassTemplate(ref), @@ -132,7 +134,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_APIEndpoint(ref common.ReferenceCa Properties: map[string]spec.Schema{ "host": { SchemaProps: spec.SchemaProps{ - Description: "The hostname on which the API server is serving.", + Description: "host is the hostname on which the API server is serving.", Default: "", Type: []string{"string"}, Format: "", @@ -140,7 +142,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_APIEndpoint(ref common.ReferenceCa }, "port": { SchemaProps: spec.SchemaProps{ - Description: "The port on which the API server is serving.", + Description: "port is the port on which the API server is serving.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -204,20 +206,23 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_Cluster(ref common.ReferenceCallba }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterSpec"), + Description: "spec is the desired state of Cluster.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterSpec"), }, }, "status": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterStatus"), + Description: "status is the observed state of Cluster.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterStatus"), }, }, }, @@ -237,12 +242,19 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterAvailabilityGate(ref common Properties: map[string]spec.Schema{ "conditionType": { SchemaProps: spec.SchemaProps{ - Description: "conditionType refers to a positive polarity condition (status true means good) with matching type in the Cluster's condition list. If the conditions doesn't exist, it will be treated as unknown. Note: Both Cluster API conditions or conditions added by 3rd party controllers can be used as availability gates.", + Description: "conditionType refers to a condition with matching type in the Cluster's condition list. If the conditions doesn't exist, it will be treated as unknown. Note: Both Cluster API conditions or conditions added by 3rd party controllers can be used as availability gates.", Default: "", Type: []string{"string"}, Format: "", }, }, + "polarity": { + SchemaProps: spec.SchemaProps{ + Description: "polarity of the conditionType specified in this availabilityGate. Valid values are Positive, Negative and omitted. When omitted, the default behaviour will be Positive. A positive polarity means that the condition should report a true status under normal conditions. A negative polarity means that the condition should report a false status under normal conditions.", + Type: []string{"string"}, + Format: "", + }, + }, }, Required: []string{"conditionType"}, }, @@ -273,20 +285,23 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterClass(ref common.ReferenceC }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassSpec"), + Description: "spec is the desired state of ClusterClass.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassSpec"), }, }, "status": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassStatus"), + Description: "status is the observed state of ClusterClass.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassStatus"), }, }, }, @@ -320,13 +335,15 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterClassList(ref common.Refere }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "items is the list of ClusterClasses.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -411,6 +428,28 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterClassSpec(ref common.Refere Description: "ClusterClassSpec describes the desired state of the ClusterClass.", Type: []string{"object"}, Properties: map[string]spec.Schema{ + "availabilityGates": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-map-keys": []interface{}{ + "conditionType", + }, + "x-kubernetes-list-type": "map", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "availabilityGates specifies additional conditions to include when evaluating Cluster Available condition.\n\nNOTE: this field is considered only for computing v1beta2 conditions. NOTE: If a Cluster is using this ClusterClass, and this Cluster defines a custom list of availabilityGates, such list overrides availabilityGates defined in this field.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterAvailabilityGate"), + }, + }, + }, + }, + }, "infrastructure": { SchemaProps: spec.SchemaProps{ Description: "infrastructure is a reference to a provider-specific template that holds the details for provisioning infrastructure specific cluster for the underlying provider. The underlying provider is responsible for the implementation of the template to an infrastructure cluster.", @@ -418,6 +457,12 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterClassSpec(ref common.Refere Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.LocalObjectTemplate"), }, }, + "infrastructureNamingStrategy": { + SchemaProps: spec.SchemaProps{ + Description: "infrastructureNamingStrategy allows changing the naming pattern used when creating the infrastructure object.", + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.InfrastructureNamingStrategy"), + }, + }, "controlPlane": { SchemaProps: spec.SchemaProps{ Description: "controlPlane is a reference to a local struct that holds the details for provisioning the Control Plane for the Cluster.", @@ -464,7 +509,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterClassSpec(ref common.Refere }, }, Dependencies: []string{ - "sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassPatch", "sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassVariable", "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneClass", "sigs.k8s.io/cluster-api/api/v1beta1.LocalObjectTemplate", "sigs.k8s.io/cluster-api/api/v1beta1.WorkersClass"}, + "sigs.k8s.io/cluster-api/api/v1beta1.ClusterAvailabilityGate", "sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassPatch", "sigs.k8s.io/cluster-api/api/v1beta1.ClusterClassVariable", "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneClass", "sigs.k8s.io/cluster-api/api/v1beta1.InfrastructureNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.LocalObjectTemplate", "sigs.k8s.io/cluster-api/api/v1beta1.WorkersClass"}, } } @@ -708,7 +753,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterClassVariableMetadata(ref c Properties: map[string]spec.Schema{ "labels": { SchemaProps: spec.SchemaProps{ - Description: "Map of string keys and values that can be used to organize and categorize (scope and select) variables.", + Description: "labels is a map of string keys and values that can be used to organize and categorize (scope and select) variables.", Type: []string{"object"}, AdditionalProperties: &spec.SchemaOrBool{ Allows: true, @@ -815,13 +860,15 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterList(ref common.ReferenceCa }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "items is the list of Clusters.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -857,19 +904,19 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterNetwork(ref common.Referenc }, "services": { SchemaProps: spec.SchemaProps{ - Description: "The network ranges from which service VIPs are allocated.", + Description: "services is the network ranges from which service VIPs are allocated.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.NetworkRanges"), }, }, "pods": { SchemaProps: spec.SchemaProps{ - Description: "The network ranges from which Pod networks are allocated.", + Description: "pods is the network ranges from which Pod networks are allocated.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.NetworkRanges"), }, }, "serviceDomain": { SchemaProps: spec.SchemaProps{ - Description: "Domain name for services.", + Description: "serviceDomain is the domain name for services.", Type: []string{"string"}, Format: "", }, @@ -898,7 +945,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterSpec(ref common.ReferenceCa }, "clusterNetwork": { SchemaProps: spec.SchemaProps{ - Description: "Cluster network configuration.", + Description: "clusterNetwork represents the cluster network configuration.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ClusterNetwork"), }, }, @@ -923,7 +970,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterSpec(ref common.ReferenceCa }, "topology": { SchemaProps: spec.SchemaProps{ - Description: "This encapsulates the topology for the cluster. NOTE: It is required to enable the ClusterTopology feature gate flag to activate managed topologies support; this feature is highly experimental, and parts of it might still be not implemented.", + Description: "topology encapsulates the topology for the cluster. NOTE: It is required to enable the ClusterTopology feature gate flag to activate managed topologies support; this feature is highly experimental, and parts of it might still be not implemented.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.Topology"), }, }, @@ -937,7 +984,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterSpec(ref common.ReferenceCa }, }, SchemaProps: spec.SchemaProps{ - Description: "availabilityGates specifies additional conditions to include when evaluating Cluster Available condition.\n\nNOTE: this field is considered only for computing v1beta2 conditions.", + Description: "availabilityGates specifies additional conditions to include when evaluating Cluster Available condition.\n\nIf this field is not defined and the Cluster implements a managed topology, availabilityGates from the corresponding ClusterClass will be used, if any.\n\nNOTE: this field is considered only for computing v1beta2 conditions.", Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ @@ -995,7 +1042,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ClusterStatus(ref common.Reference }, "phase": { SchemaProps: spec.SchemaProps{ - Description: "phase represents the current phase of cluster actuation. E.g. Pending, Running, Terminating, Failed etc.", + Description: "phase represents the current phase of cluster actuation.", Type: []string{"string"}, Format: "", }, @@ -1169,20 +1216,20 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_Condition(ref common.ReferenceCall }, "lastTransitionTime": { SchemaProps: spec.SchemaProps{ - Description: "Last time the condition transitioned from one status to another. This should be when the underlying condition changed. If that is not known, then using the time when the API field changed is acceptable.", + Description: "lastTransitionTime is the last time the condition transitioned from one status to another. This should be when the underlying condition changed. If that is not known, then using the time when the API field changed is acceptable.", Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Time"), }, }, "reason": { SchemaProps: spec.SchemaProps{ - Description: "The reason for the condition's last transition in CamelCase. The specific API may choose whether or not this field is considered a guaranteed API. This field may be empty.", + Description: "reason is the reason for the condition's last transition in CamelCase. The specific API may choose whether or not this field is considered a guaranteed API. This field may be empty.", Type: []string{"string"}, Format: "", }, }, "message": { SchemaProps: spec.SchemaProps{ - Description: "A human readable message indicating details about the transition. This field may be empty.", + Description: "message is a human readable message indicating details about the transition. This field may be empty.", Type: []string{"string"}, Format: "", }, @@ -1252,12 +1299,34 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ControlPlaneClass(ref common.Refer Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Duration"), }, }, + "readinessGates": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-map-keys": []interface{}{ + "conditionType", + }, + "x-kubernetes-list-type": "map", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "readinessGates specifies additional conditions to include when evaluating Machine Ready condition.\n\nThis field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine.\n\nNOTE: This field is considered only for computing v1beta2 conditions. NOTE: If a Cluster defines a custom list of readinessGates for the control plane, such list overrides readinessGates defined in this field. NOTE: Specific control plane provider implementations might automatically extend the list of readinessGates; e.g. the kubeadm control provider adds ReadinessGates for the APIServerPodHealthy, SchedulerPodHealthy conditions, etc.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate"), + }, + }, + }, + }, + }, }, Required: []string{"ref"}, }, }, Dependencies: []string{ - "k8s.io/api/core/v1.ObjectReference", "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneClassNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.LocalObjectTemplate", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckClass", "sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"}, + "k8s.io/api/core/v1.ObjectReference", "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneClassNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.LocalObjectTemplate", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckClass", "sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate", "sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"}, } } @@ -1326,6 +1395,28 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ControlPlaneTopology(ref common.Re Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Duration"), }, }, + "readinessGates": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-map-keys": []interface{}{ + "conditionType", + }, + "x-kubernetes-list-type": "map", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "readinessGates specifies additional conditions to include when evaluating Machine Ready condition.\n\nThis field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine.\n\nIf this field is not defined, readinessGates from the corresponding ControlPlaneClass will be used, if any.\n\nNOTE: This field is considered only for computing v1beta2 conditions. NOTE: Specific control plane provider implementations might automatically extend the list of readinessGates; e.g. the kubeadm control provider adds ReadinessGates for the APIServerPodHealthy, SchedulerPodHealthy conditions, etc.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate"), + }, + }, + }, + }, + }, "variables": { SchemaProps: spec.SchemaProps{ Description: "variables can be used to customize the ControlPlane through patches.", @@ -1336,7 +1427,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ControlPlaneTopology(ref common.Re }, }, Dependencies: []string{ - "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneVariables", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckTopology", "sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"}, + "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.ControlPlaneVariables", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckTopology", "sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate", "sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"}, } } @@ -1463,6 +1554,26 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_FailureDomainSpec(ref common.Refer } } +func schema_sigsk8sio_cluster_api_api_v1beta1_InfrastructureNamingStrategy(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "InfrastructureNamingStrategy defines the naming strategy for infrastructure objects.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "template": { + SchemaProps: spec.SchemaProps{ + Description: "template defines the template to use for generating the name of the Infrastructure object. If not defined, it will fallback to `{{ .cluster.name }}-{{ .random }}`. If the templated string exceeds 63 characters, it will be trimmed to 58 characters and will get concatenated with a random suffix of length 5. The templating mechanism provides the following arguments: * `.cluster.name`: The name of the cluster object. * `.random`: A random alphanumeric string, without vowels, of length 5.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + } +} + func schema_sigsk8sio_cluster_api_api_v1beta1_JSONPatch(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -1856,20 +1967,23 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_Machine(ref common.ReferenceCallba }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSpec"), + Description: "spec is the desired state of Machine.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSpec"), }, }, "status": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineStatus"), + Description: "status is the observed state of Machine.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineStatus"), }, }, }, @@ -1889,7 +2003,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineAddress(ref common.Referenc Properties: map[string]spec.Schema{ "type": { SchemaProps: spec.SchemaProps{ - Description: "Machine address type, one of Hostname, ExternalIP, InternalIP, ExternalDNS or InternalDNS.", + Description: "type is the machine address type, one of Hostname, ExternalIP, InternalIP, ExternalDNS or InternalDNS.", Default: "", Type: []string{"string"}, Format: "", @@ -1897,7 +2011,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineAddress(ref common.Referenc }, "address": { SchemaProps: spec.SchemaProps{ - Description: "The machine address.", + Description: "address is the machine address.", Default: "", Type: []string{"string"}, Format: "", @@ -1960,20 +2074,23 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeployment(ref common.Refer }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentSpec"), + Description: "spec is the desired state of MachineDeployment.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentSpec"), }, }, "status": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStatus"), + Description: "status is the observed state of MachineDeployment.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStatus"), }, }, }, @@ -2045,14 +2162,36 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentClass(ref common. }, "minReadySeconds": { SchemaProps: spec.SchemaProps{ - Description: "Minimum number of seconds for which a newly created machine should be ready. Defaults to 0 (machine will be considered available as soon as it is ready) NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass.", + Description: "minReadySeconds is the minimum number of seconds for which a newly created machine should be ready. Defaults to 0 (machine will be considered available as soon as it is ready) NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass.", Type: []string{"integer"}, Format: "int32", }, }, + "readinessGates": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-map-keys": []interface{}{ + "conditionType", + }, + "x-kubernetes-list-type": "map", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "readinessGates specifies additional conditions to include when evaluating Machine Ready condition.\n\nThis field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine.\n\nNOTE: This field is considered only for computing v1beta2 conditions. NOTE: If a Cluster defines a custom list of readinessGates for a MachineDeployment using this MachineDeploymentClass, such list overrides readinessGates defined in this field.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate"), + }, + }, + }, + }, + }, "strategy": { SchemaProps: spec.SchemaProps{ - Description: "The deployment strategy to use to replace existing machines with new ones. NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass.", + Description: "strategy is the deployment strategy to use to replace existing machines with new ones. NOTE: This value can be overridden while defining a Cluster.Topology using this MachineDeploymentClass.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy"), }, }, @@ -2061,7 +2200,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentClass(ref common. }, }, Dependencies: []string{ - "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentClassNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentClassTemplate", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckClass"}, + "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentClassNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentClassTemplate", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckClass", "sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate"}, } } @@ -2145,13 +2284,15 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentList(ref common.R }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "items is the list of MachineDeployments.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -2188,7 +2329,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentSpec(ref common.R }, "replicas": { SchemaProps: spec.SchemaProps{ - Description: "Number of desired machines. This is a pointer to distinguish between explicit zero and not specified.\n\nDefaults to: * if the Kubernetes autoscaler min size and max size annotations are set:\n - if it's a new MachineDeployment, use min size\n - if the replicas field of the old MachineDeployment is < min size, use min size\n - if the replicas field of the old MachineDeployment is > max size, use max size\n - if the replicas field of the old MachineDeployment is in the (min size, max size) range, keep the value from the oldMD\n* otherwise use 1 Note: Defaulting will be run whenever the replicas field is not set: * A new MachineDeployment is created with replicas not set. * On an existing MachineDeployment the replicas field was first set and is now unset. Those cases are especially relevant for the following Kubernetes autoscaler use cases: * A new MachineDeployment is created and replicas should be managed by the autoscaler * An existing MachineDeployment which initially wasn't controlled by the autoscaler\n should be later controlled by the autoscaler", + Description: "replicas is the number of desired machines. This is a pointer to distinguish between explicit zero and not specified.\n\nDefaults to: * if the Kubernetes autoscaler min size and max size annotations are set:\n - if it's a new MachineDeployment, use min size\n - if the replicas field of the old MachineDeployment is < min size, use min size\n - if the replicas field of the old MachineDeployment is > max size, use max size\n - if the replicas field of the old MachineDeployment is in the (min size, max size) range, keep the value from the oldMD\n* otherwise use 1 Note: Defaulting will be run whenever the replicas field is not set: * A new MachineDeployment is created with replicas not set. * On an existing MachineDeployment the replicas field was first set and is now unset. Those cases are especially relevant for the following Kubernetes autoscaler use cases: * A new MachineDeployment is created and replicas should be managed by the autoscaler * An existing MachineDeployment which initially wasn't controlled by the autoscaler\n should be later controlled by the autoscaler", Type: []string{"integer"}, Format: "int32", }, @@ -2201,7 +2342,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentSpec(ref common.R }, "selector": { SchemaProps: spec.SchemaProps{ - Description: "Label selector for machines. Existing MachineSets whose machines are selected by this will be the ones affected by this deployment. It must match the machine template's labels.", + Description: "selector is the label selector for machines. Existing MachineSets whose machines are selected by this will be the ones affected by this deployment. It must match the machine template's labels.", Default: map[string]interface{}{}, Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.LabelSelector"), }, @@ -2215,10 +2356,16 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentSpec(ref common.R }, "strategy": { SchemaProps: spec.SchemaProps{ - Description: "The deployment strategy to use to replace existing machines with new ones.", + Description: "strategy is the deployment strategy to use to replace existing machines with new ones.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy"), }, }, + "machineNamingStrategy": { + SchemaProps: spec.SchemaProps{ + Description: "machineNamingStrategy allows changing the naming pattern used when creating Machines. Note: InfraMachines & BootstrapConfigs will use the same name as the corresponding Machines.", + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineNamingStrategy"), + }, + }, "minReadySeconds": { SchemaProps: spec.SchemaProps{ Description: "minReadySeconds is the minimum number of seconds for which a Node for a newly created machine should be ready before considering the replica available. Defaults to 0 (machine will be considered available as soon as the Node is ready)", @@ -2228,21 +2375,21 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentSpec(ref common.R }, "revisionHistoryLimit": { SchemaProps: spec.SchemaProps{ - Description: "The number of old MachineSets to retain to allow rollback. This is a pointer to distinguish between explicit zero and not specified. Defaults to 1.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10479 for more details.", + Description: "revisionHistoryLimit is the number of old MachineSets to retain to allow rollback. This is a pointer to distinguish between explicit zero and not specified. Defaults to 1.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10479 for more details.", Type: []string{"integer"}, Format: "int32", }, }, "paused": { SchemaProps: spec.SchemaProps{ - Description: "Indicates that the deployment is paused.", + Description: "paused indicates that the deployment is paused.", Type: []string{"boolean"}, Format: "", }, }, "progressDeadlineSeconds": { SchemaProps: spec.SchemaProps{ - Description: "The maximum time in seconds for a deployment to make progress before it is considered to be failed. The deployment controller will continue to process failed deployments and a condition with a ProgressDeadlineExceeded reason will be surfaced in the deployment status. Note that progress will not be estimated during the time a deployment is paused. Defaults to 600s.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/11470 for more details.", + Description: "progressDeadlineSeconds is the maximum time in seconds for a deployment to make progress before it is considered to be failed. The deployment controller will continue to process failed deployments and a condition with a ProgressDeadlineExceeded reason will be surfaced in the deployment status. Note that progress will not be estimated during the time a deployment is paused. Defaults to 600s.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/11470 for more details.", Type: []string{"integer"}, Format: "int32", }, @@ -2252,7 +2399,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentSpec(ref common.R }, }, Dependencies: []string{ - "k8s.io/apimachinery/pkg/apis/meta/v1.LabelSelector", "k8s.io/apimachinery/pkg/apis/meta/v1.Time", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineTemplateSpec"}, + "k8s.io/apimachinery/pkg/apis/meta/v1.LabelSelector", "k8s.io/apimachinery/pkg/apis/meta/v1.Time", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineTemplateSpec"}, } } @@ -2265,7 +2412,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStatus(ref common Properties: map[string]spec.Schema{ "observedGeneration": { SchemaProps: spec.SchemaProps{ - Description: "The generation observed by the deployment controller.", + Description: "observedGeneration is the generation observed by the deployment controller.", Type: []string{"integer"}, Format: "int64", }, @@ -2279,7 +2426,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStatus(ref common }, "replicas": { SchemaProps: spec.SchemaProps{ - Description: "Total number of non-terminated machines targeted by this deployment (their labels match the selector).", + Description: "replicas is the total number of non-terminated machines targeted by this deployment (their labels match the selector).", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -2287,7 +2434,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStatus(ref common }, "updatedReplicas": { SchemaProps: spec.SchemaProps{ - Description: "Total number of non-terminated machines targeted by this deployment that have the desired template spec.", + Description: "updatedReplicas is the total number of non-terminated machines targeted by this deployment that have the desired template spec.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -2295,7 +2442,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStatus(ref common }, "readyReplicas": { SchemaProps: spec.SchemaProps{ - Description: "Total number of ready machines targeted by this deployment.", + Description: "readyReplicas is the total number of ready machines targeted by this deployment.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -2303,7 +2450,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStatus(ref common }, "availableReplicas": { SchemaProps: spec.SchemaProps{ - Description: "Total number of available machines (ready for at least minReadySeconds) targeted by this deployment.", + Description: "availableReplicas is the total number of available machines (ready for at least minReadySeconds) targeted by this deployment.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -2311,7 +2458,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStatus(ref common }, "unavailableReplicas": { SchemaProps: spec.SchemaProps{ - Description: "Total number of unavailable machines targeted by this deployment. This is the total number of machines that are still required for the deployment to have 100% available capacity. They may either be machines that are running but not yet available or machines that still have not been created.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", + Description: "unavailableReplicas is the total number of unavailable machines targeted by this deployment. This is the total number of machines that are still required for the deployment to have 100% available capacity. They may either be machines that are running but not yet available or machines that still have not been created.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -2368,7 +2515,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentStrategy(ref comm }, "rollingUpdate": { SchemaProps: spec.SchemaProps{ - Description: "Rolling update config params. Present only if MachineDeploymentStrategyType = RollingUpdate.", + Description: "rollingUpdate is the rolling update config params. Present only if MachineDeploymentStrategyType = RollingUpdate.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineRollingUpdateDeployment"), }, }, @@ -2456,14 +2603,36 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentTopology(ref comm }, "minReadySeconds": { SchemaProps: spec.SchemaProps{ - Description: "Minimum number of seconds for which a newly created machine should be ready. Defaults to 0 (machine will be considered available as soon as it is ready)", + Description: "minReadySeconds is the minimum number of seconds for which a newly created machine should be ready. Defaults to 0 (machine will be considered available as soon as it is ready)", Type: []string{"integer"}, Format: "int32", }, }, + "readinessGates": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-map-keys": []interface{}{ + "conditionType", + }, + "x-kubernetes-list-type": "map", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "readinessGates specifies additional conditions to include when evaluating Machine Ready condition.\n\nThis field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine.\n\nIf this field is not defined, readinessGates from the corresponding MachineDeploymentClass will be used, if any.\n\nNOTE: This field is considered only for computing v1beta2 conditions.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate"), + }, + }, + }, + }, + }, "strategy": { SchemaProps: spec.SchemaProps{ - Description: "The deployment strategy to use to replace existing machines with new ones.", + Description: "strategy is the deployment strategy to use to replace existing machines with new ones.", Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy"), }, }, @@ -2478,7 +2647,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDeploymentTopology(ref comm }, }, Dependencies: []string{ - "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentVariables", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckTopology", "sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"}, + "k8s.io/apimachinery/pkg/apis/meta/v1.Duration", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineDeploymentVariables", "sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckTopology", "sigs.k8s.io/cluster-api/api/v1beta1.MachineReadinessGate", "sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"}, } } @@ -2600,8 +2769,9 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDrainRule(ref common.Refere }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { @@ -2629,7 +2799,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDrainRuleDrainConfig(ref co Properties: map[string]spec.Schema{ "behavior": { SchemaProps: spec.SchemaProps{ - Description: "behavior defines the drain behavior. Can be either \"Drain\" or \"Skip\". \"Drain\" means that the Pods to which this MachineDrainRule applies will be drained. If behavior is set to \"Drain\" the order in which Pods are drained can be configured with the order field. When draining Pods of a Node the Pods will be grouped by order and one group after another will be drained (by increasing order). Cluster API will wait until all Pods of a group are terminated / removed from the Node before starting with the next group. \"Skip\" means that the Pods to which this MachineDrainRule applies will be skipped during drain.", + Description: "behavior defines the drain behavior. Can be either \"Drain\", \"Skip\", or \"WaitCompleted\". \"Drain\" means that the Pods to which this MachineDrainRule applies will be drained. If behavior is set to \"Drain\" the order in which Pods are drained can be configured with the order field. When draining Pods of a Node the Pods will be grouped by order and one group after another will be drained (by increasing order). Cluster API will wait until all Pods of a group are terminated / removed from the Node before starting with the next group. \"Skip\" means that the Pods to which this MachineDrainRule applies will be skipped during drain. \"WaitCompleted\" means that the pods to which this MachineDrainRule applies will never be evicted and we wait for them to be completed, it is enforced that pods marked with this behavior always have Order=0.", Default: "", Type: []string{"string"}, Format: "", @@ -2672,8 +2842,9 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineDrainRuleList(ref common.Re }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { @@ -2837,20 +3008,21 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheck(ref common.Refe }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Description: "Specification of machine health check policy", + Description: "spec is the specification of machine health check policy", Default: map[string]interface{}{}, Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckSpec"), }, }, "status": { SchemaProps: spec.SchemaProps{ - Description: "Most recently observed status of MachineHealthCheck resource", + Description: "status is the most recently observed status of MachineHealthCheck resource", Default: map[string]interface{}{}, Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineHealthCheckStatus"), }, @@ -2886,13 +3058,13 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckClass(ref common }, "maxUnhealthy": { SchemaProps: spec.SchemaProps{ - Description: "Any further remediation is only allowed if at most \"MaxUnhealthy\" machines selected by \"selector\" are not healthy.", + Description: "maxUnhealthy specifies the maximum number of unhealthy machines allowed. Any further remediation is only allowed if at most \"maxUnhealthy\" machines selected by \"selector\" are not healthy.", Ref: ref("k8s.io/apimachinery/pkg/util/intstr.IntOrString"), }, }, "unhealthyRange": { SchemaProps: spec.SchemaProps{ - Description: "Any further remediation is only allowed if the number of machines selected by \"selector\" as not healthy is within the range of \"UnhealthyRange\". Takes precedence over MaxUnhealthy. Eg. \"[3-5]\" - This means that remediation will be allowed only when: (a) there are at least 3 unhealthy machines (and) (b) there are at most 5 unhealthy machines", + Description: "unhealthyRange specifies the range of unhealthy machines allowed. Any further remediation is only allowed if the number of machines selected by \"selector\" as not healthy is within the range of \"unhealthyRange\". Takes precedence over maxUnhealthy. Eg. \"[3-5]\" - This means that remediation will be allowed only when: (a) there are at least 3 unhealthy machines (and) (b) there are at most 5 unhealthy machines", Type: []string{"string"}, Format: "", }, @@ -2940,13 +3112,15 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckList(ref common. }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "items is the list of MachineHealthChecks.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -2983,7 +3157,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckSpec(ref common. }, "selector": { SchemaProps: spec.SchemaProps{ - Description: "Label selector to match machines whose health will be exercised", + Description: "selector is a label selector to match machines whose health will be exercised", Default: map[string]interface{}{}, Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.LabelSelector"), }, @@ -3004,13 +3178,13 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckSpec(ref common. }, "maxUnhealthy": { SchemaProps: spec.SchemaProps{ - Description: "Any further remediation is only allowed if at most \"MaxUnhealthy\" machines selected by \"selector\" are not healthy.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10722 for more details.", + Description: "maxUnhealthy specifies the maximum number of unhealthy machines allowed. Any further remediation is only allowed if at most \"maxUnhealthy\" machines selected by \"selector\" are not healthy.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10722 for more details.", Ref: ref("k8s.io/apimachinery/pkg/util/intstr.IntOrString"), }, }, "unhealthyRange": { SchemaProps: spec.SchemaProps{ - Description: "Any further remediation is only allowed if the number of machines selected by \"selector\" as not healthy is within the range of \"UnhealthyRange\". Takes precedence over MaxUnhealthy. Eg. \"[3-5]\" - This means that remediation will be allowed only when: (a) there are at least 3 unhealthy machines (and) (b) there are at most 5 unhealthy machines\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10722 for more details.", + Description: "unhealthyRange specifies the range of unhealthy machines allowed. Any further remediation is only allowed if the number of machines selected by \"selector\" as not healthy is within the range of \"unhealthyRange\". Takes precedence over maxUnhealthy. Eg. \"[3-5]\" - This means that remediation will be allowed only when: (a) there are at least 3 unhealthy machines (and) (b) there are at most 5 unhealthy machines\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/issues/10722 for more details.", Type: []string{"string"}, Format: "", }, @@ -3045,7 +3219,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckStatus(ref commo Properties: map[string]spec.Schema{ "expectedMachines": { SchemaProps: spec.SchemaProps{ - Description: "total number of machines counted by this machine health check", + Description: "expectedMachines is the total number of machines counted by this machine health check", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -3053,7 +3227,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckStatus(ref commo }, "currentHealthy": { SchemaProps: spec.SchemaProps{ - Description: "total number of healthy machines counted by this machine health check", + Description: "currentHealthy is the total number of healthy machines counted by this machine health check", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -3147,13 +3321,13 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineHealthCheckTopology(ref com }, "maxUnhealthy": { SchemaProps: spec.SchemaProps{ - Description: "Any further remediation is only allowed if at most \"MaxUnhealthy\" machines selected by \"selector\" are not healthy.", + Description: "maxUnhealthy specifies the maximum number of unhealthy machines allowed. Any further remediation is only allowed if at most \"maxUnhealthy\" machines selected by \"selector\" are not healthy.", Ref: ref("k8s.io/apimachinery/pkg/util/intstr.IntOrString"), }, }, "unhealthyRange": { SchemaProps: spec.SchemaProps{ - Description: "Any further remediation is only allowed if the number of machines selected by \"selector\" as not healthy is within the range of \"UnhealthyRange\". Takes precedence over MaxUnhealthy. Eg. \"[3-5]\" - This means that remediation will be allowed only when: (a) there are at least 3 unhealthy machines (and) (b) there are at most 5 unhealthy machines", + Description: "unhealthyRange specifies the range of unhealthy machines allowed. Any further remediation is only allowed if the number of machines selected by \"selector\" as not healthy is within the range of \"unhealthyRange\". Takes precedence over maxUnhealthy. Eg. \"[3-5]\" - This means that remediation will be allowed only when: (a) there are at least 3 unhealthy machines (and) (b) there are at most 5 unhealthy machines", Type: []string{"string"}, Format: "", }, @@ -3238,13 +3412,15 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineList(ref common.ReferenceCa }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "items is the list of Machines.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -3264,6 +3440,26 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineList(ref common.ReferenceCa } } +func schema_sigsk8sio_cluster_api_api_v1beta1_MachineNamingStrategy(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "MachineNamingStrategy allows changing the naming pattern used when creating Machines. Note: InfraMachines & BootstrapConfigs will use the same name as the corresponding Machines.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "template": { + SchemaProps: spec.SchemaProps{ + Description: "template defines the template to use for generating the names of the Machine objects. If not defined, it will fallback to `{{ .machineSet.name }}-{{ .random }}`. If the generated name string exceeds 63 characters, it will be trimmed to 58 characters and will get concatenated with a random suffix of length 5. Length of the template string must not exceed 256 characters. The template allows the following variables `.cluster.name`, `.machineSet.name` and `.random`. The variable `.cluster.name` retrieves the name of the cluster object that owns the Machines being created. The variable `.machineSet.name` retrieves the name of the MachineSet object that owns the Machines being created. The variable `.random` is substituted with random alphanumeric string, without vowels, of length 5. This variable is required part of the template. If not provided, validation will fail.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + } +} + func schema_sigsk8sio_cluster_api_api_v1beta1_MachinePoolClass(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -3327,7 +3523,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachinePoolClass(ref common.Refere }, "minReadySeconds": { SchemaProps: spec.SchemaProps{ - Description: "Minimum number of seconds for which a newly created machine pool should be ready. Defaults to 0 (machine will be considered available as soon as it is ready) NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.", + Description: "minReadySeconds is the minimum number of seconds for which a newly created machine pool should be ready. Defaults to 0 (machine will be considered available as soon as it is ready) NOTE: This value can be overridden while defining a Cluster.Topology using this MachinePoolClass.", Type: []string{"integer"}, Format: "int32", }, @@ -3463,7 +3659,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachinePoolTopology(ref common.Ref }, "minReadySeconds": { SchemaProps: spec.SchemaProps{ - Description: "Minimum number of seconds for which a newly created machine pool should be ready. Defaults to 0 (machine will be considered available as soon as it is ready)", + Description: "minReadySeconds is the minimum number of seconds for which a newly created machine pool should be ready. Defaults to 0 (machine will be considered available as soon as it is ready)", Type: []string{"integer"}, Format: "int32", }, @@ -3536,12 +3732,19 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineReadinessGate(ref common.Re Properties: map[string]spec.Schema{ "conditionType": { SchemaProps: spec.SchemaProps{ - Description: "conditionType refers to a positive polarity condition (status true means good) with matching type in the Machine's condition list. If the conditions doesn't exist, it will be treated as unknown. Note: Both Cluster API conditions or conditions added by 3rd party controllers can be used as readiness gates.", + Description: "conditionType refers to a condition with matching type in the Machine's condition list. If the conditions doesn't exist, it will be treated as unknown. Note: Both Cluster API conditions or conditions added by 3rd party controllers can be used as readiness gates.", Default: "", Type: []string{"string"}, Format: "", }, }, + "polarity": { + SchemaProps: spec.SchemaProps{ + Description: "polarity of the conditionType specified in this readinessGate. Valid values are Positive, Negative and omitted. When omitted, the default behaviour will be Positive. A positive polarity means that the condition should report a true status under normal conditions. A negative polarity means that the condition should report a false status under normal conditions.", + Type: []string{"string"}, + Format: "", + }, + }, }, Required: []string{"conditionType"}, }, @@ -3558,13 +3761,13 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineRollingUpdateDeployment(ref Properties: map[string]spec.Schema{ "maxUnavailable": { SchemaProps: spec.SchemaProps{ - Description: "The maximum number of machines that can be unavailable during the update. Value can be an absolute number (ex: 5) or a percentage of desired machines (ex: 10%). Absolute number is calculated from percentage by rounding down. This can not be 0 if MaxSurge is 0. Defaults to 0. Example: when this is set to 30%, the old MachineSet can be scaled down to 70% of desired machines immediately when the rolling update starts. Once new machines are ready, old MachineSet can be scaled down further, followed by scaling up the new MachineSet, ensuring that the total number of machines available at all times during the update is at least 70% of desired machines.", + Description: "maxUnavailable is the maximum number of machines that can be unavailable during the update. Value can be an absolute number (ex: 5) or a percentage of desired machines (ex: 10%). Absolute number is calculated from percentage by rounding down. This can not be 0 if MaxSurge is 0. Defaults to 0. Example: when this is set to 30%, the old MachineSet can be scaled down to 70% of desired machines immediately when the rolling update starts. Once new machines are ready, old MachineSet can be scaled down further, followed by scaling up the new MachineSet, ensuring that the total number of machines available at all times during the update is at least 70% of desired machines.", Ref: ref("k8s.io/apimachinery/pkg/util/intstr.IntOrString"), }, }, "maxSurge": { SchemaProps: spec.SchemaProps{ - Description: "The maximum number of machines that can be scheduled above the desired number of machines. Value can be an absolute number (ex: 5) or a percentage of desired machines (ex: 10%). This can not be 0 if MaxUnavailable is 0. Absolute number is calculated from percentage by rounding up. Defaults to 1. Example: when this is set to 30%, the new MachineSet can be scaled up immediately when the rolling update starts, such that the total number of old and new machines do not exceed 130% of desired machines. Once old machines have been killed, new MachineSet can be scaled up further, ensuring that total number of machines running at any time during the update is at most 130% of desired machines.", + Description: "maxSurge is the maximum number of machines that can be scheduled above the desired number of machines. Value can be an absolute number (ex: 5) or a percentage of desired machines (ex: 10%). This can not be 0 if MaxUnavailable is 0. Absolute number is calculated from percentage by rounding up. Defaults to 1. Example: when this is set to 30%, the new MachineSet can be scaled up immediately when the rolling update starts, such that the total number of old and new machines do not exceed 130% of desired machines. Once old machines have been killed, new MachineSet can be scaled up further, ensuring that total number of machines running at any time during the update is at most 130% of desired machines.", Ref: ref("k8s.io/apimachinery/pkg/util/intstr.IntOrString"), }, }, @@ -3606,20 +3809,23 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSet(ref common.ReferenceCal }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSetSpec"), + Description: "spec is the desired state of MachineSet.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSetSpec"), }, }, "status": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSetStatus"), + Description: "status is the observed state of MachineSet.", + Default: map[string]interface{}{}, + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSetStatus"), }, }, }, @@ -3653,13 +3859,15 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSetList(ref common.Referenc }, "metadata": { SchemaProps: spec.SchemaProps{ - Default: map[string]interface{}{}, - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + Description: "metadata is the standard list's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), }, }, "items": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "items is the list of MachineSets.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -3729,12 +3937,18 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSetSpec(ref common.Referenc Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineTemplateSpec"), }, }, + "machineNamingStrategy": { + SchemaProps: spec.SchemaProps{ + Description: "machineNamingStrategy allows changing the naming pattern used when creating Machines. Note: InfraMachines & BootstrapConfigs will use the same name as the corresponding Machines.", + Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineNamingStrategy"), + }, + }, }, Required: []string{"clusterName", "selector"}, }, }, Dependencies: []string{ - "k8s.io/apimachinery/pkg/apis/meta/v1.LabelSelector", "sigs.k8s.io/cluster-api/api/v1beta1.MachineTemplateSpec"}, + "k8s.io/apimachinery/pkg/apis/meta/v1.LabelSelector", "sigs.k8s.io/cluster-api/api/v1beta1.MachineNamingStrategy", "sigs.k8s.io/cluster-api/api/v1beta1.MachineTemplateSpec"}, } } @@ -3762,7 +3976,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSetStatus(ref common.Refere }, "fullyLabeledReplicas": { SchemaProps: spec.SchemaProps{ - Description: "The number of replicas that have labels matching the labels of the machine template of the MachineSet.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", + Description: "fullyLabeledReplicas is the number of replicas that have labels matching the labels of the machine template of the MachineSet.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -3770,7 +3984,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSetStatus(ref common.Refere }, "readyReplicas": { SchemaProps: spec.SchemaProps{ - Description: "The number of ready replicas for this MachineSet. A machine is considered ready when the node has been created and is \"Ready\".", + Description: "readyReplicas is the number of ready replicas for this MachineSet. A machine is considered ready when the node has been created and is \"Ready\".", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -3778,7 +3992,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSetStatus(ref common.Refere }, "availableReplicas": { SchemaProps: spec.SchemaProps{ - Description: "The number of available replicas (ready for at least minReadySeconds) for this MachineSet.", + Description: "availableReplicas is the number of available replicas (ready for at least minReadySeconds) for this MachineSet.", Default: 0, Type: []string{"integer"}, Format: "int32", @@ -3793,14 +4007,14 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineSetStatus(ref common.Refere }, "failureReason": { SchemaProps: spec.SchemaProps{ - Description: "In the event that there is a terminal problem reconciling the replicas, both FailureReason and FailureMessage will be set. FailureReason will be populated with a succinct value suitable for machine interpretation, while FailureMessage will contain a more verbose string suitable for logging and human consumption.\n\nThese fields should not be set for transitive errors that a controller faces that are expected to be fixed automatically over time (like service outages), but instead indicate that something is fundamentally wrong with the MachineTemplate's spec or the configuration of the machine controller, and that manual intervention is required. Examples of terminal errors would be invalid combinations of settings in the spec, values that are unsupported by the machine controller, or the responsible machine controller itself being critically misconfigured.\n\nAny transient errors that occur during the reconciliation of Machines can be added as events to the MachineSet object and/or logged in the controller's output.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", + Description: "failureReason will be set in the event that there is a terminal problem reconciling the Machine and will contain a succinct value suitable for machine interpretation.\n\nIn the event that there is a terminal problem reconciling the replicas, both FailureReason and FailureMessage will be set. FailureReason will be populated with a succinct value suitable for machine interpretation, while FailureMessage will contain a more verbose string suitable for logging and human consumption.\n\nThese fields should not be set for transitive errors that a controller faces that are expected to be fixed automatically over time (like service outages), but instead indicate that something is fundamentally wrong with the MachineTemplate's spec or the configuration of the machine controller, and that manual intervention is required. Examples of terminal errors would be invalid combinations of settings in the spec, values that are unsupported by the machine controller, or the responsible machine controller itself being critically misconfigured.\n\nAny transient errors that occur during the reconciliation of Machines can be added as events to the MachineSet object and/or logged in the controller's output.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", Type: []string{"string"}, Format: "", }, }, "failureMessage": { SchemaProps: spec.SchemaProps{ - Description: "Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", + Description: "failureMessage will be set in the event that there is a terminal problem reconciling the Machine and will contain a more verbose string suitable for logging and human consumption.\n\nDeprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details.", Type: []string{"string"}, Format: "", }, @@ -4045,7 +4259,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineStatus(ref common.Reference }, "phase": { SchemaProps: spec.SchemaProps{ - Description: "phase represents the current phase of machine actuation. E.g. Pending, Running, Terminating, Failed etc.", + Description: "phase represents the current phase of machine actuation.", Type: []string{"string"}, Format: "", }, @@ -4122,14 +4336,14 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_MachineTemplateSpec(ref common.Ref Properties: map[string]spec.Schema{ "metadata": { SchemaProps: spec.SchemaProps{ - Description: "Standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", + Description: "metadata is the standard object's metadata. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata", Default: map[string]interface{}{}, Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.ObjectMeta"), }, }, "spec": { SchemaProps: spec.SchemaProps{ - Description: "Specification of the desired behavior of the machine. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#spec-and-status", + Description: "spec is the specification of the desired behavior of the machine. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#spec-and-status", Default: map[string]interface{}{}, Ref: ref("sigs.k8s.io/cluster-api/api/v1beta1.MachineSpec"), }, @@ -4188,7 +4402,8 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_NetworkRanges(ref common.Reference Properties: map[string]spec.Schema{ "cidrBlocks": { SchemaProps: spec.SchemaProps{ - Type: []string{"array"}, + Description: "cidrBlocks is a list of CIDR blocks.", + Type: []string{"array"}, Items: &spec.SchemaOrArray{ Schema: &spec.Schema{ SchemaProps: spec.SchemaProps{ @@ -4216,7 +4431,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_ObjectMeta(ref common.ReferenceCal Properties: map[string]spec.Schema{ "labels": { SchemaProps: spec.SchemaProps{ - Description: "Map of string keys and values that can be used to organize and categorize (scope and select) objects. May match selectors of replication controllers and services. More info: http://kubernetes.io/docs/user-guide/labels", + Description: "labels is a map of string keys and values that can be used to organize and categorize (scope and select) objects. May match selectors of replication controllers and services. More info: http://kubernetes.io/docs/user-guide/labels", Type: []string{"object"}, AdditionalProperties: &spec.SchemaOrBool{ Allows: true, @@ -4455,15 +4670,22 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_Topology(ref common.ReferenceCallb Properties: map[string]spec.Schema{ "class": { SchemaProps: spec.SchemaProps{ - Description: "The name of the ClusterClass object to create the topology.", + Description: "class is the name of the ClusterClass object to create the topology.", Default: "", Type: []string{"string"}, Format: "", }, }, + "classNamespace": { + SchemaProps: spec.SchemaProps{ + Description: "classNamespace is the namespace of the ClusterClass object to create the topology. If the namespace is empty or not set, it is defaulted to the namespace of the cluster object. Value must follow the DNS1123Subdomain syntax.", + Type: []string{"string"}, + Format: "", + }, + }, "version": { SchemaProps: spec.SchemaProps{ - Description: "The Kubernetes version of the cluster.", + Description: "version is the Kubernetes version of the cluster.", Default: "", Type: []string{"string"}, Format: "", @@ -4528,21 +4750,24 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_UnhealthyCondition(ref common.Refe Properties: map[string]spec.Schema{ "type": { SchemaProps: spec.SchemaProps{ - Default: "", - Type: []string{"string"}, - Format: "", + Description: "type of Node condition", + Default: "", + Type: []string{"string"}, + Format: "", }, }, "status": { SchemaProps: spec.SchemaProps{ - Default: "", - Type: []string{"string"}, - Format: "", + Description: "status of the condition, one of True, False, Unknown.", + Default: "", + Type: []string{"string"}, + Format: "", }, }, "timeout": { SchemaProps: spec.SchemaProps{ - Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Duration"), + Description: "timeout is the duration that a node must be in a given status for, after which the node is considered unhealthy. For example, with a value of \"1h\", the node must match the status for at least 1 hour before being considered unhealthy.", + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Duration"), }, }, }, @@ -4637,7 +4862,7 @@ func schema_sigsk8sio_cluster_api_api_v1beta1_VariableSchemaMetadata(ref common. Properties: map[string]spec.Schema{ "labels": { SchemaProps: spec.SchemaProps{ - Description: "Map of string keys and values that can be used to organize and categorize (scope and select) variables.", + Description: "labels is a map of string keys and values that can be used to organize and categorize (scope and select) variables.", Type: []string{"object"}, AdditionalProperties: &spec.SchemaOrBool{ Allows: true, diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go index 7c9ac375330..97f7dafca20 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadm_types.go @@ -38,6 +38,7 @@ type InitConfiguration struct { // bootstrapTokens is respected at `kubeadm init` time and describes a set of Bootstrap Tokens to create. // This information IS NOT uploaded to the kubeadm cluster configmap, partly because of its sensitive nature // +optional + // +kubebuilder:validation:MaxItems=100 BootstrapTokens []BootstrapToken `json:"bootstrapTokens,omitempty"` // nodeRegistration holds fields that relate to registering the new control-plane node to the cluster. @@ -59,6 +60,9 @@ type InitConfiguration struct { // The list of phases can be obtained with the "kubeadm init --help" command. // This option takes effect only on Kubernetes >=1.22.0. // +optional + // +kubebuilder:validation:MaxItems=50 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 SkipPhases []string `json:"skipPhases,omitempty"` // patches contains options related to applying patches to components deployed by kubeadm during @@ -86,6 +90,8 @@ type ClusterConfiguration struct { // kubernetesVersion is the target version of the control plane. // NB: This value defaults to the Machine object spec.version // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 KubernetesVersion string `json:"kubernetesVersion,omitempty"` // controlPlaneEndpoint sets a stable IP address or DNS name for the control plane; it @@ -101,6 +107,8 @@ type ClusterConfiguration struct { // could be used for assigning a stable DNS to the control plane. // NB: This value defaults to the first value in the Cluster object status.apiEndpoints array. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 ControlPlaneEndpoint string `json:"controlPlaneEndpoint,omitempty"` // apiServer contains extra settings for the API server control plane component @@ -122,6 +130,8 @@ type ClusterConfiguration struct { // certificatesDir specifies where to store or look for all required certificates. // NB: if not provided, this will default to `/etc/kubernetes/pki` // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 CertificatesDir string `json:"certificatesDir,omitempty"` // imageRepository sets the container registry to pull images from. @@ -136,14 +146,18 @@ type ClusterConfiguration struct { // `gcr.io/k8s-staging-ci-images` will be used as a default for control plane components // and for kube-proxy, while `registry.k8s.io` will be used for all the other images. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 ImageRepository string `json:"imageRepository,omitempty"` // featureGates enabled by the user. // +optional FeatureGates map[string]bool `json:"featureGates,omitempty"` - // The cluster name + // clusterName is the cluster name // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName,omitempty"` } @@ -156,12 +170,14 @@ type ControlPlaneComponent struct { // extraVolumes is an extra set of host volumes, mounted to the control plane component. // +optional + // +kubebuilder:validation:MaxItems=100 ExtraVolumes []HostPathMount `json:"extraVolumes,omitempty"` // extraEnvs is an extra set of environment variables to pass to the control plane component. // Environment variables passed using ExtraEnvs will override any existing environment variables, or *_proxy environment variables that kubeadm adds by default. // This option takes effect only on Kubernetes >=1.31.0. // +optional + // +kubebuilder:validation:MaxItems=100 ExtraEnvs []EnvVar `json:"extraEnvs,omitempty"` } @@ -171,6 +187,9 @@ type APIServer struct { // certSANs sets extra Subject Alternative Names for the API Server signing cert. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=253 CertSANs []string `json:"certSANs,omitempty"` // timeoutForControlPlane controls the timeout that we use for API server to appear @@ -190,11 +209,15 @@ type ImageMeta struct { // imageRepository sets the container registry to pull images from. // if not set, the ImageRepository defined in ClusterConfiguration will be used instead. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 ImageRepository string `json:"imageRepository,omitempty"` // imageTag allows to specify a tag for the image. // In case this value is set, kubeadm does not change automatically the version of the above components during upgrades. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 ImageTag string `json:"imageTag,omitempty"` // TODO: evaluate if we need also a ImageName based on user feedbacks @@ -212,6 +235,7 @@ type ClusterStatus struct { // apiEndpoints currently available in the cluster, one for each control plane/api server instance. // The key of the map is the IP of the host's default interface + // +optional APIEndpoints map[string]APIEndpoint `json:"apiEndpoints"` } @@ -219,6 +243,8 @@ type ClusterStatus struct { type APIEndpoint struct { // advertiseAddress sets the IP address for the API server to advertise. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=39 AdvertiseAddress string `json:"advertiseAddress,omitempty"` // bindPort sets the secure port for the API Server to bind to. @@ -235,16 +261,21 @@ type NodeRegistrationOptions struct { // This field is also used in the CommonName field of the kubelet's client certificate to the API server. // Defaults to the hostname of the node if not provided. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 Name string `json:"name,omitempty"` // criSocket is used to retrieve container runtime info. This information will be annotated to the Node API object, for later re-use // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 CRISocket string `json:"criSocket,omitempty"` // taints specifies the taints the Node API object should be registered with. If this field is unset, i.e. nil, in the `kubeadm init` process // it will be defaulted to []v1.Taint{'node-role.kubernetes.io/master=""'}. If you don't want to taint your control-plane node, set this field to an // empty slice, i.e. `taints: []` in the YAML file. This field is solely used for Node registration. // +optional + // +kubebuilder:validation:MaxItems=100 Taints []corev1.Taint `json:"taints,omitempty"` // kubeletExtraArgs passes through extra arguments to the kubelet. The arguments here are passed to the kubelet command line via the environment file @@ -255,6 +286,9 @@ type NodeRegistrationOptions struct { // ignorePreflightErrors provides a slice of pre-flight errors to be ignored when the current node is registered. // +optional + // +kubebuilder:validation:MaxItems=50 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=512 IgnorePreflightErrors []string `json:"ignorePreflightErrors,omitempty"` // imagePullPolicy specifies the policy for image pulling @@ -330,14 +364,20 @@ type Networking struct { // Defaults to a comma-delimited string of the Cluster object's spec.clusterNetwork.pods.cidrBlocks, or // to "10.96.0.0/12" if that's unset. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 ServiceSubnet string `json:"serviceSubnet,omitempty"` // podSubnet is the subnet used by pods. // If unset, the API server will not allocate CIDR ranges for every node. // Defaults to a comma-delimited string of the Cluster object's spec.clusterNetwork.services.cidrBlocks if that is set // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 PodSubnet string `json:"podSubnet,omitempty"` // dnsDomain is the dns domain used by k8s services. Defaults to "cluster.local". // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 DNSDomain string `json:"dnsDomain,omitempty"` } @@ -345,10 +385,13 @@ type Networking struct { type BootstrapToken struct { // token is used for establishing bidirectional trust between nodes and control-planes. // Used for joining nodes in the cluster. + // +required Token *BootstrapTokenString `json:"token"` // description sets a human-friendly message why this token exists and what it's used // for, so other administrators can know its purpose. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Description string `json:"description,omitempty"` // ttl defines the time to live for this token. Defaults to 24h. // Expires and TTL are mutually exclusive. @@ -361,10 +404,16 @@ type BootstrapToken struct { // usages describes the ways in which this token can be used. Can by default be used // for establishing bidirectional trust, but that can be changed here. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 Usages []string `json:"usages,omitempty"` // groups specifies the extra groups that this token will authenticate as when/if // used for authentication // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 Groups []string `json:"groups,omitempty"` } @@ -390,6 +439,8 @@ type LocalEtcd struct { // dataDir is the directory etcd will place its data. // Defaults to "/var/lib/etcd". // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 DataDir string `json:"dataDir,omitempty"` // extraArgs are extra arguments provided to the etcd binary @@ -401,13 +452,21 @@ type LocalEtcd struct { // Environment variables passed using ExtraEnvs will override any existing environment variables, or *_proxy environment variables that kubeadm adds by default. // This option takes effect only on Kubernetes >=1.31.0. // +optional + // +kubebuilder:validation:MaxItems=100 ExtraEnvs []EnvVar `json:"extraEnvs,omitempty"` // serverCertSANs sets extra Subject Alternative Names for the etcd server signing cert. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=253 ServerCertSANs []string `json:"serverCertSANs,omitempty"` + // peerCertSANs sets extra Subject Alternative Names for the etcd peer signing cert. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=253 PeerCertSANs []string `json:"peerCertSANs,omitempty"` } @@ -415,18 +474,31 @@ type LocalEtcd struct { // Kubeadm has no knowledge of where certificate files live and they must be supplied. type ExternalEtcd struct { // endpoints of etcd members. Required for ExternalEtcd. + // +required + // +kubebuilder:validation:MaxItems=50 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=512 Endpoints []string `json:"endpoints"` // caFile is an SSL Certificate Authority file used to secure etcd communication. // Required if using a TLS connection. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 CAFile string `json:"caFile"` // certFile is an SSL certification file used to secure etcd communication. // Required if using a TLS connection. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 CertFile string `json:"certFile"` // keyFile is an SSL key file used to secure etcd communication. // Required if using a TLS connection. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 KeyFile string `json:"keyFile"` } @@ -447,6 +519,8 @@ type JoinConfiguration struct { // Defaults to "/etc/kubernetes/pki/ca.crt". // +optional // TODO: revisit when there is defaulting from k/k + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 CACertPath string `json:"caCertPath,omitempty"` // discovery specifies the options for the kubelet to use during the TLS Bootstrap process @@ -463,6 +537,9 @@ type JoinConfiguration struct { // The list of phases can be obtained with the "kubeadm init --help" command. // This option takes effect only on Kubernetes >=1.22.0. // +optional + // +kubebuilder:validation:MaxItems=50 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 SkipPhases []string `json:"skipPhases,omitempty"` // patches contains options related to applying patches to components deployed by kubeadm during @@ -494,6 +571,8 @@ type Discovery struct { // If .BootstrapToken is set, this field is defaulted to .BootstrapToken.Token, but can be overridden. // If .File is set, this field **must be set** in case the KubeConfigFile does not contain any other authentication information // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 TLSBootstrapToken string `json:"tlsBootstrapToken,omitempty"` // timeout modifies the discovery timeout @@ -505,10 +584,15 @@ type Discovery struct { type BootstrapTokenDiscovery struct { // token is a token used to validate cluster information // fetched from the control-plane. - Token string `json:"token"` + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 + Token string `json:"token,omitempty"` // apiServerEndpoint is an IP or domain name to the API server from which info will be fetched. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 APIServerEndpoint string `json:"apiServerEndpoint,omitempty"` // caCertHashes specifies a set of public key pins to verify @@ -520,6 +604,9 @@ type BootstrapTokenDiscovery struct { // ASN.1. These hashes can be calculated using, for example, OpenSSL: // openssl x509 -pubkey -in ca.crt openssl rsa -pubin -outform der 2>&/dev/null | openssl dgst -sha256 -hex // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=512 CACertHashes []string `json:"caCertHashes,omitempty"` // unsafeSkipCAVerification allows token-based discovery @@ -532,6 +619,9 @@ type BootstrapTokenDiscovery struct { // FileDiscovery is used to specify a file or URL to a kubeconfig file from which to load cluster information. type FileDiscovery struct { // kubeConfigPath is used to specify the actual file path or URL to the kubeconfig file from which to load cluster information + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 KubeConfigPath string `json:"kubeConfigPath"` // kubeConfig is used (optionally) to generate a KubeConfig based on the KubeadmConfig's information. @@ -556,6 +646,7 @@ type FileDiscoveryKubeConfig struct { // user contains information that describes identity information. // This is used to tell the kubernetes cluster who you are. + // +required User KubeConfigUser `json:"user"` } @@ -568,10 +659,14 @@ type KubeConfigCluster struct { // Defaults to https:// + Cluster.Spec.ControlPlaneEndpoint. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Server string `json:"server,omitempty"` // tlsServerName is used to check server certificate. If TLSServerName is empty, the hostname used to contact the server is used. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 TLSServerName string `json:"tlsServerName,omitempty"` // insecureSkipTLSVerify skips the validity check for the server's certificate. This will make your HTTPS connections insecure. @@ -583,6 +678,8 @@ type KubeConfigCluster struct { // Defaults to the Cluster's CA certificate if empty. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=51200 CertificateAuthorityData []byte `json:"certificateAuthorityData,omitempty"` // proxyURL is the URL to the proxy to be used for all requests made by this @@ -596,6 +693,8 @@ type KubeConfigCluster struct { // attach, port forward). // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 ProxyURL string `json:"proxyURL,omitempty"` } @@ -618,6 +717,9 @@ type KubeConfigUser struct { // KubeConfigAuthProvider holds the configuration for a specified auth provider. type KubeConfigAuthProvider struct { // name is the name of the authentication plugin. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Name string `json:"name"` // config holds the parameters for the authentication plugin. @@ -632,22 +734,31 @@ type KubeConfigAuthProvider struct { // and output format. type KubeConfigAuthExec struct { // command to execute. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=1024 Command string `json:"command"` - // Arguments to pass to the command when executing it. + // args is the arguments to pass to the command when executing it. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=512 Args []string `json:"args,omitempty"` // env defines additional environment variables to expose to the process. These // are unioned with the host's environment, as well as variables client-go uses // to pass argument to the plugin. // +optional + // +kubebuilder:validation:MaxItems=100 Env []KubeConfigAuthExecEnv `json:"env,omitempty"` - // Preferred input version of the ExecInfo. The returned ExecCredentials MUST use + // apiVersion is preferred input version of the ExecInfo. The returned ExecCredentials MUST use // the same encoding version as the input. // Defaults to client.authentication.k8s.io/v1 if not set. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 APIVersion string `json:"apiVersion,omitempty"` // provideClusterInfo determines whether or not to provide cluster information, @@ -662,7 +773,15 @@ type KubeConfigAuthExec struct { // KubeConfigAuthExecEnv is used for setting environment variables when executing an exec-based // credential plugin. type KubeConfigAuthExecEnv struct { - Name string `json:"name"` + // name of the environment variable + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 + Name string `json:"name"` + // value of the environment variable + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Value string `json:"value"` } @@ -670,11 +789,20 @@ type KubeConfigAuthExecEnv struct { // host. type HostPathMount struct { // name of the volume inside the pod template. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Name string `json:"name"` // hostPath is the path in the host that will be mounted inside // the pod. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 HostPath string `json:"hostPath"` // mountPath is the path inside the pod where hostPath will be mounted. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 MountPath string `json:"mountPath"` // readOnly controls write access to the volume // +optional @@ -754,6 +882,8 @@ type Patches struct { // specifies additional files to be created on the machine, either with content inline or // by referencing a secret. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Directory string `json:"directory,omitempty"` } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfig_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfig_types.go index ea2956d3085..b52ffdcd545 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfig_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfig_types.go @@ -65,6 +65,7 @@ type KubeadmConfigSpec struct { // files specifies extra files to be passed to user_data upon creation. // +optional + // +kubebuilder:validation:MaxItems=200 Files []File `json:"files,omitempty"` // diskSetup specifies options for the creation of partition tables and file systems on devices. @@ -73,18 +74,39 @@ type KubeadmConfigSpec struct { // mounts specifies a list of mount points to be setup. // +optional + // +kubebuilder:validation:MaxItems=100 Mounts []MountPoints `json:"mounts,omitempty"` - // preKubeadmCommands specifies extra commands to run before kubeadm runs + // bootCommands specifies extra commands to run very early in the boot process via the cloud-init bootcmd + // module. bootcmd will run on every boot, 'cloud-init-per' command can be used to make bootcmd run exactly + // once. This is typically run in the cloud-init.service systemd unit. This has no effect in Ignition. // +optional + // +kubebuilder:validation:MaxItems=1000 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=10240 + BootCommands []string `json:"bootCommands,omitempty"` + + // preKubeadmCommands specifies extra commands to run before kubeadm runs. + // With cloud-init, this is prepended to the runcmd module configuration, and is typically executed in + // the cloud-final.service systemd unit. In Ignition, this is prepended to /etc/kubeadm.sh. + // +optional + // +kubebuilder:validation:MaxItems=1000 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=10240 PreKubeadmCommands []string `json:"preKubeadmCommands,omitempty"` - // postKubeadmCommands specifies extra commands to run after kubeadm runs + // postKubeadmCommands specifies extra commands to run after kubeadm runs. + // With cloud-init, this is appended to the runcmd module configuration, and is typically executed in + // the cloud-final.service systemd unit. In Ignition, this is appended to /etc/kubeadm.sh. // +optional + // +kubebuilder:validation:MaxItems=1000 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=10240 PostKubeadmCommands []string `json:"postKubeadmCommands,omitempty"` // users specifies extra users to add // +optional + // +kubebuilder:validation:MaxItems=100 Users []User `json:"users,omitempty"` // ntp specifies NTP configuration @@ -347,6 +369,16 @@ func (c *KubeadmConfigSpec) validateIgnition(pathPrefix *field.Path) field.Error } } + if c.BootCommands != nil { + allErrs = append( + allErrs, + field.Forbidden( + pathPrefix.Child("bootCommands"), + cannotUseWithIgnition, + ), + ) + } + if c.DiskSetup == nil { return allErrs } @@ -409,6 +441,8 @@ type ContainerLinuxConfig struct { // // The data format is documented here: https://kinvolk.io/docs/flatcar-container-linux/latest/provisioning/cl-config/ // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 AdditionalConfig string `json:"additionalConfig,omitempty"` // strict controls if AdditionalConfig should be strictly parsed. If so, warnings are treated as errors. @@ -424,6 +458,8 @@ type KubeadmConfigStatus struct { // dataSecretName is the name of the secret that stores the bootstrap data script. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 DataSecretName *string `json:"dataSecretName,omitempty"` // failureReason will be set on non-retryable errors @@ -431,6 +467,8 @@ type KubeadmConfigStatus struct { // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 FailureReason string `json:"failureReason,omitempty"` // failureMessage will be set on non-retryable errors @@ -438,6 +476,8 @@ type KubeadmConfigStatus struct { // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 FailureMessage string `json:"failureMessage,omitempty"` // observedGeneration is the latest generation observed by the controller. @@ -474,10 +514,17 @@ type KubeadmConfigV1Beta2Status struct { // KubeadmConfig is the Schema for the kubeadmconfigs API. type KubeadmConfig struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec KubeadmConfigSpec `json:"spec,omitempty"` + // spec is the desired state of KubeadmConfig. + // +optional + Spec KubeadmConfigSpec `json:"spec,omitempty"` + // status is the observed state of KubeadmConfig. + // +optional Status KubeadmConfigStatus `json:"status,omitempty"` } @@ -512,8 +559,12 @@ func (c *KubeadmConfig) SetV1Beta2Conditions(conditions []metav1.Condition) { // KubeadmConfigList contains a list of KubeadmConfig. type KubeadmConfigList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []KubeadmConfig `json:"items"` + // items is the list of KubeadmConfigs. + Items []KubeadmConfig `json:"items"` } func init() { @@ -536,14 +587,21 @@ const ( // File defines the input for generating write_files in cloud-init. type File struct { // path specifies the full path on disk where to store the file. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 Path string `json:"path"` // owner specifies the ownership of the file, e.g. "root:root". // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Owner string `json:"owner,omitempty"` // permissions specifies the permissions to assign to the file, e.g. "0640". // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=16 Permissions string `json:"permissions,omitempty"` // encoding specifies the encoding of the file contents. @@ -556,6 +614,8 @@ type File struct { // content is the actual content of the file. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 Content string `json:"content,omitempty"` // contentFrom is a referenced source of content to populate the file. @@ -568,6 +628,7 @@ type File struct { // sources of data for target systems should add them here. type FileSource struct { // secret represents a secret that should populate this file. + // +required Secret SecretFileSource `json:"secret"` } @@ -577,9 +638,15 @@ type FileSource struct { // as files using the keys in the Data field as the file names. type SecretFileSource struct { // name of the secret in the KubeadmBootstrapConfig's namespace to use. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 Name string `json:"name"` // key is the key in the secret's data map for this value. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Key string `json:"key"` } @@ -588,6 +655,7 @@ type SecretFileSource struct { // sources of data for target systems should add them here. type PasswdSource struct { // secret represents a secret that should populate this password. + // +required Secret SecretPasswdSource `json:"secret"` } @@ -597,27 +665,42 @@ type PasswdSource struct { // as passwd using the keys in the Data field as the file names. type SecretPasswdSource struct { // name of the secret in the KubeadmBootstrapConfig's namespace to use. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 Name string `json:"name"` // key is the key in the secret's data map for this value. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Key string `json:"key"` } // User defines the input for a generated user in cloud-init. type User struct { // name specifies the user name + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Name string `json:"name"` // gecos specifies the gecos to use for the user // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Gecos *string `json:"gecos,omitempty"` // groups specifies the additional groups for the user // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Groups *string `json:"groups,omitempty"` // homeDir specifies the home directory to use for the user // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 HomeDir *string `json:"homeDir,omitempty"` // inactive specifies whether to mark the user as inactive @@ -626,10 +709,14 @@ type User struct { // shell specifies the user's shell // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Shell *string `json:"shell,omitempty"` // passwd specifies a hashed password for the user // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Passwd *string `json:"passwd,omitempty"` // passwdFrom is a referenced source of passwd to populate the passwd. @@ -638,6 +725,8 @@ type User struct { // primaryGroup specifies the primary group for the user // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 PrimaryGroup *string `json:"primaryGroup,omitempty"` // lockPassword specifies if password login should be disabled @@ -646,10 +735,15 @@ type User struct { // sudo specifies a sudo role for the user // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Sudo *string `json:"sudo,omitempty"` // sshAuthorizedKeys specifies a list of ssh authorized keys for the user // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=2048 SSHAuthorizedKeys []string `json:"sshAuthorizedKeys,omitempty"` } @@ -657,6 +751,9 @@ type User struct { type NTP struct { // servers specifies which NTP servers to use // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=512 Servers []string `json:"servers,omitempty"` // enabled specifies whether NTP should be enabled @@ -668,20 +765,26 @@ type NTP struct { type DiskSetup struct { // partitions specifies the list of the partitions to setup. // +optional + // +kubebuilder:validation:MaxItems=100 Partitions []Partition `json:"partitions,omitempty"` // filesystems specifies the list of file systems to setup. // +optional + // +kubebuilder:validation:MaxItems=100 Filesystems []Filesystem `json:"filesystems,omitempty"` } // Partition defines how to create and layout a partition. type Partition struct { // device is the name of the device. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Device string `json:"device"` // layout specifies the device layout. // If it is true, a single partition will be created for the entire device. // When layout is false, it means don't partition or ignore existing partitioning. + // +required Layout bool `json:"layout"` // overwrite describes whether to skip checks and create the partition if a partition or filesystem is found on the device. // Use with caution. Default is 'false'. @@ -691,32 +794,57 @@ type Partition struct { // 'mbr': default and setups a MS-DOS partition table // 'gpt': setups a GPT partition table // +optional + // +kubebuilder:validation:Enum=mbr;gpt TableType *string `json:"tableType,omitempty"` } // Filesystem defines the file systems to be created. type Filesystem struct { // device specifies the device name + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Device string `json:"device"` + // filesystem specifies the file system type. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=128 Filesystem string `json:"filesystem"` + // label specifies the file system label to be used. If set to None, no label is used. - Label string `json:"label"` + // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=512 + Label string `json:"label,omitempty"` + // partition specifies the partition to use. The valid options are: "auto|any", "auto", "any", "none", and , where NUM is the actual partition number. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=128 Partition *string `json:"partition,omitempty"` + // overwrite defines whether or not to overwrite any existing filesystem. // If true, any pre-existing file system will be destroyed. Use with Caution. // +optional Overwrite *bool `json:"overwrite,omitempty"` + // replaceFS is a special directive, used for Microsoft Azure that instructs cloud-init to replace a file system of . // NOTE: unless you define a label, this requires the use of the 'any' partition directive. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=128 ReplaceFS *string `json:"replaceFS,omitempty"` + // extraOpts defined extra options to add to the command for creating the file system. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 ExtraOpts []string `json:"extraOpts,omitempty"` } // MountPoints defines input for generated mounts in cloud-init. +// +kubebuilder:validation:items:MinLength=1 +// +kubebuilder:validation:items:MaxLength=512 type MountPoints []string diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfigtemplate_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfigtemplate_types.go index 4326cb4599c..c1309bf15c7 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfigtemplate_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/kubeadmconfigtemplate_types.go @@ -24,16 +24,20 @@ import ( // KubeadmConfigTemplateSpec defines the desired state of KubeadmConfigTemplate. type KubeadmConfigTemplateSpec struct { + // template defines the desired state of KubeadmConfigTemplate. + // +required Template KubeadmConfigTemplateResource `json:"template"` } // KubeadmConfigTemplateResource defines the Template structure. type KubeadmConfigTemplateResource struct { - // Standard object's metadata. + // metadata is the standard object's metadata. // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata // +optional ObjectMeta clusterv1.ObjectMeta `json:"metadata,omitempty"` + // spec is the desired state of KubeadmConfig. + // +optional Spec KubeadmConfigSpec `json:"spec,omitempty"` } @@ -44,9 +48,14 @@ type KubeadmConfigTemplateResource struct { // KubeadmConfigTemplate is the Schema for the kubeadmconfigtemplates API. type KubeadmConfigTemplate struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` + // spec is the desired state of KubeadmConfigTemplate. + // +optional Spec KubeadmConfigTemplateSpec `json:"spec,omitempty"` } @@ -55,8 +64,12 @@ type KubeadmConfigTemplate struct { // KubeadmConfigTemplateList contains a list of KubeadmConfigTemplate. type KubeadmConfigTemplateList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []KubeadmConfigTemplate `json:"items"` + // items is the list of KubeadmConfigTemplates. + Items []KubeadmConfigTemplate `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go index 3f508065e68..e1bdbac23f9 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/bootstrap/kubeadm/api/v1beta1/zz_generated.deepcopy.go @@ -864,6 +864,11 @@ func (in *KubeadmConfigSpec) DeepCopyInto(out *KubeadmConfigSpec) { } } } + if in.BootCommands != nil { + in, out := &in.BootCommands, &out.BootCommands + *out = make([]string, len(*in)) + copy(*out, *in) + } if in.PreKubeadmCommands != nil { in, out := &in.PreKubeadmCommands, &out.PreKubeadmCommands *out = make([]string, len(*in)) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor.go index ff24b0d6e1e..710bda38cdc 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor.go @@ -54,6 +54,10 @@ type clusterAccessor struct { // and health checking information (e.g. lastProbeSuccessTimestamp, consecutiveFailures). // lockedStateLock must be *always* held (via lock or rLock) before accessing this field. lockedState clusterAccessorLockedState + + // cacheCtx is the ctx used when starting the cache. + // This ctx can be used by the ClusterCache to stop the cache. + cacheCtx context.Context //nolint:containedctx } // clusterAccessorConfig is the config of the clusterAccessor. @@ -211,10 +215,11 @@ type clusterAccessorLockedHealthCheckingState struct { } // newClusterAccessor creates a new clusterAccessor. -func newClusterAccessor(cluster client.ObjectKey, clusterAccessorConfig *clusterAccessorConfig) *clusterAccessor { +func newClusterAccessor(cacheCtx context.Context, cluster client.ObjectKey, clusterAccessorConfig *clusterAccessorConfig) *clusterAccessor { return &clusterAccessor{ - cluster: cluster, - config: clusterAccessorConfig, + cacheCtx: cacheCtx, + cluster: cluster, + config: clusterAccessorConfig, } } @@ -255,7 +260,10 @@ func (ca *clusterAccessor) Connect(ctx context.Context) (retErr error) { defer func() { if retErr != nil { log.Error(retErr, "Connect failed") + connectionUp.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace).Set(0) ca.lockedState.lastConnectionCreationErrorTimestamp = time.Now() + } else { + connectionUp.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace).Set(1) } }() @@ -298,15 +306,17 @@ func (ca *clusterAccessor) Connect(ctx context.Context) (retErr error) { // Disconnect disconnects a connection to the workload cluster. func (ca *clusterAccessor) Disconnect(ctx context.Context) { log := ctrl.LoggerFrom(ctx) - if !ca.Connected(ctx) { log.V(6).Info("Skipping disconnect, already disconnected") return } ca.lock(ctx) - defer ca.unlock(ctx) + defer func() { + ca.unlock(ctx) + connectionUp.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace).Set(0) + }() log.Info("Disconnecting") // Stopping the cache is non-blocking, so it's okay to do it while holding the lock. @@ -351,14 +361,20 @@ func (ca *clusterAccessor) HealthCheck(ctx context.Context) (bool, bool) { unauthorizedErrorOccurred = true ca.lockedState.healthChecking.consecutiveFailures++ log.V(6).Info(fmt.Sprintf("Health probe failed (unauthorized error occurred): %v", err)) + healthCheck.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace).Set(0) + healthChecksTotal.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace, "error").Inc() case err != nil: ca.lockedState.healthChecking.consecutiveFailures++ log.V(6).Info(fmt.Sprintf("Health probe failed (%d/%d): %v", ca.lockedState.healthChecking.consecutiveFailures, ca.config.HealthProbe.FailureThreshold, err)) + healthCheck.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace).Set(0) + healthChecksTotal.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace, "error").Inc() default: ca.lockedState.healthChecking.consecutiveFailures = 0 ca.lockedState.healthChecking.lastProbeSuccessTimestamp = ca.lockedState.healthChecking.lastProbeTimestamp log.V(6).Info("Health probe succeeded") + healthCheck.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace).Set(1) + healthChecksTotal.WithLabelValues(ca.cluster.Name, ca.cluster.Namespace, "success").Inc() } tooManyConsecutiveFailures := ca.lockedState.healthChecking.consecutiveFailures >= ca.config.HealthProbe.FailureThreshold diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor_client.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor_client.go index 55fe61ca602..7e5ae248462 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor_client.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_accessor_client.go @@ -100,7 +100,7 @@ func (ca *clusterAccessor) createConnection(ctx context.Context) (*createConnect } log.V(6).Info("Creating cached client and cache") - cachedClient, cache, err := createCachedClient(ctx, ca.config, restConfig, httpClient, mapper) + cachedClient, cache, err := createCachedClient(ctx, ca.cacheCtx, ca.config, restConfig, httpClient, mapper) if err != nil { return nil, err } @@ -212,23 +212,37 @@ func createUncachedClient(scheme *runtime.Scheme, config *rest.Config, httpClien } // createCachedClient creates a cached client for the given cluster, based on the rest.Config. -func createCachedClient(ctx context.Context, clusterAccessorConfig *clusterAccessorConfig, config *rest.Config, httpClient *http.Client, mapper meta.RESTMapper) (client.Client, *stoppableCache, error) { +func createCachedClient(ctx, cacheCtx context.Context, clusterAccessorConfig *clusterAccessorConfig, config *rest.Config, httpClient *http.Client, mapper meta.RESTMapper) (client.Client, *stoppableCache, error) { + // This config will only be used for List and Watch calls of informers + // because we don't want these requests to time out after the regular timeout + // of Options.Client.Timeout (default 10s). + // Lists of informers have no timeouts set. + // Watches of informers are timing out per default after [5m, 2*5m]. + // https://github.com/kubernetes/client-go/blob/v0.32.0/tools/cache/reflector.go#L53-L55 + // We are setting 11m to set a timeout for List calls without influencing Watch calls. + configWith11mTimeout := rest.CopyConfig(config) + configWith11mTimeout.Timeout = 11 * time.Minute + httpClientWith11mTimeout, err := rest.HTTPClientFor(configWith11mTimeout) + if err != nil { + return nil, nil, errors.Wrapf(err, "error creating cache: error creating HTTP client") + } + // Create the cache for the cluster. cacheOptions := cache.Options{ - HTTPClient: httpClient, + HTTPClient: httpClientWith11mTimeout, Scheme: clusterAccessorConfig.Scheme, Mapper: mapper, SyncPeriod: clusterAccessorConfig.Cache.SyncPeriod, ByObject: clusterAccessorConfig.Cache.ByObject, } - remoteCache, err := cache.New(config, cacheOptions) + remoteCache, err := cache.New(configWith11mTimeout, cacheOptions) if err != nil { return nil, nil, errors.Wrapf(err, "error creating cache") } // Use a context that is independent of the passed in context, so the cache doesn't get stopped // when the passed in context is canceled. - cacheCtx, cacheCtxCancel := context.WithCancel(context.Background()) + cacheCtx, cacheCtxCancel := context.WithCancelCause(cacheCtx) // We need to be able to stop the cache's shared informers, so wrap this in a stoppableCache. cache := &stoppableCache{ @@ -261,7 +275,7 @@ func createCachedClient(ctx context.Context, clusterAccessorConfig *clusterAcces go cache.Start(cacheCtx) //nolint:errcheck // Wait until the cache is initially synced. - cacheSyncCtx, cacheSyncCtxCancel := context.WithTimeout(ctx, clusterAccessorConfig.Cache.InitialSyncTimeout) + cacheSyncCtx, cacheSyncCtxCancel := context.WithTimeoutCause(ctx, clusterAccessorConfig.Cache.InitialSyncTimeout, errors.New("initial sync timeout expired")) defer cacheSyncCtxCancel() if !cache.WaitForCacheSync(cacheSyncCtx) { cache.Stop() @@ -297,13 +311,13 @@ type clientWithTimeout struct { var _ client.Client = &clientWithTimeout{} func (c clientWithTimeout) Get(ctx context.Context, key client.ObjectKey, obj client.Object, opts ...client.GetOption) error { - ctx, cancel := context.WithTimeout(ctx, c.timeout) + ctx, cancel := context.WithTimeoutCause(ctx, c.timeout, errors.New("call timeout expired")) defer cancel() return c.Client.Get(ctx, key, obj, opts...) } func (c clientWithTimeout) List(ctx context.Context, list client.ObjectList, opts ...client.ListOption) error { - ctx, cancel := context.WithTimeout(ctx, c.timeout) + ctx, cancel := context.WithTimeoutCause(ctx, c.timeout, errors.New("call timeout expired")) defer cancel() return c.Client.List(ctx, list, opts...) } @@ -314,7 +328,7 @@ type stoppableCache struct { lock sync.Mutex stopped bool - cancelFunc context.CancelFunc + cancelFunc context.CancelCauseFunc } // Stop cancels the cache.Cache's context, unless it has already been stopped. @@ -327,5 +341,5 @@ func (cc *stoppableCache) Stop() { } cc.stopped = true - cc.cancelFunc() + cc.cancelFunc(errors.New("cache stopped")) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_cache.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_cache.go index f907e252569..eee8dcdc7c0 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_cache.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/cluster_cache.go @@ -295,10 +295,14 @@ func SetupWithManager(ctx context.Context, mgr manager.Manager, options Options, log.Info("Couldn't find controller Pod metadata, the ClusterCache will always access the cluster it is running on using the regular apiserver endpoint") } + cacheCtx, cacheCtxCancel := context.WithCancelCause(context.Background()) + cc := &clusterCache{ client: mgr.GetClient(), clusterAccessorConfig: buildClusterAccessorConfig(mgr.GetScheme(), options, controllerPodMetadata), clusterAccessors: make(map[client.ObjectKey]*clusterAccessor), + cacheCtx: cacheCtx, + cacheCtxCancel: cacheCtxCancel, } err := ctrl.NewControllerManagedBy(mgr). @@ -331,6 +335,12 @@ type clusterCache struct { // This information is necessary so we can enqueue reconcile.Requests for reconcilers that // got a cluster source via GetClusterSource. clusterSources []clusterSource + + // cacheCtx is passed to clusterAccessors to be used when starting caches. + cacheCtx context.Context //nolint:containedctx + + // cacheCtxCancel is used during Shutdown to stop caches. + cacheCtxCancel context.CancelCauseFunc } // clusterSource stores the necessary information so we can enqueue reconcile.Requests for reconcilers that @@ -523,7 +533,7 @@ func (cc *clusterCache) getOrCreateClusterAccessor(cluster client.ObjectKey) *cl accessor, ok := cc.clusterAccessors[cluster] if !ok { - accessor = newClusterAccessor(cluster, cc.clusterAccessorConfig) + accessor = newClusterAccessor(cc.cacheCtx, cluster, cc.clusterAccessorConfig) cc.clusterAccessors[cluster] = accessor } @@ -656,6 +666,13 @@ func (cc *clusterCache) SetConnectionCreationRetryInterval(interval time.Duratio cc.clusterAccessorConfig.ConnectionCreationRetryInterval = interval } +// Shutdown can be used to shut down the ClusterCache in unit tests. +// This method should only be used for tests because it hasn't been designed for production usage +// in a manager (race conditions with manager shutdown etc.). +func (cc *clusterCache) Shutdown() { + cc.cacheCtxCancel(errors.New("ClusterCache is shutdown")) +} + func validateAndDefaultOptions(opts *Options) error { if opts.SecretClient == nil { return errors.New("options.SecretClient must be set") diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/metrics.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/metrics.go new file mode 100644 index 00000000000..7999560fa37 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/clustercache/metrics.go @@ -0,0 +1,56 @@ +/* +Copyright 2024 The Kubernetes Authors. + +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 clustercache + +import ( + "github.com/prometheus/client_golang/prometheus" + ctrlmetrics "sigs.k8s.io/controller-runtime/pkg/metrics" +) + +func init() { + // Register the metrics at the controller-runtime metrics registry. + ctrlmetrics.Registry.MustRegister(healthCheck) + ctrlmetrics.Registry.MustRegister(connectionUp) + ctrlmetrics.Registry.MustRegister(healthChecksTotal) +} + +var ( + healthCheck = prometheus.NewGaugeVec( + prometheus.GaugeOpts{ + Name: "capi_cluster_cache_healthcheck", + Help: "Result of the last clustercache healthcheck for a cluster.", + }, []string{ + "cluster_name", "cluster_namespace", + }, + ) + healthChecksTotal = prometheus.NewCounterVec( + prometheus.CounterOpts{ + Name: "capi_cluster_cache_healthchecks_total", + Help: "Results of all clustercache healthchecks.", + }, []string{ + "cluster_name", "cluster_namespace", "status", + }, + ) + connectionUp = prometheus.NewGaugeVec( + prometheus.GaugeOpts{ + Name: "capi_cluster_cache_connection_up", + Help: "Whether the connection to the cluster is up.", + }, []string{ + "cluster_name", "cluster_namespace", + }, + ) +) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/crdmigrator/crd_migrator.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/crdmigrator/crd_migrator.go new file mode 100644 index 00000000000..d2c024989ff --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/crdmigrator/crd_migrator.go @@ -0,0 +1,567 @@ +/* +Copyright 2025 The Kubernetes Authors. + +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 crdmigrator contains the CRD migrator implementation. +package crdmigrator + +import ( + "context" + "encoding/json" + "fmt" + "strconv" + "time" + + "github.com/pkg/errors" + apiextensionsv1 "k8s.io/apiextensions-apiserver/pkg/apis/apiextensions/v1" + apierrors "k8s.io/apimachinery/pkg/api/errors" + "k8s.io/apimachinery/pkg/api/meta" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured" + "k8s.io/apimachinery/pkg/runtime" + "k8s.io/apimachinery/pkg/runtime/schema" + "k8s.io/apimachinery/pkg/types" + kerrors "k8s.io/apimachinery/pkg/util/errors" + "k8s.io/apimachinery/pkg/util/sets" + "k8s.io/client-go/util/retry" + "k8s.io/klog/v2" + "k8s.io/utils/ptr" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/builder" + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/client/apiutil" + "sigs.k8s.io/controller-runtime/pkg/controller" + + clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" + "sigs.k8s.io/cluster-api/util/cache" + "sigs.k8s.io/cluster-api/util/contract" + "sigs.k8s.io/cluster-api/util/predicates" +) + +// Phase is a phase of the CRD migration. +type Phase string + +var ( + // StorageVersionMigrationPhase is the phase in which the storage version is migrated. + // This means if the .status.storedVersions field of a CRD is not equal to [storageVersion], + // a no-op patch is applied to all custom resources of the CRD to ensure they are all stored in + // the current storageVersion in etcd. Afterward .status.storedVersions is set to [storageVersion]. + // For more information see: + // https://kubernetes.io/docs/tasks/extend-kubernetes/custom-resources/custom-resource-definition-versioning/ + StorageVersionMigrationPhase Phase = "StorageVersionMigration" + + // CleanupManagedFieldsPhase is the phase in which managedFields are cleaned up. + // This means for all custom resources of a CRD, managedFields that contain apiVersions that + // are not served anymore are removed. + // For more information see: + // https://github.com/kubernetes/kubernetes/issues/111937 + CleanupManagedFieldsPhase Phase = "CleanupManagedFields" +) + +// CRDMigrator migrates CRDs. +type CRDMigrator struct { + // Client is a cached client that is used: + // * for all cached Get & List calls + // * for all Patch calls + Client client.Client + + // APIReader is a live client that is used: + // * for all live Get & List calls + APIReader client.Reader + + // Comma-separated list of CRD migration phases to skip. + // Valid values are: All, StorageVersionMigration, CleanupManagedFields. + SkipCRDMigrationPhases []Phase + crdMigrationPhasesToRun sets.Set[Phase] + + // Config allows to configure which objects should be migrated. + Config map[client.Object]ByObjectConfig + configByCRDName map[string]ByObjectConfig + + storageVersionMigrationCache cache.Cache[objectEntry] +} + +// ByObjectConfig contains object-specific config for the CRD migration. +type ByObjectConfig struct { + // UseCache configures if the cached client should be used for Get & List calls for this object. + // Get & List calls on the cached client automatically trigger the creation of an informer which + // requires a significant amount of memory. + // Thus it is only recommended to enable this setting for objects for which the controller already uses the cache. + // Note: If this is enabled, we will use the corresponding Go type of the object for Get & List calls to avoid + // creating additional informers for UnstructuredList/PartialObjectMetadataList. + UseCache bool + + // UseStatusForStorageVersionMigration configures if the storage version migration for this CRD should + // be triggered via the status endpoint instead of an update on the CRs directly (which is the default). + // As mutating and validating webhooks are usually not configured on the status subresource this can help to + // avoid mutating & validation webhook errors that would block the no-op updates and thus the storage migration. + UseStatusForStorageVersionMigration bool +} + +func (r *CRDMigrator) SetupWithManager(ctx context.Context, mgr ctrl.Manager, controllerOptions controller.Options) error { + if err := r.setup(mgr.GetScheme()); err != nil { + return err + } + + if len(r.crdMigrationPhasesToRun) == 0 { + // Nothing to do + return nil + } + + predicateLog := ctrl.LoggerFrom(ctx).WithValues("controller", "crdmigrator") + err := ctrl.NewControllerManagedBy(mgr). + For(&apiextensionsv1.CustomResourceDefinition{}, + // This controller uses a PartialObjectMetadata watch/informer to avoid an informer for CRDs + // to reduce memory usage. + // Core CAPI also already has an informer on PartialObjectMetadata for CRDs because it uses + // conversion.UpdateReferenceAPIContract. + builder.OnlyMetadata, + builder.WithPredicates( + // We filter out all re-sync events. CRDMigrator only has to reconcile a CRD + // if the CRD actually changed, e.g. changes in apiVersions. + predicates.ResourceIsChanged(mgr.GetScheme(), predicateLog), + ), + ). + Named("crdmigrator"). + WithOptions(controllerOptions). + Complete(r) + if err != nil { + return errors.Wrap(err, "failed setting up with a controller manager") + } + + return nil +} + +func (r *CRDMigrator) setup(scheme *runtime.Scheme) error { + if r.Client == nil || r.APIReader == nil || len(r.Config) == 0 { + return errors.New("Client and APIReader must not be nil and Config must not be empty") + } + + r.crdMigrationPhasesToRun = sets.Set[Phase]{}.Insert(StorageVersionMigrationPhase, CleanupManagedFieldsPhase) + for _, skipPhase := range r.SkipCRDMigrationPhases { + switch skipPhase { + case StorageVersionMigrationPhase: + r.crdMigrationPhasesToRun.Delete(StorageVersionMigrationPhase) + case CleanupManagedFieldsPhase: + r.crdMigrationPhasesToRun.Delete(CleanupManagedFieldsPhase) + default: + return errors.Errorf("Invalid phase %s specified in SkipCRDMigrationPhases", skipPhase) + } + } + + r.configByCRDName = map[string]ByObjectConfig{} + for obj, cfg := range r.Config { + gvk, err := apiutil.GVKForObject(obj, scheme) + if err != nil { + return errors.Wrap(err, "failed to get GVK for object") + } + + r.configByCRDName[contract.CalculateCRDName(gvk.Group, gvk.Kind)] = cfg + } + + r.storageVersionMigrationCache = cache.New[objectEntry](1 * time.Hour) + return nil +} + +func (r *CRDMigrator) Reconcile(ctx context.Context, req ctrl.Request) (_ ctrl.Result, reterr error) { + migrationConfig, ok := r.configByCRDName[req.Name] + if !ok { + // If there is no migrationConfig for this CRD, do nothing. + return ctrl.Result{}, nil + } + + crdPartial := &metav1.PartialObjectMetadata{} + crdPartial.SetGroupVersionKind(apiextensionsv1.SchemeGroupVersion.WithKind("CustomResourceDefinition")) + if err := r.Client.Get(ctx, req.NamespacedName, crdPartial); err != nil { + return ctrl.Result{}, client.IgnoreNotFound(err) + } + + currentGeneration := strconv.FormatInt(crdPartial.GetGeneration(), 10) + if observedGeneration, ok := crdPartial.Annotations[clusterv1.CRDMigrationObservedGenerationAnnotation]; ok && + currentGeneration == observedGeneration { + // If the current generation was already reconciled/observed, do nothing. + return ctrl.Result{}, nil + } + + crd := &apiextensionsv1.CustomResourceDefinition{} + if err := r.APIReader.Get(ctx, req.NamespacedName, crd); err != nil { + return ctrl.Result{}, client.IgnoreNotFound(err) + } + // Note: The CRD might have a newer generation than PartialObjectMeta above, we should use the + // generation of the CRD we actually use for reconciliation. + currentGeneration = strconv.FormatInt(crd.GetGeneration(), 10) + + storageVersion, err := storageVersionForCRD(crd) + if err != nil { + return ctrl.Result{}, err + } + + defer func() { + if reterr == nil { + originalCRD := crd.DeepCopy() + if crd.Annotations == nil { + crd.Annotations = map[string]string{} + } + crd.Annotations[clusterv1.CRDMigrationObservedGenerationAnnotation] = currentGeneration + // Note: Optimistic locking is not required here, because if the CRD and its apiVersions was changed + // in the meantime, we'll reconcile it again with the next generation. + if err := r.Client.Patch(ctx, crd, client.MergeFrom(originalCRD)); err != nil { + reterr = kerrors.NewAggregate([]error{reterr, errors.Wrapf(err, "failed to patch CustomResourceDefinition %s", crd.Name)}) + } + } + }() + + var customResourceObjects []client.Object + if r.crdMigrationPhasesToRun.Has(StorageVersionMigrationPhase) && storageVersionMigrationRequired(crd, storageVersion) || + r.crdMigrationPhasesToRun.Has(CleanupManagedFieldsPhase) { + // Get CustomResources only if we actually are going to run one of the phases. + // Note: This relies on that the version that is storageVersion is also served. + var err error + customResourceObjects, err = r.listCustomResources(ctx, crd, migrationConfig, storageVersion) + if err != nil { + return ctrl.Result{}, err + } + } + + // If phase should be run and .status.storedVersions != [storageVersion], run storage version migration. + if r.crdMigrationPhasesToRun.Has(StorageVersionMigrationPhase) && storageVersionMigrationRequired(crd, storageVersion) { + if err := r.reconcileStorageVersionMigration(ctx, crd, migrationConfig, customResourceObjects, storageVersion); err != nil { + return ctrl.Result{}, err + } + + originalCRD := crd.DeepCopy() + crd.Status.StoredVersions = []string{storageVersion} + // Note: Using optimistic locking to ensure the CRD and its apiVersions was not changed in the meantime. + if err := r.Client.Status().Patch(ctx, crd, client.MergeFromWithOptions(originalCRD, client.MergeFromWithOptimisticLock{})); err != nil { + return ctrl.Result{}, errors.Wrapf(err, "failed to patch CustomResourceDefinition %s", crd.Name) + } + } + + if r.crdMigrationPhasesToRun.Has(CleanupManagedFieldsPhase) { + if err := r.reconcileCleanupManagedFields(ctx, crd, customResourceObjects, migrationConfig, storageVersion); err != nil { + return ctrl.Result{}, err + } + } + + return ctrl.Result{}, nil +} + +func storageVersionForCRD(crd *apiextensionsv1.CustomResourceDefinition) (string, error) { + for _, v := range crd.Spec.Versions { + if v.Storage { + return v.Name, nil + } + } + + return "", errors.Errorf("could not find storage version for CustomResourceDefinition %s", crd.Name) +} + +func storageVersionMigrationRequired(crd *apiextensionsv1.CustomResourceDefinition, storageVersion string) bool { + if len(crd.Status.StoredVersions) == 1 && crd.Status.StoredVersions[0] == storageVersion { + return false + } + return true +} + +func (r *CRDMigrator) listCustomResources(ctx context.Context, crd *apiextensionsv1.CustomResourceDefinition, migrationConfig ByObjectConfig, storageVersion string) ([]client.Object, error) { + var objs []client.Object + + listGVK := schema.GroupVersionKind{ + Group: crd.Spec.Group, + Version: storageVersion, + Kind: crd.Spec.Names.ListKind, + } + + if migrationConfig.UseCache { + // Note: We should only use the cached client with a typed object list. + // Otherwise we would create an additional informer for an UnstructuredList/PartialObjectMetadataList. + object, err := r.Client.Scheme().New(listGVK) + if err != nil { + return nil, errors.Wrapf(err, "failed to list %s: failed to create %s object", crd.Spec.Names.Kind, crd.Spec.Names.ListKind) + } + objectList, ok := object.(client.ObjectList) + if !ok { + return nil, errors.Wrapf(err, "failed to list %s: %s object is not an ObjectList", crd.Spec.Names.Kind, crd.Spec.Names.ListKind) + } + objects, err := listObjectsFromCachedClient(ctx, r.Client, objectList) + if err != nil { + return nil, errors.Wrapf(err, "failed to list %s via cached client", crd.Spec.Names.Kind) + } + objs = append(objs, objects...) + } else { + // Note: As the APIReader won't create an informer we can use PartialObjectMetadataList. + // PartialObjectMetadataList is used instead of UnstructuredList to avoid retrieving unnecessary data. + objectList := &metav1.PartialObjectMetadataList{} + objectList.SetGroupVersionKind(listGVK) + objects, err := listObjectsFromAPIReader(ctx, r.APIReader, objectList) + if err != nil { + return nil, errors.Wrapf(err, "failed to list %s via live client", crd.Spec.Names.Kind) + } + objs = append(objs, objects...) + } + + return objs, nil +} + +func listObjectsFromCachedClient(ctx context.Context, c client.Client, objectList client.ObjectList) ([]client.Object, error) { + objs := []client.Object{} + + // Note: No pagination needed as we are just reading from the cached client. + if err := c.List(ctx, objectList); err != nil { + return nil, err + } + + objectListItems, err := meta.ExtractList(objectList) + if err != nil { + return nil, errors.Wrapf(err, "failed to extract list items") + } + for _, obj := range objectListItems { + objs = append(objs, obj.(client.Object)) + } + + return objs, nil +} + +func listObjectsFromAPIReader(ctx context.Context, c client.Reader, objectList client.ObjectList) ([]client.Object, error) { + objs := []client.Object{} + + for { + listOpts := []client.ListOption{ + client.Continue(objectList.GetContinue()), + client.Limit(500), + } + if err := c.List(ctx, objectList, listOpts...); err != nil { + return nil, err + } + + objectListItems, err := meta.ExtractList(objectList) + if err != nil { + return nil, errors.Wrapf(err, "failed to extract list items") + } + for _, obj := range objectListItems { + objs = append(objs, obj.(client.Object)) + } + + if objectList.GetContinue() == "" { + break + } + } + + return objs, nil +} + +func (r *CRDMigrator) reconcileStorageVersionMigration(ctx context.Context, crd *apiextensionsv1.CustomResourceDefinition, migrationConfig ByObjectConfig, customResourceObjects []client.Object, storageVersion string) error { + if len(customResourceObjects) == 0 { + return nil + } + + log := ctrl.LoggerFrom(ctx) + log.Info(fmt.Sprintf("Running storage version migration to apiVersion %s (for %d objects)", storageVersion, len(customResourceObjects))) + + gvk := schema.GroupVersionKind{ + Group: crd.Spec.Group, + Version: storageVersion, + Kind: crd.Spec.Names.Kind, + } + + errs := []error{} + for _, obj := range customResourceObjects { + e := objectEntry{ + Kind: gvk.Kind, + ObjectKey: client.ObjectKeyFromObject(obj), + // Note: We also have to set the generation of the CRD to ensure we actually run the migration + // on the latest state of the CRD. + CRDGeneration: crd.Generation, + } + + if _, alreadyMigrated := r.storageVersionMigrationCache.Has(e.Key()); alreadyMigrated { + // Refresh the cache entry, so that we don't try to migrate the storage version for CRs that were + // already migrated successfully in cases where storage migrations failed for a subset of the CRs. + r.storageVersionMigrationCache.Add(e) + continue + } + + // Based on: https://github.com/kubernetes/kubernetes/blob/v1.32.0/pkg/controller/storageversionmigrator/storageversionmigrator.go#L275-L284 + u := &unstructured.Unstructured{} + u.SetGroupVersionKind(gvk) + u.SetNamespace(obj.GetNamespace()) + u.SetName(obj.GetName()) + // Set UID so that when a resource gets deleted, we get an "uid mismatch" + // conflict error instead of trying to create it. + u.SetUID(obj.GetUID()) + // Set RV so that when a resources gets updated or deleted+recreated, we get an "object has been modified" + // conflict error. We do not actually need to do this for the updated case because if RV + // was not set, it would just result in no-op request. But for the deleted+recreated case, if RV is + // not set but UID is set, we would get an immutable field validation error. Hence we must set both. + u.SetResourceVersion(obj.GetResourceVersion()) + + log.V(4).Info("Migrating to new storage version", gvk.Kind, klog.KObj(u)) + var err error + if migrationConfig.UseStatusForStorageVersionMigration { + err = r.Client.Status().Patch(ctx, u, client.Apply, client.FieldOwner("crdmigrator")) + } else { + err = r.Client.Patch(ctx, u, client.Apply, client.FieldOwner("crdmigrator")) + } + // If we got a NotFound error, the object no longer exists so no need to update it. + // If we got a Conflict error, another client wrote the object already so no need to update it. + if err != nil && !apierrors.IsNotFound(err) && !apierrors.IsConflict(err) { + errs = append(errs, errors.Wrap(err, klog.KObj(u).String())) + continue + } + + r.storageVersionMigrationCache.Add(e) + } + + if len(errs) > 0 { + return errors.Wrapf(kerrors.NewAggregate(errs), "failed to migrate storage version of %s objects", gvk.Kind) + } + + return nil +} + +func (r *CRDMigrator) reconcileCleanupManagedFields(ctx context.Context, crd *apiextensionsv1.CustomResourceDefinition, customResourceObjects []client.Object, migrationConfig ByObjectConfig, storageVersion string) error { + if len(customResourceObjects) == 0 { + return nil + } + + log := ctrl.LoggerFrom(ctx) + log.Info(fmt.Sprintf("Running managedField cleanup (for %d objects)", len(customResourceObjects))) + + // Collect all GroupVersions that still exist and are served. + servedGroupVersions := sets.Set[string]{} + for _, v := range crd.Spec.Versions { + if v.Served { + servedGroupVersions.Insert(fmt.Sprintf("%s/%s", crd.Spec.Group, v.Name)) + } + } + + errs := []error{} + for _, obj := range customResourceObjects { + if len(obj.GetManagedFields()) == 0 { + continue + } + + var getErr error + if err := retry.RetryOnConflict(retry.DefaultRetry, func() error { + getErr = nil + + managedFields, removed := removeManagedFieldsWithNotServedGroupVersion(obj, servedGroupVersions) + if !removed { + return nil + } + + if len(managedFields) == 0 { + // Add a seeding managedFieldEntry for SSA to prevent SSA to create/infer a default managedFieldEntry + // when the first SSA is applied. + // More specifically, if an existing object doesn't have managedFields when applying the first SSA + // the API server creates an entry with operation=Update (kind of guessing where the object comes from), + // but this entry ends up acting as a co-ownership and we want to prevent this. + // NOTE: fieldV1Map cannot be empty, so we add metadata.name which will be cleaned up at the first + // SSA patch of the same fieldManager. + // NOTE: We use the fieldManager and operation from the managedFields that we remove to increase the + // chances that the managedField entry gets cleaned up. In any case having a minimal entry only + // for metadata.name is better than leaving the old entry that uses an apiVersion that is not + // served anymore (see: https://github.com/kubernetes/kubernetes/issues/111937). + fieldV1Map := map[string]interface{}{ + "f:metadata": map[string]interface{}{ + "f:name": map[string]interface{}{}, + }, + } + fieldV1, err := json.Marshal(fieldV1Map) + if err != nil { + return errors.Wrap(err, "failed to create seeding managedField entry") + } + managedFields = append(managedFields, metav1.ManagedFieldsEntry{ + Manager: obj.GetManagedFields()[0].Manager, + Operation: obj.GetManagedFields()[0].Operation, + APIVersion: schema.GroupVersion{Group: crd.Spec.Group, Version: storageVersion}.String(), + Time: ptr.To(metav1.Now()), + FieldsType: "FieldsV1", + FieldsV1: &metav1.FieldsV1{Raw: fieldV1}, + }) + } + + // Create a patch to update only managedFields. + // Include resourceVersion to avoid race conditions. + jsonPatch := []map[string]interface{}{ + { + "op": "replace", + "path": "/metadata/managedFields", + "value": managedFields, + }, + { + "op": "replace", + "path": "/metadata/resourceVersion", + "value": obj.GetResourceVersion(), + }, + } + patch, err := json.Marshal(jsonPatch) + if err != nil { + return errors.Wrap(err, "failed to marshal patch") + } + + log.V(4).Info("Cleaning up managedFields", crd.Spec.Names.Kind, klog.KObj(obj)) + err = r.Client.Patch(ctx, obj, client.RawPatch(types.JSONPatchType, patch)) + // If the resource no longer exists, the managedFields don't have to be cleaned up anymore. + if err == nil || apierrors.IsNotFound(err) { + return nil + } + + if apierrors.IsConflict(err) { + if migrationConfig.UseCache { + getErr = r.Client.Get(ctx, client.ObjectKeyFromObject(obj), obj) + } else { + getErr = r.APIReader.Get(ctx, client.ObjectKeyFromObject(obj), obj) + } + } + // Note: We always have to return the conflict error directly (instead of an aggregate) so retry on conflict works. + return err + }); err != nil { + errs = append(errs, errors.Wrap(kerrors.NewAggregate([]error{err, getErr}), klog.KObj(obj).String())) + continue + } + } + + if len(errs) > 0 { + return errors.Wrapf(kerrors.NewAggregate(errs), "failed to cleanup managedFields of %s objects", crd.Spec.Names.Kind) + } + + return nil +} + +func removeManagedFieldsWithNotServedGroupVersion(obj client.Object, servedGroupVersions sets.Set[string]) ([]metav1.ManagedFieldsEntry, bool) { + removedManagedFields := false + managedFields := []metav1.ManagedFieldsEntry{} + for _, managedField := range obj.GetManagedFields() { + if servedGroupVersions.Has(managedField.APIVersion) { + managedFields = append(managedFields, managedField) + continue + } + + removedManagedFields = true + } + + return managedFields, removedManagedFields +} + +type objectEntry struct { + Kind string + client.ObjectKey + CRDGeneration int64 +} + +func (r objectEntry) Key() string { + return fmt.Sprintf("%s %s %d", r.Kind, r.ObjectKey.String(), r.CRDGeneration) +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/cluster_cache_tracker.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/cluster_cache_tracker.go index a52687d1525..a93b709aa15 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/cluster_cache_tracker.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/cluster_cache_tracker.go @@ -514,7 +514,7 @@ func (t *ClusterCacheTracker) createCachedClient(ctx context.Context, config *re // Use a context that is independent of the passed in context, so the cache doesn't get stopped // when the passed in context is canceled. - cacheCtx, cacheCtxCancel := context.WithCancel(context.Background()) + cacheCtx, cacheCtxCancel := context.WithCancelCause(context.Background()) // We need to be able to stop the cache's shared informers, so wrap this in a stoppableCache. cache := &stoppableCache{ @@ -547,7 +547,7 @@ func (t *ClusterCacheTracker) createCachedClient(ctx context.Context, config *re go cache.Start(cacheCtx) //nolint:errcheck // Wait until the cache is initially synced - cacheSyncCtx, cacheSyncCtxCancel := context.WithTimeout(ctx, initialCacheSyncTimeout) + cacheSyncCtx, cacheSyncCtxCancel := context.WithTimeoutCause(ctx, initialCacheSyncTimeout, errors.New("initial sync timeout expired")) defer cacheSyncCtxCancel() if !cache.WaitForCacheSync(cacheSyncCtx) { cache.Stop() @@ -774,13 +774,13 @@ type clientWithTimeout struct { var _ client.Client = &clientWithTimeout{} func (c clientWithTimeout) Get(ctx context.Context, key client.ObjectKey, obj client.Object, opts ...client.GetOption) error { - ctx, cancel := context.WithTimeout(ctx, c.timeout) + ctx, cancel := context.WithTimeoutCause(ctx, c.timeout, errors.New("call timeout expired")) defer cancel() return c.Client.Get(ctx, key, obj, opts...) } func (c clientWithTimeout) List(ctx context.Context, list client.ObjectList, opts ...client.ListOption) error { - ctx, cancel := context.WithTimeout(ctx, c.timeout) + ctx, cancel := context.WithTimeoutCause(ctx, c.timeout, errors.New("call timeout expired")) defer cancel() return c.Client.List(ctx, list, opts...) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/stoppable_cache.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/stoppable_cache.go index 5c72f26aeac..d81a0dd4b80 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/stoppable_cache.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controllers/remote/stoppable_cache.go @@ -20,6 +20,7 @@ import ( "context" "sync" + "github.com/pkg/errors" "sigs.k8s.io/controller-runtime/pkg/cache" ) @@ -29,7 +30,7 @@ type stoppableCache struct { lock sync.Mutex stopped bool - cancelFunc context.CancelFunc + cancelFunc context.CancelCauseFunc } // Stop cancels the cache.Cache's context, unless it has already been stopped. @@ -42,5 +43,5 @@ func (cc *stoppableCache) Stop() { } cc.stopped = true - cc.cancelFunc() + cc.cancelFunc(errors.New("cache stopped")) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadm_control_plane_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadm_control_plane_types.go index ae85a68d616..0ab5d5d499a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadm_control_plane_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadm_control_plane_types.go @@ -29,6 +29,7 @@ import ( ) // RolloutStrategyType defines the rollout strategies for a KubeadmControlPlane. +// +kubebuilder:validation:Enum=RollingUpdate type RolloutStrategyType string const ( @@ -78,7 +79,7 @@ const ( // KubeadmControlPlaneSpec defines the desired state of KubeadmControlPlane. type KubeadmControlPlaneSpec struct { - // Number of desired machines. Defaults to 1. When stacked etcd is used only + // replicas is the number of desired machines. Defaults to 1. When stacked etcd is used only // odd numbers are permitted, as per [etcd best practice](https://etcd.io/docs/v3.3.12/faq/#why-an-odd-number-of-cluster-members). // This is a pointer to distinguish between explicit zero and not specified. // +optional @@ -90,14 +91,19 @@ type KubeadmControlPlaneSpec struct { // Please use a newer patch version with the new registry instead. The default registries of kubeadm are: // * registry.k8s.io (new registry): >= v1.22.17, >= v1.23.15, >= v1.24.9, >= v1.25.0 // * k8s.gcr.io (old registry): all older versions + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Version string `json:"version"` // machineTemplate contains information about how machines // should be shaped when creating or updating a control plane. + // +required MachineTemplate KubeadmControlPlaneMachineTemplate `json:"machineTemplate"` // kubeadmConfigSpec is a KubeadmConfigSpec // to use for initializing and joining machines to the control plane. + // +required KubeadmConfigSpec bootstrapv1.KubeadmConfigSpec `json:"kubeadmConfigSpec"` // rolloutBefore is a field to indicate a rollout should be performed @@ -114,17 +120,17 @@ type KubeadmControlPlaneSpec struct { // +optional RolloutAfter *metav1.Time `json:"rolloutAfter,omitempty"` - // The RolloutStrategy to use to replace control plane machines with + // rolloutStrategy is the RolloutStrategy to use to replace control plane machines with // new ones. // +optional // +kubebuilder:default={type: "RollingUpdate", rollingUpdate: {maxSurge: 1}} RolloutStrategy *RolloutStrategy `json:"rolloutStrategy,omitempty"` - // The RemediationStrategy that controls how control plane machine remediation happens. + // remediationStrategy is the RemediationStrategy that controls how control plane machine remediation happens. // +optional RemediationStrategy *RemediationStrategy `json:"remediationStrategy,omitempty"` - // MachineNamingStrategy allows changing the naming pattern used when creating Machines. + // machineNamingStrategy allows changing the naming pattern used when creating Machines. // InfraMachines & KubeadmConfigs will use the same name as the corresponding Machines. // +optional MachineNamingStrategy *MachineNamingStrategy `json:"machineNamingStrategy,omitempty"` @@ -133,15 +139,31 @@ type KubeadmControlPlaneSpec struct { // KubeadmControlPlaneMachineTemplate defines the template for Machines // in a KubeadmControlPlane object. type KubeadmControlPlaneMachineTemplate struct { - // Standard object's metadata. + // metadata is the standard object's metadata. // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata // +optional ObjectMeta clusterv1.ObjectMeta `json:"metadata,omitempty"` // infrastructureRef is a required reference to a custom resource // offered by an infrastructure provider. + // +required InfrastructureRef corev1.ObjectReference `json:"infrastructureRef"` + // readinessGates specifies additional conditions to include when evaluating Machine Ready condition; + // KubeadmControlPlane will always add readinessGates for the condition it is setting on the Machine: + // APIServerPodHealthy, SchedulerPodHealthy, ControllerManagerPodHealthy, and if etcd is managed by CKP also + // EtcdPodHealthy, EtcdMemberHealthy. + // + // This field can be used e.g. to instruct the machine controller to include in the computation for Machine's ready + // computation a condition, managed by an external controllers, reporting the status of special software/hardware installed on the Machine. + // + // NOTE: This field is considered only for computing v1beta2 conditions. + // +optional + // +listType=map + // +listMapKey=conditionType + // +kubebuilder:validation:MaxItems=32 + ReadinessGates []clusterv1.MachineReadinessGate `json:"readinessGates,omitempty"` + // nodeDrainTimeout is the total amount of time that the controller will spend on draining a controlplane node // The default value is 0, meaning that the node can be drained without any time limitations. // NOTE: NodeDrainTimeout is different from `kubectl drain --timeout` @@ -177,7 +199,7 @@ type RolloutStrategy struct { // +optional Type RolloutStrategyType `json:"type,omitempty"` - // Rolling update config params. Present only if + // rollingUpdate is the rolling update config params. Present only if // RolloutStrategyType = RollingUpdate. // +optional RollingUpdate *RollingUpdate `json:"rollingUpdate,omitempty"` @@ -185,7 +207,7 @@ type RolloutStrategy struct { // RollingUpdate is used to control the desired behavior of rolling update. type RollingUpdate struct { - // The maximum number of control planes that can be scheduled above or under the + // maxSurge is the maximum number of control planes that can be scheduled above or under the // desired number of control planes. // Value can be an absolute number 1 or 0. // Defaults to 1. @@ -242,7 +264,7 @@ type RemediationStrategy struct { // MachineNamingStrategy allows changing the naming pattern used when creating Machines. // InfraMachines & KubeadmConfigs will use the same name as the corresponding Machines. type MachineNamingStrategy struct { - // Template defines the template to use for generating the names of the Machine objects. + // template defines the template to use for generating the names of the Machine objects. // If not defined, it will fallback to `{{ .kubeadmControlPlane.name }}-{{ .random }}`. // If the generated name string exceeds 63 characters, it will be trimmed to 58 characters and will // get concatenated with a random suffix of length 5. @@ -250,8 +272,10 @@ type MachineNamingStrategy struct { // The template allows the following variables `.cluster.name`, `.kubeadmControlPlane.name` and `.random`. // The variable `.cluster.name` retrieves the name of the cluster object that owns the Machines being created. // The variable `.kubeadmControlPlane.name` retrieves the name of the KubeadmControlPlane object that owns the Machines being created. - // The variable `.random` is substituted with random alphanumeric string, without vowels, of length 5. + // The variable `.random` is substituted with random alphanumeric string, without vowels, of length 5. This variable is required + // part of the template. If not provided, validation will fail. // +optional + // +kubebuilder:validation:MinLength=1 // +kubebuilder:validation:MaxLength=256 Template string `json:"template,omitempty"` } @@ -264,9 +288,11 @@ type KubeadmControlPlaneStatus struct { // describe.. The string will be in the same format as the query-param syntax. // More info about label selectors: http://kubernetes.io/docs/user-guide/labels#label-selectors // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=4096 Selector string `json:"selector,omitempty"` - // Total number of non-terminated machines targeted by this control plane + // replicas is the total number of non-terminated machines targeted by this control plane // (their labels match the selector). // +optional Replicas int32 `json:"replicas"` @@ -274,18 +300,20 @@ type KubeadmControlPlaneStatus struct { // version represents the minimum Kubernetes version for the control plane machines // in the cluster. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=256 Version *string `json:"version,omitempty"` - // Total number of non-terminated machines targeted by this control plane + // updatedReplicas is the total number of non-terminated machines targeted by this control plane // that have the desired template spec. // +optional UpdatedReplicas int32 `json:"updatedReplicas"` - // Total number of fully running and ready control plane machines. + // readyReplicas is the total number of fully running and ready control plane machines. // +optional ReadyReplicas int32 `json:"readyReplicas"` - // Total number of unavailable machines targeted by this control plane. + // unavailableReplicas is the total number of unavailable machines targeted by this control plane. // This is the total number of machines that are still required for // the deployment to have 100% available capacity. They may either // be machines that are running but not yet ready or machines @@ -321,12 +349,14 @@ type KubeadmControlPlaneStatus struct { // +optional FailureReason errors.KubeadmControlPlaneStatusError `json:"failureReason,omitempty"` - // ErrorMessage indicates that there is a terminal problem reconciling the + // failureMessage indicates that there is a terminal problem reconciling the // state, and will be set to a descriptive error message. // // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 FailureMessage *string `json:"failureMessage,omitempty"` // observedGeneration is the latest generation observed by the controller. @@ -376,13 +406,18 @@ type KubeadmControlPlaneV1Beta2Status struct { // more remediations than expected might happen. type LastRemediationStatus struct { // machine is the machine name of the latest machine being remediated. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=253 Machine string `json:"machine"` // timestamp is when last remediation happened. It is represented in RFC3339 form and is in UTC. + // +required Timestamp metav1.Time `json:"timestamp"` // retryCount used to keep track of remediation retry for the last remediated machine. // A retry happens when a machine that was created as a replacement for an unhealthy machine also fails. + // +required RetryCount int32 `json:"retryCount"` } @@ -404,10 +439,17 @@ type LastRemediationStatus struct { // KubeadmControlPlane is the Schema for the KubeadmControlPlane API. type KubeadmControlPlane struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec KubeadmControlPlaneSpec `json:"spec,omitempty"` + // spec is the desired state of KubeadmControlPlane. + // +optional + Spec KubeadmControlPlaneSpec `json:"spec,omitempty"` + // status is the observed state of KubeadmControlPlane. + // +optional Status KubeadmControlPlaneStatus `json:"status,omitempty"` } @@ -442,8 +484,12 @@ func (in *KubeadmControlPlane) SetV1Beta2Conditions(conditions []metav1.Conditio // KubeadmControlPlaneList contains a list of KubeadmControlPlane. type KubeadmControlPlaneList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []KubeadmControlPlane `json:"items"` + // items is the list of KubeadmControlPlanes. + Items []KubeadmControlPlane `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadmcontrolplanetemplate_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadmcontrolplanetemplate_types.go index 122acb24c5a..09d9f0f0515 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadmcontrolplanetemplate_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/kubeadmcontrolplanetemplate_types.go @@ -25,6 +25,8 @@ import ( // KubeadmControlPlaneTemplateSpec defines the desired state of KubeadmControlPlaneTemplate. type KubeadmControlPlaneTemplateSpec struct { + // template defines the desired state of KubeadmControlPlaneTemplate. + // +required Template KubeadmControlPlaneTemplateResource `json:"template"` } @@ -35,9 +37,14 @@ type KubeadmControlPlaneTemplateSpec struct { // KubeadmControlPlaneTemplate is the Schema for the kubeadmcontrolplanetemplates API. type KubeadmControlPlaneTemplate struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` + // spec is the desired state of KubeadmControlPlaneTemplate. + // +optional Spec KubeadmControlPlaneTemplateSpec `json:"spec,omitempty"` } @@ -46,8 +53,12 @@ type KubeadmControlPlaneTemplate struct { // KubeadmControlPlaneTemplateList contains a list of KubeadmControlPlaneTemplate. type KubeadmControlPlaneTemplateList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []KubeadmControlPlaneTemplate `json:"items"` + // items is the list of KubeadmControlPlaneTemplates. + Items []KubeadmControlPlaneTemplate `json:"items"` } func init() { @@ -56,11 +67,13 @@ func init() { // KubeadmControlPlaneTemplateResource describes the data needed to create a KubeadmControlPlane from a template. type KubeadmControlPlaneTemplateResource struct { - // Standard object's metadata. + // metadata is the standard object's metadata. // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata // +optional ObjectMeta clusterv1.ObjectMeta `json:"metadata,omitempty"` + // spec is the desired state of KubeadmControlPlaneTemplateResource. + // +required Spec KubeadmControlPlaneTemplateResourceSpec `json:"spec"` } @@ -77,6 +90,7 @@ type KubeadmControlPlaneTemplateResourceSpec struct { // kubeadmConfigSpec is a KubeadmConfigSpec // to use for initializing and joining machines to the control plane. + // +required KubeadmConfigSpec bootstrapv1.KubeadmConfigSpec `json:"kubeadmConfigSpec"` // rolloutBefore is a field to indicate a rollout should be performed @@ -92,17 +106,17 @@ type KubeadmControlPlaneTemplateResourceSpec struct { // +optional RolloutAfter *metav1.Time `json:"rolloutAfter,omitempty"` - // The RolloutStrategy to use to replace control plane machines with + // rolloutStrategy is the RolloutStrategy to use to replace control plane machines with // new ones. // +optional // +kubebuilder:default={type: "RollingUpdate", rollingUpdate: {maxSurge: 1}} RolloutStrategy *RolloutStrategy `json:"rolloutStrategy,omitempty"` - // The RemediationStrategy that controls how control plane machine remediation happens. + // remediationStrategy is the RemediationStrategy that controls how control plane machine remediation happens. // +optional RemediationStrategy *RemediationStrategy `json:"remediationStrategy,omitempty"` - // MachineNamingStrategy allows changing the naming pattern used when creating Machines. + // machineNamingStrategy allows changing the naming pattern used when creating Machines. // InfraMachines & KubeadmConfigs will use the same name as the corresponding Machines. // +optional MachineNamingStrategy *MachineNamingStrategy `json:"machineNamingStrategy,omitempty"` @@ -115,7 +129,7 @@ type KubeadmControlPlaneTemplateResourceSpec struct { // because they are calculated by the Cluster topology reconciler during reconciliation and thus cannot // be configured on the KubeadmControlPlaneTemplate. type KubeadmControlPlaneTemplateMachineTemplate struct { - // Standard object's metadata. + // metadata is the standard object's metadata. // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata // +optional ObjectMeta clusterv1.ObjectMeta `json:"metadata,omitempty"` diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/zz_generated.deepcopy.go index 46cd8278d46..b6d41c20e60 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/controlplane/kubeadm/api/v1beta1/zz_generated.deepcopy.go @@ -91,6 +91,11 @@ func (in *KubeadmControlPlaneMachineTemplate) DeepCopyInto(out *KubeadmControlPl *out = *in in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) out.InfrastructureRef = in.InfrastructureRef + if in.ReadinessGates != nil { + in, out := &in.ReadinessGates, &out.ReadinessGates + *out = make([]apiv1beta1.MachineReadinessGate, len(*in)) + copy(*out, *in) + } if in.NodeDrainTimeout != nil { in, out := &in.NodeDrainTimeout, &out.NodeDrainTimeout *out = new(v1.Duration) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/api/v1beta1/machinepool_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/api/v1beta1/machinepool_types.go index cc8e4561bd0..be97236182d 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/api/v1beta1/machinepool_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/api/v1beta1/machinepool_types.go @@ -34,18 +34,21 @@ const ( // MachinePoolSpec defines the desired state of MachinePool. type MachinePoolSpec struct { // clusterName is the name of the Cluster this object belongs to. + // +required // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName"` - // Number of desired machines. Defaults to 1. + // replicas is the number of desired machines. Defaults to 1. // This is a pointer to distinguish between explicit zero and not specified. // +optional Replicas *int32 `json:"replicas,omitempty"` // template describes the machines that will be created. + // +required Template clusterv1.MachineTemplateSpec `json:"template"` - // Minimum number of seconds for which a newly created machine instances should + // minReadySeconds is the minimum number of seconds for which a newly created machine instances should // be ready. // Defaults to 0 (machine instance will be considered available as soon as it // is ready) @@ -55,10 +58,16 @@ type MachinePoolSpec struct { // providerIDList are the identification IDs of machine instances provided by the provider. // This field must match the provider IDs as seen on the node objects corresponding to a machine pool's machine instances. // +optional + // +kubebuilder:validation:MaxItems=10000 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=512 ProviderIDList []string `json:"providerIDList,omitempty"` // failureDomains is the list of failure domains this MachinePool should be attached to. // +optional + // +kubebuilder:validation:MaxItems=100 + // +kubebuilder:validation:items:MinLength=1 + // +kubebuilder:validation:items:MaxLength=256 FailureDomains []string `json:"failureDomains,omitempty"` } @@ -70,21 +79,22 @@ type MachinePoolSpec struct { type MachinePoolStatus struct { // nodeRefs will point to the corresponding Nodes if it they exist. // +optional + // +kubebuilder:validation:MaxItems=10000 NodeRefs []corev1.ObjectReference `json:"nodeRefs,omitempty"` // replicas is the most recently observed number of replicas. // +optional Replicas int32 `json:"replicas"` - // The number of ready replicas for this MachinePool. A machine is considered ready when the node has been created and is "Ready". + // readyReplicas is the number of ready replicas for this MachinePool. A machine is considered ready when the node has been created and is "Ready". // +optional ReadyReplicas int32 `json:"readyReplicas,omitempty"` - // The number of available replicas (ready for at least minReadySeconds) for this MachinePool. + // availableReplicas is the number of available replicas (ready for at least minReadySeconds) for this MachinePool. // +optional AvailableReplicas int32 `json:"availableReplicas,omitempty"` - // Total number of unavailable machine instances targeted by this machine pool. + // unavailableReplicas is the total number of unavailable machine instances targeted by this machine pool. // This is the total number of machine instances that are still required for // the machine pool to have 100% available capacity. They may either // be machine instances that are running but not yet available or machine instances @@ -109,11 +119,13 @@ type MachinePoolStatus struct { // Deprecated: This field is deprecated and is going to be removed in the next apiVersion. Please see https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more details. // // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=10240 FailureMessage *string `json:"failureMessage,omitempty"` // phase represents the current phase of cluster actuation. - // E.g. Pending, Running, Terminating, Failed etc. // +optional + // +kubebuilder:validation:Enum=Pending;Provisioning;Provisioned;Running;ScalingUp;ScalingDown;Scaling;Deleting;Failed;Unknown Phase string `json:"phase,omitempty"` // bootstrapReady is the state of the bootstrap provider. @@ -259,10 +271,17 @@ func (m *MachinePoolStatus) GetTypedPhase() MachinePoolPhase { // MachinePool is the Schema for the machinepools API. type MachinePool struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec MachinePoolSpec `json:"spec,omitempty"` + // spec is the desired state of MachinePool. + // +optional + Spec MachinePoolSpec `json:"spec,omitempty"` + // status is the observed state of MachinePool. + // +optional Status MachinePoolStatus `json:"status,omitempty"` } @@ -297,8 +316,12 @@ func (m *MachinePool) SetV1Beta2Conditions(conditions []metav1.Condition) { // MachinePoolList contains a list of MachinePool. type MachinePoolList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []MachinePool `json:"items"` + // items is the list of MachinePools. + Items []MachinePool `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddress_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddress_types.go index fd69f033f5b..8410bf08f79 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddress_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddress_types.go @@ -24,19 +24,27 @@ import ( // IPAddressSpec is the desired state of an IPAddress. type IPAddressSpec struct { // claimRef is a reference to the claim this IPAddress was created for. + // +required ClaimRef corev1.LocalObjectReference `json:"claimRef"` // poolRef is a reference to the pool that this IPAddress was created from. + // +required PoolRef corev1.TypedLocalObjectReference `json:"poolRef"` // address is the IP address. + // +required + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=39 Address string `json:"address"` // prefix is the prefix of the address. + // +required Prefix int `json:"prefix"` // gateway is the network gateway of the network the address is from. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=39 Gateway string `json:"gateway,omitempty"` } @@ -50,9 +58,14 @@ type IPAddressSpec struct { // IPAddress is the Schema for the ipaddress API. type IPAddress struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` + // spec is the desired state of IPAddress. + // +optional Spec IPAddressSpec `json:"spec,omitempty"` } @@ -61,8 +74,12 @@ type IPAddress struct { // IPAddressList is a list of IPAddress. type IPAddressList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []IPAddress `json:"items"` + // items is the list of IPAddresses. + Items []IPAddress `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddressclaim_types.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddressclaim_types.go index 2e136196d1e..635df232c67 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddressclaim_types.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/ipaddressclaim_types.go @@ -27,9 +27,12 @@ import ( type IPAddressClaimSpec struct { // clusterName is the name of the Cluster this object belongs to. // +optional + // +kubebuilder:validation:MinLength=1 + // +kubebuilder:validation:MaxLength=63 ClusterName string `json:"clusterName,omitempty"` // poolRef is a reference to the pool from which an IP address should be created. + // +required PoolRef corev1.TypedLocalObjectReference `json:"poolRef"` } @@ -42,6 +45,21 @@ type IPAddressClaimStatus struct { // conditions summarises the current state of the IPAddressClaim // +optional Conditions clusterv1.Conditions `json:"conditions,omitempty"` + + // v1beta2 groups all the fields that will be added or modified in IPAddressClaim's status with the V1Beta2 version. + // +optional + V1Beta2 *IPAddressClaimV1Beta2Status `json:"v1beta2,omitempty"` +} + +// IPAddressClaimV1Beta2Status groups all the fields that will be added or modified in IPAddressClaimStatus with the V1Beta2 version. +// See https://github.com/kubernetes-sigs/cluster-api/blob/main/docs/proposals/20240916-improve-status-in-CAPI-resources.md for more context. +type IPAddressClaimV1Beta2Status struct { + // conditions represents the observations of a IPAddressClaim's current state. + // +optional + // +listType=map + // +listMapKey=type + // +kubebuilder:validation:MaxItems=32 + Conditions []metav1.Condition `json:"conditions,omitempty"` } // +kubebuilder:object:root=true @@ -54,10 +72,17 @@ type IPAddressClaimStatus struct { // IPAddressClaim is the Schema for the ipaddressclaim API. type IPAddressClaim struct { - metav1.TypeMeta `json:",inline"` + metav1.TypeMeta `json:",inline"` + // metadata is the standard object's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#metadata + // +optional metav1.ObjectMeta `json:"metadata,omitempty"` - Spec IPAddressClaimSpec `json:"spec,omitempty"` + // spec is the desired state of IPAddressClaim. + // +optional + Spec IPAddressClaimSpec `json:"spec,omitempty"` + // status is the observed state of IPAddressClaim. + // +optional Status IPAddressClaimStatus `json:"status,omitempty"` } @@ -71,13 +96,33 @@ func (m *IPAddressClaim) SetConditions(conditions clusterv1.Conditions) { m.Status.Conditions = conditions } +// GetV1Beta2Conditions returns the set of conditions for this object. +func (m *IPAddressClaim) GetV1Beta2Conditions() []metav1.Condition { + if m.Status.V1Beta2 == nil { + return nil + } + return m.Status.V1Beta2.Conditions +} + +// SetV1Beta2Conditions sets conditions for an API object. +func (m *IPAddressClaim) SetV1Beta2Conditions(conditions []metav1.Condition) { + if m.Status.V1Beta2 == nil { + m.Status.V1Beta2 = &IPAddressClaimV1Beta2Status{} + } + m.Status.V1Beta2.Conditions = conditions +} + // +kubebuilder:object:root=true // IPAddressClaimList is a list of IPAddressClaims. type IPAddressClaimList struct { metav1.TypeMeta `json:",inline"` + // metadata is the standard list's metadata. + // More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#lists-and-simple-kinds + // +optional metav1.ListMeta `json:"metadata,omitempty"` - Items []IPAddressClaim `json:"items"` + // items is the list of IPAddressClaims. + Items []IPAddressClaim `json:"items"` } func init() { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/zz_generated.deepcopy.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/zz_generated.deepcopy.go index ef05c5b2fc8..338a238c266 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/zz_generated.deepcopy.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/exp/ipam/api/v1beta1/zz_generated.deepcopy.go @@ -21,6 +21,7 @@ limitations under the License. package v1beta1 import ( + "k8s.io/apimachinery/pkg/apis/meta/v1" "k8s.io/apimachinery/pkg/runtime" apiv1beta1 "sigs.k8s.io/cluster-api/api/v1beta1" ) @@ -137,6 +138,11 @@ func (in *IPAddressClaimStatus) DeepCopyInto(out *IPAddressClaimStatus) { (*in)[i].DeepCopyInto(&(*out)[i]) } } + if in.V1Beta2 != nil { + in, out := &in.V1Beta2, &out.V1Beta2 + *out = new(IPAddressClaimV1Beta2Status) + (*in).DeepCopyInto(*out) + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new IPAddressClaimStatus. @@ -149,6 +155,28 @@ func (in *IPAddressClaimStatus) DeepCopy() *IPAddressClaimStatus { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *IPAddressClaimV1Beta2Status) DeepCopyInto(out *IPAddressClaimV1Beta2Status) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]v1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new IPAddressClaimV1Beta2Status. +func (in *IPAddressClaimV1Beta2Status) DeepCopy() *IPAddressClaimV1Beta2Status { + if in == nil { + return nil + } + out := new(IPAddressClaimV1Beta2Status) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *IPAddressList) DeepCopyInto(out *IPAddressList) { *out = *in diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/feature/feature.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/feature/feature.go index 9d1af07ab35..15a6fb169b4 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/feature/feature.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/feature/feature.go @@ -39,6 +39,9 @@ const ( // // alpha: v0.3 // beta: v0.4 + // GA: v1.10 + // + // Deprecated: ClusterResourceSet feature is now GA and the corresponding feature flag will be removed in 1.12 release. ClusterResourceSet featuregate.Feature = "ClusterResourceSet" // ClusterTopology is a feature gate for the ClusterClass and managed topologies functionality. @@ -68,6 +71,12 @@ const ( // // beta: v1.9 MachineWaitForVolumeDetachConsiderVolumeAttachments featuregate.Feature = "MachineWaitForVolumeDetachConsiderVolumeAttachments" + + // PriorityQueue is a feature gate that controls if the controller uses the controller-runtime PriorityQueue + // instead of the default queue implementation. + // + // alpha: v1.10 + PriorityQueue featuregate.Feature = "PriorityQueue" ) func init() { @@ -78,10 +87,11 @@ func init() { // To add a new feature, define a key for it above and add it here. var defaultClusterAPIFeatureGates = map[featuregate.Feature]featuregate.FeatureSpec{ // Every feature should be initiated here: - ClusterResourceSet: {Default: true, PreRelease: featuregate.Beta}, + ClusterResourceSet: {Default: true, PreRelease: featuregate.GA}, MachinePool: {Default: true, PreRelease: featuregate.Beta}, MachineSetPreflightChecks: {Default: true, PreRelease: featuregate.Beta}, MachineWaitForVolumeDetachConsiderVolumeAttachments: {Default: true, PreRelease: featuregate.Beta}, + PriorityQueue: {Default: false, PreRelease: featuregate.Alpha}, ClusterTopology: {Default: false, PreRelease: featuregate.Alpha}, KubeadmBootstrapFormatIgnition: {Default: false, PreRelease: featuregate.Alpha}, RuntimeSDK: {Default: false, PreRelease: featuregate.Alpha}, diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/annotations/helpers.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/annotations/helpers.go index e4990032b45..964609ac97a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/annotations/helpers.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/annotations/helpers.go @@ -18,6 +18,7 @@ limitations under the License. package annotations import ( + "regexp" "strings" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" @@ -88,6 +89,36 @@ func AddAnnotations(o metav1.Object, desired map[string]string) bool { return hasChanged } +// GetManagedAnnotations filters out and returns the CAPI-managed annotations for a Machine, with an optional list of regex patterns for user-specified annotations. +func GetManagedAnnotations(m *clusterv1.Machine, additionalSyncMachineAnnotations ...*regexp.Regexp) map[string]string { + // Always sync CAPI's bookkeeping annotations + managedAnnotations := map[string]string{ + clusterv1.ClusterNameAnnotation: m.Spec.ClusterName, + clusterv1.ClusterNamespaceAnnotation: m.GetNamespace(), + clusterv1.MachineAnnotation: m.Name, + } + if owner := metav1.GetControllerOfNoCopy(m); owner != nil { + managedAnnotations[clusterv1.OwnerKindAnnotation] = owner.Kind + managedAnnotations[clusterv1.OwnerNameAnnotation] = owner.Name + } + for key, value := range m.GetAnnotations() { + // Always sync CAPI's default annotation node domain + dnsSubdomainOrName := strings.Split(key, "/")[0] + if dnsSubdomainOrName == clusterv1.ManagedNodeAnnotationDomain || strings.HasSuffix(dnsSubdomainOrName, "."+clusterv1.ManagedNodeAnnotationDomain) { + managedAnnotations[key] = value + continue + } + // Sync if the annotations matches at least one user provided regex + for _, regex := range additionalSyncMachineAnnotations { + if regex.MatchString(key) { + managedAnnotations[key] = value + break + } + } + } + return managedAnnotations +} + // hasAnnotation returns true if the object has the specified annotation. func hasAnnotation(o metav1.Object, annotation string) bool { annotations := o.GetAnnotations() diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/cache.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/cache.go new file mode 100644 index 00000000000..31ec3e2c17d --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/cache.go @@ -0,0 +1,149 @@ +/* +Copyright 2024 The Kubernetes Authors. + +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 cache + +import ( + "time" + + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/types" + kcache "k8s.io/client-go/tools/cache" + ctrl "sigs.k8s.io/controller-runtime" +) + +const ( + // DefaultTTL is the duration for which we keep entries in the cache. + DefaultTTL = 10 * time.Minute + + // expirationInterval is the interval in which we will remove expired entries + // from the cache. + expirationInterval = 10 * time.Hour +) + +// Entry is the interface for the type of Cache entries. +type Entry interface { + // Key returns the cache key of an Entry. + Key() string +} + +// Cache caches objects of type Entry. +type Cache[E Entry] interface { + // Add adds the given entry to the Cache. + // Note: entries expire after the ttl. + Add(entry E) + + // Has checks if the given key (still) exists in the Cache. + // Note: entries expire after the ttl. + Has(key string) (E, bool) +} + +// New creates a new cache. +// ttl is the duration for which we keep entries in the cache. +func New[E Entry](ttl time.Duration) Cache[E] { + r := &cache[E]{ + Store: kcache.NewTTLStore(func(obj interface{}) (string, error) { + // We only add objects of type E to the cache, so it's safe to cast to E. + return obj.(E).Key(), nil + }, ttl), + } + go func() { + for { + // Call list to clear the cache of expired items. + // We have to do this periodically as the cache itself only expires + // items lazily. If we don't do this the cache grows indefinitely. + r.List() + + time.Sleep(expirationInterval) + } + }() + return r +} + +type cache[E Entry] struct { + kcache.Store +} + +// Add adds the given entry to the Cache. +// Note: entries expire after the ttl. +func (r *cache[E]) Add(entry E) { + // Note: We can ignore the error here because the key func we pass into NewTTLStore never + // returns errors. + _ = r.Store.Add(entry) +} + +// Has checks if the given key (still) exists in the Cache. +// Note: entries expire after the ttl. +func (r *cache[E]) Has(key string) (E, bool) { + // Note: We can ignore the error here because GetByKey never returns an error. + item, exists, _ := r.Store.GetByKey(key) + if exists { + return item.(E), true + } + return *new(E), false +} + +// ReconcileEntry is an Entry for the Cache that stores the +// earliest time after which the next Reconcile should be executed. +type ReconcileEntry struct { + Request ctrl.Request + ReconcileAfter time.Time +} + +// NewReconcileEntry creates a new ReconcileEntry based on an object and a reconcileAfter time. +func NewReconcileEntry(obj metav1.Object, reconcileAfter time.Time) ReconcileEntry { + return ReconcileEntry{ + Request: ctrl.Request{ + NamespacedName: types.NamespacedName{ + Namespace: obj.GetNamespace(), + Name: obj.GetName(), + }, + }, + ReconcileAfter: reconcileAfter, + } +} + +// NewReconcileEntryKey returns the key of a ReconcileEntry based on an object. +func NewReconcileEntryKey(obj metav1.Object) string { + return ReconcileEntry{ + Request: ctrl.Request{ + NamespacedName: types.NamespacedName{ + Namespace: obj.GetNamespace(), + Name: obj.GetName(), + }, + }, + }.Key() +} + +var _ Entry = &ReconcileEntry{} + +// Key returns the cache key of a ReconcileEntry. +func (r ReconcileEntry) Key() string { + return r.Request.String() +} + +// ShouldRequeue returns if the current Reconcile should be requeued. +func (r ReconcileEntry) ShouldRequeue(now time.Time) (requeueAfter time.Duration, requeue bool) { + if r.ReconcileAfter.IsZero() { + return time.Duration(0), false + } + + if r.ReconcileAfter.After(now) { + return r.ReconcileAfter.Sub(now), true + } + + return time.Duration(0), false +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/doc.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/doc.go new file mode 100644 index 00000000000..be95d4e8027 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/cache/doc.go @@ -0,0 +1,18 @@ +/* +Copyright 2024 The Kubernetes Authors. + +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 cache implements some cache utils. +package cache diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/collections/machine_collection.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/collections/machine_collection.go index a8c686a8a97..ed8686810d2 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/collections/machine_collection.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/collections/machine_collection.go @@ -123,6 +123,16 @@ func ToMachineList(machines Machines) clusterv1.MachineList { return ml } +// Has return true when the collection has the given machine. +func (s Machines) Has(machine *clusterv1.Machine) bool { + for _, m := range s { + if m.Name == machine.Name && m.Namespace == machine.Namespace { + return true + } + } + return false +} + // Insert adds items to the set. func (s Machines) Insert(machines ...*clusterv1.Machine) { for i := range machines { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/aggregate.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/aggregate.go index 3a3615a2896..892fd9a9ce3 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/aggregate.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/aggregate.go @@ -110,7 +110,7 @@ func NewAggregateCondition[T Getter](sourceObjs []T, sourceConditionType string, } } - status, reason, message, err := aggregateOpt.mergeStrategy.Merge(conditionsInScope, []string{sourceConditionType}) + status, reason, message, err := aggregateOpt.mergeStrategy.Merge(AggregateMergeOperation, conditionsInScope, []string{sourceConditionType}) if err != nil { return nil, err } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/merge_strategies.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/merge_strategies.go index f51cd2e882d..1d45e6c271c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/merge_strategies.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/merge_strategies.go @@ -51,6 +51,19 @@ func (o ConditionOwnerInfo) String() string { return fmt.Sprintf("%s %s", o.Kind, o.Name) } +// MergeOperation defines merge operations. +type MergeOperation string + +const ( + // SummaryMergeOperation defines a merge operation of type Summary. + // Summary should merge different conditions from the same object. + SummaryMergeOperation MergeOperation = "Summary" + + // AggregateMergeOperation defines a merge operation of type Aggregate. + // Aggregate should merge the same condition across many objects. + AggregateMergeOperation MergeOperation = "Aggregate" +) + // MergeStrategy defines a strategy used to merge conditions during the aggregate or summary operation. type MergeStrategy interface { // Merge passed in conditions. @@ -59,7 +72,7 @@ type MergeStrategy interface { // Conditions passed in must be of the given conditionTypes (other condition types must be discarded). // // The list of conditionTypes has an implicit order; it is up to the implementation of merge to use this info or not. - Merge(conditions []ConditionWithOwnerInfo, conditionTypes []string) (status metav1.ConditionStatus, reason, message string, err error) + Merge(operation MergeOperation, conditions []ConditionWithOwnerInfo, conditionTypes []string) (status metav1.ConditionStatus, reason, message string, err error) } // DefaultMergeStrategyOption is some configuration that modifies the DefaultMergeStrategy behaviour. @@ -199,7 +212,7 @@ type defaultMergeStrategy struct { // - issues: conditions with positive polarity (normal True) and status False or conditions with negative polarity (normal False) and status True. // - unknown: conditions with status unknown. // - info: conditions with positive polarity (normal True) and status True or conditions with negative polarity (normal False) and status False. -func (d *defaultMergeStrategy) Merge(conditions []ConditionWithOwnerInfo, conditionTypes []string) (status metav1.ConditionStatus, reason, message string, err error) { +func (d *defaultMergeStrategy) Merge(operation MergeOperation, conditions []ConditionWithOwnerInfo, conditionTypes []string) (status metav1.ConditionStatus, reason, message string, err error) { if len(conditions) == 0 { return "", "", "", errors.New("can't merge an empty list of conditions") } @@ -208,15 +221,6 @@ func (d *defaultMergeStrategy) Merge(conditions []ConditionWithOwnerInfo, condit return "", "", "", errors.New("can't merge without a getPriority func") } - // Infer which operation is calling this func, so it is possible to use different strategies for computing the message for the target condition. - // - When merge should consider a single condition type, we can assume this func is called within an aggregate operation - // (Aggregate should merge the same condition across many objects) - isAggregateOperation := len(conditionTypes) == 1 - - // - Otherwise we can assume this func is called within a summary operation - // (Summary should merge different conditions from the same object) - isSummaryOperation := !isAggregateOperation - // sortConditions the relevance defined by the users (the order of condition types), LastTransition time (older first). sortConditions(conditions, conditionTypes) @@ -265,7 +269,7 @@ func (d *defaultMergeStrategy) Merge(conditions []ConditionWithOwnerInfo, condit // // When including messages from conditions, they are sorted by issue/unknown and by the implicit order of condition types // provided by the user (it is considered as order of relevance). - if isSummaryOperation { + if operation == SummaryMergeOperation { message = summaryMessage(conditions, d, status) } @@ -291,7 +295,7 @@ func (d *defaultMergeStrategy) Merge(conditions []ConditionWithOwnerInfo, condit // // e.g. ...; 2 more Objects with issues; 1 more Objects with unknown status // - if isAggregateOperation { + if operation == AggregateMergeOperation { n := 3 messages := []string{} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/patch.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/patch.go index 4c94286b8f9..939ff41ff01 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/patch.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/patch.go @@ -243,3 +243,12 @@ func HasSameState(i, j *metav1.Condition) bool { i.Reason == j.Reason && i.Message == j.Message } + +// HasSameStateExceptObservedGeneration returns true if a condition has the same state of another; state is defined +// by the union of following fields: Type, Status, Reason and Message (it excludes ObservedGeneration and LastTransitionTime). +func HasSameStateExceptObservedGeneration(i, j *metav1.Condition) bool { + return i.Type == j.Type && + i.Status == j.Status && + i.Reason == j.Reason && + i.Message == j.Message +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/summary.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/summary.go index d7a08463d66..beb5fd461a7 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/summary.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/conditions/v1beta2/summary.go @@ -137,7 +137,7 @@ func NewSummaryCondition(sourceObj Getter, targetConditionType string, opts ...S return nil, errors.New("summary can't be performed when the list of conditions to be summarized is empty") } - status, reason, message, err := summarizeOpt.mergeStrategy.Merge(conditionsInScope, summarizeOpt.conditionTypes) + status, reason, message, err := summarizeOpt.mergeStrategy.Merge(SummaryMergeOperation, conditionsInScope, summarizeOpt.conditionTypes) if err != nil { return nil, err } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/finalizers/finalizers.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/finalizers/finalizers.go new file mode 100644 index 00000000000..2e351dd8e72 --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/finalizers/finalizers.go @@ -0,0 +1,55 @@ +/* +Copyright 2024 The Kubernetes Authors. + +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 finalizers implements finalizer helper functions. +package finalizers + +import ( + "context" + + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" + + "sigs.k8s.io/cluster-api/util/patch" +) + +// EnsureFinalizer adds a finalizer if the object doesn't have a deletionTimestamp set +// and if the finalizer is not already set. +// This util is usually used in reconcilers directly after the reconciled object was retrieved +// and before pause is handled or "defer patch" with the patch helper. +func EnsureFinalizer(ctx context.Context, c client.Client, o client.Object, finalizer string) (finalizerAdded bool, err error) { + // Finalizers can only be added when the deletionTimestamp is not set. + if !o.GetDeletionTimestamp().IsZero() { + return false, nil + } + + if controllerutil.ContainsFinalizer(o, finalizer) { + return false, nil + } + + patchHelper, err := patch.NewHelper(o, c) + if err != nil { + return false, err + } + + controllerutil.AddFinalizer(o, finalizer) + + if err := patchHelper.Patch(ctx, o); err != nil { + return false, err + } + + return true, nil +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/labels/helpers.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/labels/helpers.go index c13ee48e1e1..d88bd8be16a 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/labels/helpers.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/labels/helpers.go @@ -18,6 +18,9 @@ limitations under the License. package labels import ( + "regexp" + "strings" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" @@ -52,3 +55,33 @@ func HasWatchLabel(o metav1.Object, labelValue string) bool { } return val == labelValue } + +// GetManagedLabels returns the set of labels managed by CAPI, with an optional list of regex patterns for user-specified labels. +func GetManagedLabels(labels map[string]string, additionalSyncMachineLabels ...*regexp.Regexp) map[string]string { + managedLabels := make(map[string]string) + for key, value := range labels { + // Always sync the default set of labels. + dnsSubdomainOrName := strings.Split(key, "/")[0] + if dnsSubdomainOrName == clusterv1.NodeRoleLabelPrefix { + managedLabels[key] = value + continue + } + if dnsSubdomainOrName == clusterv1.NodeRestrictionLabelDomain || strings.HasSuffix(dnsSubdomainOrName, "."+clusterv1.NodeRestrictionLabelDomain) { + managedLabels[key] = value + continue + } + if dnsSubdomainOrName == clusterv1.ManagedNodeLabelDomain || strings.HasSuffix(dnsSubdomainOrName, "."+clusterv1.ManagedNodeLabelDomain) { + managedLabels[key] = value + continue + } + + // Sync if the labels matches at least one user provided regex. + for _, regex := range additionalSyncMachineLabels { + if regex.MatchString(key) { + managedLabels[key] = value + break + } + } + } + return managedLabels +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/patch/patch.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/patch/patch.go index ad8d0e53118..73e60f253d3 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/patch/patch.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/patch/patch.go @@ -84,16 +84,9 @@ func NewHelper(obj client.Object, crClient client.Client) (*Helper, error) { return nil, errors.Wrapf(err, "failed to identify condition fields for object %s", klog.KObj(obj)) } - // Convert the object to unstructured to compare against our before copy. - unstructuredObj, err := toUnstructured(obj, gvk) - if err != nil { - return nil, errors.Wrapf(err, "failed to create patch helper for %s %s: failed to convert object to Unstructured", gvk.Kind, klog.KObj(obj)) - } - return &Helper{ client: crClient, gvk: gvk, - before: unstructuredObj, beforeObject: obj.DeepCopyObject().(client.Object), metav1ConditionsFieldPath: metav1ConditionsFieldPath, clusterv1ConditionsFieldPath: clusterv1ConditionsFieldPath, @@ -138,10 +131,16 @@ func (h *Helper) Patch(ctx context.Context, obj client.Object, opts ...Option) e h.metav1ConditionsFieldPath = nil } - // Convert the object to unstructured to compare against our before copy. + // Convert the before object to unstructured. + h.before, err = toUnstructured(h.beforeObject, gvk) + if err != nil { + return errors.Wrapf(err, "failed to patch %s %s: failed to convert before object to Unstructured", h.gvk.Kind, klog.KObj(h.beforeObject)) + } + + // Convert the after object to unstructured. h.after, err = toUnstructured(obj, gvk) if err != nil { - return errors.Wrapf(err, "failed to patch %s %s: failed to convert object to Unstructured", h.gvk.Kind, klog.KObj(h.beforeObject)) + return errors.Wrapf(err, "failed to patch %s %s: failed to convert after object to Unstructured", h.gvk.Kind, klog.KObj(h.beforeObject)) } // Determine if the object has status. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/paused/paused.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/paused/paused.go new file mode 100644 index 00000000000..e5d401c435b --- /dev/null +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/paused/paused.go @@ -0,0 +1,122 @@ +/* +Copyright 2024 The Kubernetes Authors. + +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 paused implements paused helper functions. +package paused + +import ( + "context" + "fmt" + "strings" + + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/runtime" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/client/apiutil" + + clusterv1 "sigs.k8s.io/cluster-api/api/v1beta1" + "sigs.k8s.io/cluster-api/util/annotations" + v1beta2conditions "sigs.k8s.io/cluster-api/util/conditions/v1beta2" + "sigs.k8s.io/cluster-api/util/patch" +) + +// ConditionSetter combines the client.Object and Setter interface. +type ConditionSetter interface { + v1beta2conditions.Setter + client.Object +} + +// EnsurePausedCondition sets the paused condition on the object and returns if it should be considered as paused. +func EnsurePausedCondition(ctx context.Context, c client.Client, cluster *clusterv1.Cluster, obj ConditionSetter) (isPaused bool, requeue bool, err error) { + oldCondition := v1beta2conditions.Get(obj, clusterv1.PausedV1Beta2Condition) + newCondition := pausedCondition(c.Scheme(), cluster, obj, clusterv1.PausedV1Beta2Condition) + + isPaused = newCondition.Status == metav1.ConditionTrue + pausedStatusChanged := oldCondition == nil || oldCondition.Status != newCondition.Status + + log := ctrl.LoggerFrom(ctx) + + switch { + case pausedStatusChanged && isPaused: + log.V(4).Info("Pausing reconciliation for this object", "reason", newCondition.Message) + case pausedStatusChanged && !isPaused: + log.V(4).Info("Unpausing reconciliation for this object") + case !pausedStatusChanged && isPaused: + log.V(6).Info("Reconciliation is paused for this object", "reason", newCondition.Message) + } + + if oldCondition != nil { + // Return early if the paused condition did not change at all. + if v1beta2conditions.HasSameState(oldCondition, &newCondition) { + return isPaused, false, nil + } + + // Set condition and return early if only observed generation changed and obj is not paused. + // In this case we want to avoid the additional reconcile that we would get by requeueing. + if v1beta2conditions.HasSameStateExceptObservedGeneration(oldCondition, &newCondition) && !isPaused { + v1beta2conditions.Set(obj, newCondition) + return isPaused, false, nil + } + } + + patchHelper, err := patch.NewHelper(obj, c) + if err != nil { + return isPaused, false, err + } + + v1beta2conditions.Set(obj, newCondition) + + if err := patchHelper.Patch(ctx, obj, patch.WithOwnedV1Beta2Conditions{Conditions: []string{ + clusterv1.PausedV1Beta2Condition, + }}); err != nil { + return isPaused, false, err + } + + return isPaused, true, nil +} + +// pausedCondition sets the paused condition on the object and returns if it should be considered as paused. +func pausedCondition(scheme *runtime.Scheme, cluster *clusterv1.Cluster, obj ConditionSetter, targetConditionType string) metav1.Condition { + if (cluster != nil && cluster.Spec.Paused) || annotations.HasPaused(obj) { + var messages []string + if cluster != nil && cluster.Spec.Paused { + messages = append(messages, "Cluster spec.paused is set to true") + } + if annotations.HasPaused(obj) { + kind := "Object" + if gvk, err := apiutil.GVKForObject(obj, scheme); err == nil { + kind = gvk.Kind + } + messages = append(messages, fmt.Sprintf("%s has the cluster.x-k8s.io/paused annotation", kind)) + } + + return metav1.Condition{ + Type: targetConditionType, + Status: metav1.ConditionTrue, + Reason: clusterv1.PausedV1Beta2Reason, + Message: strings.Join(messages, ", "), + ObservedGeneration: obj.GetGeneration(), + } + } + + return metav1.Condition{ + Type: targetConditionType, + Status: metav1.ConditionFalse, + Reason: clusterv1.NotPausedV1Beta2Reason, + ObservedGeneration: obj.GetGeneration(), + } +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/cluster_predicates.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/cluster_predicates.go index adc6ca65997..57dec27cb91 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/cluster_predicates.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/cluster_predicates.go @@ -341,3 +341,46 @@ func processIfTopologyManaged(scheme *runtime.Scheme, logger logr.Logger, object logger.V(6).Info("Cluster does not have topology, blocking further processing") return false } + +// ClusterTopologyVersionChanged returns a Predicate that returns true when cluster.Spec.Topology.Version +// was changed. +func ClusterTopologyVersionChanged(scheme *runtime.Scheme, logger logr.Logger) predicate.Funcs { + return predicate.Funcs{ + UpdateFunc: func(e event.UpdateEvent) bool { + logger := logger.WithValues("predicate", "ClusterTopologyVersionChanged", "eventType", "update") + if gvk, err := apiutil.GVKForObject(e.ObjectOld, scheme); err == nil { + logger = logger.WithValues(gvk.Kind, klog.KObj(e.ObjectOld)) + } + + oldCluster, ok := e.ObjectOld.(*clusterv1.Cluster) + if !ok { + logger.V(4).Info("Expected Cluster", "type", fmt.Sprintf("%T", e.ObjectOld)) + return false + } + + newCluster := e.ObjectNew.(*clusterv1.Cluster) + + if oldCluster.Spec.Topology == nil || newCluster.Spec.Topology == nil { + logger.V(6).Info("Cluster does not have topology, blocking further processing") + return false + } + + if oldCluster.Spec.Topology.Version != newCluster.Spec.Topology.Version { + logger.V(6).Info("Cluster topology version has changed, allowing further processing") + return true + } + + logger.V(6).Info("Cluster topology version has not changed, blocking further processing") + return false + }, + CreateFunc: func(_ event.CreateEvent) bool { + return false + }, + DeleteFunc: func(_ event.DeleteEvent) bool { + return false + }, + GenericFunc: func(_ event.GenericEvent) bool { + return false + }, + } +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/generic_predicates.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/generic_predicates.go index fe170f846f7..84d8071ebe8 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/generic_predicates.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/predicates/generic_predicates.go @@ -31,8 +31,13 @@ import ( // All returns a predicate that returns true only if all given predicates return true. func All(scheme *runtime.Scheme, logger logr.Logger, predicates ...predicate.Funcs) predicate.Funcs { - return predicate.Funcs{ - UpdateFunc: func(e event.UpdateEvent) bool { + return TypedAll(scheme, logger, predicates...) +} + +// TypedAll returns a predicate that returns true only if all given predicates return true. +func TypedAll[T client.Object](scheme *runtime.Scheme, logger logr.Logger, predicates ...predicate.TypedFuncs[T]) predicate.TypedFuncs[T] { + return predicate.TypedFuncs[T]{ + UpdateFunc: func(e event.TypedUpdateEvent[T]) bool { log := logger.WithValues("predicateAggregation", "All") if gvk, err := apiutil.GVKForObject(e.ObjectNew, scheme); err == nil { log = log.WithValues(gvk.Kind, klog.KObj(e.ObjectNew)) @@ -46,7 +51,7 @@ func All(scheme *runtime.Scheme, logger logr.Logger, predicates ...predicate.Fun log.V(6).Info("All provided predicates returned true, allowing further processing") return true }, - CreateFunc: func(e event.CreateEvent) bool { + CreateFunc: func(e event.TypedCreateEvent[T]) bool { log := logger.WithValues("predicateAggregation", "All") if gvk, err := apiutil.GVKForObject(e.Object, scheme); err == nil { log = log.WithValues(gvk.Kind, klog.KObj(e.Object)) @@ -60,7 +65,7 @@ func All(scheme *runtime.Scheme, logger logr.Logger, predicates ...predicate.Fun log.V(6).Info("All provided predicates returned true, allowing further processing") return true }, - DeleteFunc: func(e event.DeleteEvent) bool { + DeleteFunc: func(e event.TypedDeleteEvent[T]) bool { log := logger.WithValues("predicateAggregation", "All") if gvk, err := apiutil.GVKForObject(e.Object, scheme); err == nil { log = log.WithValues(gvk.Kind, klog.KObj(e.Object)) @@ -74,7 +79,7 @@ func All(scheme *runtime.Scheme, logger logr.Logger, predicates ...predicate.Fun log.V(6).Info("All provided predicates returned true, allowing further processing") return true }, - GenericFunc: func(e event.GenericEvent) bool { + GenericFunc: func(e event.TypedGenericEvent[T]) bool { log := logger.WithValues("predicateAggregation", "All") if gvk, err := apiutil.GVKForObject(e.Object, scheme); err == nil { log = log.WithValues(gvk.Kind, klog.KObj(e.Object)) @@ -303,3 +308,33 @@ func processIfTopologyOwned(scheme *runtime.Scheme, logger logr.Logger, obj clie logger.V(6).Info("Resource is not topology owned, will not attempt to map resource") return false } + +// ResourceIsChanged returns a predicate that returns true only if the resource +// has changed. This predicate allows to drop resync events on additionally watched objects. +func ResourceIsChanged(scheme *runtime.Scheme, logger logr.Logger) predicate.Funcs { + return TypedResourceIsChanged[client.Object](scheme, logger) +} + +// TypedResourceIsChanged returns a predicate that returns true only if the resource +// has changed. This predicate allows to drop resync events on additionally watched objects. +func TypedResourceIsChanged[T client.Object](scheme *runtime.Scheme, logger logr.Logger) predicate.TypedFuncs[T] { + log := logger.WithValues("predicate", "ResourceIsChanged") + return predicate.TypedFuncs[T]{ + UpdateFunc: func(e event.TypedUpdateEvent[T]) bool { + // Ensure we don't modify log from above. + log := log + if gvk, err := apiutil.GVKForObject(e.ObjectNew, scheme); err == nil { + log = log.WithValues(gvk.Kind, klog.KObj(e.ObjectNew)) + } + if e.ObjectOld.GetResourceVersion() == e.ObjectNew.GetResourceVersion() { + log.WithValues("eventType", "update").V(6).Info("Resource is not changed, will not attempt to map resource") + return false + } + log.WithValues("eventType", "update").V(6).Info("Resource is changed, will attempt to map resource") + return true + }, + CreateFunc: func(event.TypedCreateEvent[T]) bool { return true }, + DeleteFunc: func(event.TypedDeleteEvent[T]) bool { return true }, + GenericFunc: func(event.TypedGenericEvent[T]) bool { return true }, + } +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/util.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/util.go index b5a5b6b946b..dfe38100ef8 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/util.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/cluster-api/util/util.go @@ -39,6 +39,7 @@ import ( "k8s.io/apimachinery/pkg/runtime/schema" "k8s.io/apimachinery/pkg/types" k8sversion "k8s.io/apimachinery/pkg/version" + "k8s.io/utils/ptr" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/client" "sigs.k8s.io/controller-runtime/pkg/client/apiutil" @@ -334,6 +335,21 @@ func RemoveOwnerRef(ownerReferences []metav1.OwnerReference, inputRef metav1.Own return ownerReferences } +// HasExactOwnerRef returns true if the exact OwnerReference is already in the slice. +// It matches based on APIVersion, Kind, Name and Controller. +func HasExactOwnerRef(ownerReferences []metav1.OwnerReference, ref metav1.OwnerReference) bool { + for _, r := range ownerReferences { + if r.APIVersion == ref.APIVersion && + r.Kind == ref.Kind && + r.Name == ref.Name && + r.UID == ref.UID && + ptr.Deref(r.Controller, false) == ptr.Deref(ref.Controller, false) { + return true + } + } + return false +} + // indexOwnerRef returns the index of the owner reference in the slice if found, or -1. func indexOwnerRef(ownerReferences []metav1.OwnerReference, ref metav1.OwnerReference) int { for index, r := range ownerReferences { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/Makefile b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/Makefile index 0406fc8a60a..2361df981d9 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/Makefile +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/Makefile @@ -27,7 +27,7 @@ SHELL:=/usr/bin/env bash # # Go. # -GO_VERSION ?= 1.23.2 +GO_VERSION ?= 1.23.0 # Use GOPROXY environment variable if set GOPROXY := $(shell go env GOPROXY) @@ -88,7 +88,7 @@ GO_APIDIFF_PKG := github.com/joelanford/go-apidiff $(GO_APIDIFF): # Build go-apidiff from tools folder. GOBIN=$(TOOLS_BIN_DIR) $(GO_INSTALL) $(GO_APIDIFF_PKG) $(GO_APIDIFF_BIN) $(GO_APIDIFF_VER) -CONTROLLER_GEN_VER := v0.14.0 +CONTROLLER_GEN_VER := v0.17.1 CONTROLLER_GEN_BIN := controller-gen CONTROLLER_GEN := $(abspath $(TOOLS_BIN_DIR)/$(CONTROLLER_GEN_BIN)-$(CONTROLLER_GEN_VER)) CONTROLLER_GEN_PKG := sigs.k8s.io/controller-tools/cmd/controller-gen @@ -174,7 +174,7 @@ release-binary: $(RELEASE_DIR) -v "$$(pwd):/workspace$(DOCKER_VOL_OPTS)" \ -w /workspace/tools/setup-envtest \ golang:$(GO_VERSION) \ - go build -a -trimpath -ldflags "-extldflags '-static'" \ + go build -a -trimpath -ldflags "-X 'sigs.k8s.io/controller-runtime/tools/setup-envtest/version.version=$(RELEASE_TAG)' -extldflags '-static'" \ -o ./out/$(RELEASE_BINARY) ./ ## -------------------------------------- diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/builder/controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/builder/controller.go index 0760953e026..6d906f6e52c 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/builder/controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/builder/controller.go @@ -163,7 +163,7 @@ func (blder *TypedBuilder[request]) Watches( ) *TypedBuilder[request] { input := WatchesInput[request]{ obj: object, - handler: handler.WithLowPriorityWhenUnchanged(eventHandler), + handler: eventHandler, } for _, opt := range opts { opt.ApplyToWatches(&input) @@ -317,7 +317,7 @@ func (blder *TypedBuilder[request]) doWatch() error { } var hdler handler.TypedEventHandler[client.Object, request] - reflect.ValueOf(&hdler).Elem().Set(reflect.ValueOf(handler.WithLowPriorityWhenUnchanged(&handler.EnqueueRequestForObject{}))) + reflect.ValueOf(&hdler).Elem().Set(reflect.ValueOf(&handler.EnqueueRequestForObject{})) allPredicates := append([]predicate.Predicate(nil), blder.globalPredicates...) allPredicates = append(allPredicates, blder.forInput.predicates...) src := source.TypedKind(blder.mgr.GetCache(), obj, hdler, allPredicates...) @@ -341,11 +341,11 @@ func (blder *TypedBuilder[request]) doWatch() error { } var hdler handler.TypedEventHandler[client.Object, request] - reflect.ValueOf(&hdler).Elem().Set(reflect.ValueOf(handler.WithLowPriorityWhenUnchanged(handler.EnqueueRequestForOwner( + reflect.ValueOf(&hdler).Elem().Set(reflect.ValueOf(handler.EnqueueRequestForOwner( blder.mgr.GetScheme(), blder.mgr.GetRESTMapper(), blder.forInput.object, opts..., - )))) + ))) allPredicates := append([]predicate.Predicate(nil), blder.globalPredicates...) allPredicates = append(allPredicates, own.predicates...) src := source.TypedKind(blder.mgr.GetCache(), obj, hdler, allPredicates...) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/cache/multi_namespace_cache.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/cache/multi_namespace_cache.go index da69f40f65e..aeeeb66937b 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/cache/multi_namespace_cache.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/cache/multi_namespace_cache.go @@ -262,6 +262,9 @@ func (c *multiNamespaceCache) List(ctx context.Context, list client.ObjectList, if listOpts.Namespace != corev1.NamespaceAll { cache, ok := c.namespaceToCache[listOpts.Namespace] if !ok { + if global, hasGlobal := c.namespaceToCache[AllNamespaces]; hasGlobal { + return global.List(ctx, list, opts...) + } return fmt.Errorf("unable to list: %v because of unknown namespace for the cache", listOpts.Namespace) } return cache.List(ctx, list, opts...) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/apiutil/restmapper.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/apiutil/restmapper.go index ad898617fa9..7a7a0d11455 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/apiutil/restmapper.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/apiutil/restmapper.go @@ -246,10 +246,18 @@ func (m *mapper) addGroupVersionResourcesToCacheAndReloadLocked(gvr map[schema.G } if !found { - groupResources.Group.Versions = append(groupResources.Group.Versions, metav1.GroupVersionForDiscovery{ + gv := metav1.GroupVersionForDiscovery{ GroupVersion: metav1.GroupVersion{Group: groupVersion.Group, Version: version}.String(), Version: version, - }) + } + + // Prepend if preferred version, else append. The upstream DiscoveryRestMappper assumes + // the first version is the preferred one: https://github.com/kubernetes/kubernetes/blob/ef54ac803b712137871c1a1f8d635d50e69ffa6c/staging/src/k8s.io/apimachinery/pkg/api/meta/restmapper.go#L458-L461 + if group, ok := m.apiGroups[groupVersion.Group]; ok && group.PreferredVersion.Version == version { + groupResources.Group.Versions = append([]metav1.GroupVersionForDiscovery{gv}, groupResources.Group.Versions...) + } else { + groupResources.Group.Versions = append(groupResources.Group.Versions, gv) + } } // Update data in the cache. @@ -284,14 +292,14 @@ func (m *mapper) findAPIGroupByNameAndMaybeAggregatedDiscoveryLocked(groupName s } m.initialDiscoveryDone = true - if len(maybeResources) > 0 { - didAggregatedDiscovery = true - m.addGroupVersionResourcesToCacheAndReloadLocked(maybeResources) - } for i := range apiGroups.Groups { group := &apiGroups.Groups[i] m.apiGroups[group.Name] = group } + if len(maybeResources) > 0 { + didAggregatedDiscovery = true + m.addGroupVersionResourcesToCacheAndReloadLocked(maybeResources) + } // Looking in the cache again. // Don't return an error here if the API group is not present. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go index 0c4300d548b..793219c7237 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go @@ -75,8 +75,8 @@ type fakeClient struct { trackerWriteLock sync.Mutex tracker versionedTracker - schemeWriteLock sync.Mutex - scheme *runtime.Scheme + schemeLock sync.RWMutex + scheme *runtime.Scheme restMapper meta.RESTMapper withStatusSubresource sets.Set[schema.GroupVersionKind] @@ -512,6 +512,8 @@ func (t versionedTracker) updateObject(gvr schema.GroupVersionResource, obj runt } func (c *fakeClient) Get(ctx context.Context, key client.ObjectKey, obj client.Object, opts ...client.GetOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() gvr, err := getGVRFromObject(obj, c.scheme) if err != nil { return err @@ -561,6 +563,8 @@ func (c *fakeClient) Watch(ctx context.Context, list client.ObjectList, opts ... } func (c *fakeClient) List(ctx context.Context, obj client.ObjectList, opts ...client.ListOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() gvk, err := apiutil.GVKForObject(obj, c.scheme) if err != nil { return err @@ -573,9 +577,11 @@ func (c *fakeClient) List(ctx context.Context, obj client.ObjectList, opts ...cl if _, isUnstructuredList := obj.(runtime.Unstructured); isUnstructuredList && !c.scheme.Recognizes(gvk) { // We need to register the ListKind with UnstructuredList: // https://github.com/kubernetes/kubernetes/blob/7b2776b89fb1be28d4e9203bdeec079be903c103/staging/src/k8s.io/client-go/dynamic/fake/simple.go#L44-L51 - c.schemeWriteLock.Lock() + c.schemeLock.RUnlock() + c.schemeLock.Lock() c.scheme.AddKnownTypeWithName(gvk.GroupVersion().WithKind(gvk.Kind+"List"), &unstructured.UnstructuredList{}) - c.schemeWriteLock.Unlock() + c.schemeLock.Unlock() + c.schemeLock.RLock() } listOpts := client.ListOptions{} @@ -726,6 +732,8 @@ func (c *fakeClient) IsObjectNamespaced(obj runtime.Object) (bool, error) { } func (c *fakeClient) Create(ctx context.Context, obj client.Object, opts ...client.CreateOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() createOptions := &client.CreateOptions{} createOptions.ApplyOptions(opts) @@ -762,6 +770,8 @@ func (c *fakeClient) Create(ctx context.Context, obj client.Object, opts ...clie } func (c *fakeClient) Delete(ctx context.Context, obj client.Object, opts ...client.DeleteOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() gvr, err := getGVRFromObject(obj, c.scheme) if err != nil { return err @@ -807,6 +817,8 @@ func (c *fakeClient) Delete(ctx context.Context, obj client.Object, opts ...clie } func (c *fakeClient) DeleteAllOf(ctx context.Context, obj client.Object, opts ...client.DeleteAllOfOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() gvk, err := apiutil.GVKForObject(obj, c.scheme) if err != nil { return err @@ -856,6 +868,8 @@ func (c *fakeClient) Update(ctx context.Context, obj client.Object, opts ...clie } func (c *fakeClient) update(obj client.Object, isStatus bool, opts ...client.UpdateOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() updateOptions := &client.UpdateOptions{} updateOptions.ApplyOptions(opts) @@ -884,6 +898,8 @@ func (c *fakeClient) Patch(ctx context.Context, obj client.Object, patch client. } func (c *fakeClient) patch(obj client.Object, patch client.Patch, opts ...client.PatchOption) error { + c.schemeLock.RLock() + defer c.schemeLock.RUnlock() patchOptions := &client.PatchOptions{} patchOptions.ApplyOptions(opts) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/name.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/name.go index 0e71a01c667..00ca6551281 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/name.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/name.go @@ -34,7 +34,7 @@ func checkName(name string) error { } if usedNames.Has(name) { - return fmt.Errorf("controller with name %s already exists. Controller names must be unique to avoid multiple controllers reporting to the same metric", name) + return fmt.Errorf("controller with name %s already exists. Controller names must be unique to avoid multiple controllers reporting the same metric. This validation can be disabled via the SkipNameValidation option", name) } usedNames.Insert(name) diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/priorityqueue/priorityqueue.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/priorityqueue/priorityqueue.go index 996369f47ac..ff5dea9021b 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/priorityqueue/priorityqueue.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/controller/priorityqueue/priorityqueue.go @@ -11,6 +11,7 @@ import ( "k8s.io/client-go/util/workqueue" "k8s.io/utils/clock" "k8s.io/utils/ptr" + "sigs.k8s.io/controller-runtime/pkg/internal/metrics" ) @@ -132,16 +133,17 @@ func (w *priorityqueue[T]) AddWithOpts(o AddOpts, items ...T) { defer w.lock.Unlock() for _, key := range items { + after := o.After if o.RateLimited { - after := w.rateLimiter.When(key) - if o.After == 0 || after < o.After { - o.After = after + rlAfter := w.rateLimiter.When(key) + if after == 0 || rlAfter < after { + after = rlAfter } } var readyAt *time.Time - if o.After > 0 { - readyAt = ptr.To(w.now().Add(o.After)) + if after > 0 { + readyAt = ptr.To(w.now().Add(after)) w.metrics.retry() } if _, ok := w.items[key]; !ok { diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue.go index 1a1d1ab2f44..64cbe8a4d13 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue.go @@ -52,25 +52,32 @@ func (e *TypedEnqueueRequestForObject[T]) Create(ctx context.Context, evt event. enqueueLog.Error(nil, "CreateEvent received with no metadata", "event", evt) return } - q.Add(reconcile.Request{NamespacedName: types.NamespacedName{ + + item := reconcile.Request{NamespacedName: types.NamespacedName{ Name: evt.Object.GetName(), Namespace: evt.Object.GetNamespace(), - }}) + }} + + addToQueueCreate(q, evt, item) } // Update implements EventHandler. func (e *TypedEnqueueRequestForObject[T]) Update(ctx context.Context, evt event.TypedUpdateEvent[T], q workqueue.TypedRateLimitingInterface[reconcile.Request]) { switch { case !isNil(evt.ObjectNew): - q.Add(reconcile.Request{NamespacedName: types.NamespacedName{ + item := reconcile.Request{NamespacedName: types.NamespacedName{ Name: evt.ObjectNew.GetName(), Namespace: evt.ObjectNew.GetNamespace(), - }}) + }} + + addToQueueUpdate(q, evt, item) case !isNil(evt.ObjectOld): - q.Add(reconcile.Request{NamespacedName: types.NamespacedName{ + item := reconcile.Request{NamespacedName: types.NamespacedName{ Name: evt.ObjectOld.GetName(), Namespace: evt.ObjectOld.GetNamespace(), - }}) + }} + + addToQueueUpdate(q, evt, item) default: enqueueLog.Error(nil, "UpdateEvent received with no metadata", "event", evt) } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_mapped.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_mapped.go index 491bc40c420..be97fa37815 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_mapped.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_mapped.go @@ -21,6 +21,7 @@ import ( "k8s.io/client-go/util/workqueue" "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/controller/priorityqueue" "sigs.k8s.io/controller-runtime/pkg/event" "sigs.k8s.io/controller-runtime/pkg/reconcile" ) @@ -63,7 +64,8 @@ func EnqueueRequestsFromMapFunc(fn MapFunc) EventHandler { // TypedEnqueueRequestsFromMapFunc is experimental and subject to future change. func TypedEnqueueRequestsFromMapFunc[object any, request comparable](fn TypedMapFunc[object, request]) TypedEventHandler[object, request] { return &enqueueRequestsFromMapFunc[object, request]{ - toRequests: fn, + toRequests: fn, + objectImplementsClientObject: implementsClientObject[object](), } } @@ -71,7 +73,8 @@ var _ EventHandler = &enqueueRequestsFromMapFunc[client.Object, reconcile.Reques type enqueueRequestsFromMapFunc[object any, request comparable] struct { // Mapper transforms the argument into a slice of keys to be reconciled - toRequests TypedMapFunc[object, request] + toRequests TypedMapFunc[object, request] + objectImplementsClientObject bool } // Create implements EventHandler. @@ -81,7 +84,15 @@ func (e *enqueueRequestsFromMapFunc[object, request]) Create( q workqueue.TypedRateLimitingInterface[request], ) { reqs := map[request]empty{} - e.mapAndEnqueue(ctx, q, evt.Object, reqs) + + var lowPriority bool + if e.objectImplementsClientObject && isPriorityQueue(q) && !isNil(evt.Object) { + clientObjectEvent := event.CreateEvent{Object: any(evt.Object).(client.Object)} + if isObjectUnchanged(clientObjectEvent) { + lowPriority = true + } + } + e.mapAndEnqueue(ctx, q, evt.Object, reqs, lowPriority) } // Update implements EventHandler. @@ -90,9 +101,13 @@ func (e *enqueueRequestsFromMapFunc[object, request]) Update( evt event.TypedUpdateEvent[object], q workqueue.TypedRateLimitingInterface[request], ) { + var lowPriority bool + if e.objectImplementsClientObject && isPriorityQueue(q) && !isNil(evt.ObjectOld) && !isNil(evt.ObjectNew) { + lowPriority = any(evt.ObjectOld).(client.Object).GetResourceVersion() == any(evt.ObjectNew).(client.Object).GetResourceVersion() + } reqs := map[request]empty{} - e.mapAndEnqueue(ctx, q, evt.ObjectOld, reqs) - e.mapAndEnqueue(ctx, q, evt.ObjectNew, reqs) + e.mapAndEnqueue(ctx, q, evt.ObjectOld, reqs, lowPriority) + e.mapAndEnqueue(ctx, q, evt.ObjectNew, reqs, lowPriority) } // Delete implements EventHandler. @@ -102,7 +117,7 @@ func (e *enqueueRequestsFromMapFunc[object, request]) Delete( q workqueue.TypedRateLimitingInterface[request], ) { reqs := map[request]empty{} - e.mapAndEnqueue(ctx, q, evt.Object, reqs) + e.mapAndEnqueue(ctx, q, evt.Object, reqs, false) } // Generic implements EventHandler. @@ -112,14 +127,26 @@ func (e *enqueueRequestsFromMapFunc[object, request]) Generic( q workqueue.TypedRateLimitingInterface[request], ) { reqs := map[request]empty{} - e.mapAndEnqueue(ctx, q, evt.Object, reqs) + e.mapAndEnqueue(ctx, q, evt.Object, reqs, false) } -func (e *enqueueRequestsFromMapFunc[object, request]) mapAndEnqueue(ctx context.Context, q workqueue.TypedRateLimitingInterface[request], o object, reqs map[request]empty) { +func (e *enqueueRequestsFromMapFunc[object, request]) mapAndEnqueue( + ctx context.Context, + q workqueue.TypedRateLimitingInterface[request], + o object, + reqs map[request]empty, + lowPriority bool, +) { for _, req := range e.toRequests(ctx, o) { _, ok := reqs[req] if !ok { - q.Add(req) + if lowPriority { + q.(priorityqueue.PriorityQueue[request]).AddWithOpts(priorityqueue.AddOpts{ + Priority: LowPriority, + }, req) + } else { + q.Add(req) + } reqs[req] = empty{} } } diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_owner.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_owner.go index 1680043b46f..e8fc8eb46e2 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_owner.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/enqueue_owner.go @@ -72,7 +72,7 @@ func TypedEnqueueRequestForOwner[object client.Object](scheme *runtime.Scheme, m for _, opt := range opts { opt(e) } - return e + return WithLowPriorityWhenUnchanged(e) } // OnlyControllerOwner if provided will only look at the first OwnerReference with Controller: true. diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/eventhandler.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/eventhandler.go index 57107f20e92..84a10ac077d 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/eventhandler.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/handler/eventhandler.go @@ -18,6 +18,7 @@ package handler import ( "context" + "reflect" "time" "k8s.io/client-go/util/workqueue" @@ -108,10 +109,46 @@ type TypedFuncs[object any, request comparable] struct { GenericFunc func(context.Context, event.TypedGenericEvent[object], workqueue.TypedRateLimitingInterface[request]) } +var typeForClientObject = reflect.TypeFor[client.Object]() + +func implementsClientObject[object any]() bool { + return reflect.TypeFor[object]().Implements(typeForClientObject) +} + +func isPriorityQueue[request comparable](q workqueue.TypedRateLimitingInterface[request]) bool { + _, ok := q.(priorityqueue.PriorityQueue[request]) + return ok +} + // Create implements EventHandler. func (h TypedFuncs[object, request]) Create(ctx context.Context, e event.TypedCreateEvent[object], q workqueue.TypedRateLimitingInterface[request]) { if h.CreateFunc != nil { - h.CreateFunc(ctx, e, q) + if !implementsClientObject[object]() || !isPriorityQueue(q) || isNil(e.Object) { + h.CreateFunc(ctx, e, q) + return + } + wq := workqueueWithCustomAddFunc[request]{ + TypedRateLimitingInterface: q, + // We already know that we have a priority queue, that event.Object implements + // client.Object and that its not nil + addFunc: func(item request, q workqueue.TypedRateLimitingInterface[request]) { + // We construct a new event typed to client.Object because isObjectUnchanged + // is a generic and hence has to know at compile time the type of the event + // it gets. We only figure that out at runtime though, but we know for sure + // that it implements client.Object at this point so we can hardcode the event + // type to that. + evt := event.CreateEvent{Object: any(e.Object).(client.Object)} + var priority int + if isObjectUnchanged(evt) { + priority = LowPriority + } + q.(priorityqueue.PriorityQueue[request]).AddWithOpts( + priorityqueue.AddOpts{Priority: priority}, + item, + ) + }, + } + h.CreateFunc(ctx, e, wq) } } @@ -125,7 +162,27 @@ func (h TypedFuncs[object, request]) Delete(ctx context.Context, e event.TypedDe // Update implements EventHandler. func (h TypedFuncs[object, request]) Update(ctx context.Context, e event.TypedUpdateEvent[object], q workqueue.TypedRateLimitingInterface[request]) { if h.UpdateFunc != nil { - h.UpdateFunc(ctx, e, q) + if !implementsClientObject[object]() || !isPriorityQueue(q) || isNil(e.ObjectOld) || isNil(e.ObjectNew) { + h.UpdateFunc(ctx, e, q) + return + } + + wq := workqueueWithCustomAddFunc[request]{ + TypedRateLimitingInterface: q, + // We already know that we have a priority queue, that event.ObjectOld and ObjectNew implement + // client.Object and that they are not nil + addFunc: func(item request, q workqueue.TypedRateLimitingInterface[request]) { + var priority int + if any(e.ObjectOld).(client.Object).GetResourceVersion() == any(e.ObjectNew).(client.Object).GetResourceVersion() { + priority = LowPriority + } + q.(priorityqueue.PriorityQueue[request]).AddWithOpts( + priorityqueue.AddOpts{Priority: priority}, + item, + ) + }, + } + h.UpdateFunc(ctx, e, wq) } } @@ -142,43 +199,10 @@ const LowPriority = -100 // WithLowPriorityWhenUnchanged reduces the priority of events stemming from the initial listwatch or from a resync if // and only if a priorityqueue.PriorityQueue is used. If not, it does nothing. func WithLowPriorityWhenUnchanged[object client.Object, request comparable](u TypedEventHandler[object, request]) TypedEventHandler[object, request] { + // TypedFuncs already implements this so just wrap return TypedFuncs[object, request]{ - CreateFunc: func(ctx context.Context, tce event.TypedCreateEvent[object], trli workqueue.TypedRateLimitingInterface[request]) { - // Due to how the handlers are factored, we have to wrap the workqueue to be able - // to inject custom behavior. - u.Create(ctx, tce, workqueueWithCustomAddFunc[request]{ - TypedRateLimitingInterface: trli, - addFunc: func(item request, q workqueue.TypedRateLimitingInterface[request]) { - priorityQueue, isPriorityQueue := q.(priorityqueue.PriorityQueue[request]) - if !isPriorityQueue { - q.Add(item) - return - } - var priority int - if isObjectUnchanged(tce) { - priority = LowPriority - } - priorityQueue.AddWithOpts(priorityqueue.AddOpts{Priority: priority}, item) - }, - }) - }, - UpdateFunc: func(ctx context.Context, tue event.TypedUpdateEvent[object], trli workqueue.TypedRateLimitingInterface[request]) { - u.Update(ctx, tue, workqueueWithCustomAddFunc[request]{ - TypedRateLimitingInterface: trli, - addFunc: func(item request, q workqueue.TypedRateLimitingInterface[request]) { - priorityQueue, isPriorityQueue := q.(priorityqueue.PriorityQueue[request]) - if !isPriorityQueue { - q.Add(item) - return - } - var priority int - if tue.ObjectOld.GetResourceVersion() == tue.ObjectNew.GetResourceVersion() { - priority = LowPriority - } - priorityQueue.AddWithOpts(priorityqueue.AddOpts{Priority: priority}, item) - }, - }) - }, + CreateFunc: u.Create, + UpdateFunc: u.Update, DeleteFunc: u.Delete, GenericFunc: u.Generic, } @@ -199,3 +223,35 @@ func (w workqueueWithCustomAddFunc[request]) Add(item request) { func isObjectUnchanged[object client.Object](e event.TypedCreateEvent[object]) bool { return e.Object.GetCreationTimestamp().Time.Before(time.Now().Add(-time.Minute)) } + +// addToQueueCreate adds the reconcile.Request to the priorityqueue in the handler +// for Create requests if and only if the workqueue being used is of type priorityqueue.PriorityQueue[reconcile.Request] +func addToQueueCreate[T client.Object, request comparable](q workqueue.TypedRateLimitingInterface[request], evt event.TypedCreateEvent[T], item request) { + priorityQueue, isPriorityQueue := q.(priorityqueue.PriorityQueue[request]) + if !isPriorityQueue { + q.Add(item) + return + } + + var priority int + if isObjectUnchanged(evt) { + priority = LowPriority + } + priorityQueue.AddWithOpts(priorityqueue.AddOpts{Priority: priority}, item) +} + +// addToQueueUpdate adds the reconcile.Request to the priorityqueue in the handler +// for Update requests if and only if the workqueue being used is of type priorityqueue.PriorityQueue[reconcile.Request] +func addToQueueUpdate[T client.Object, request comparable](q workqueue.TypedRateLimitingInterface[request], evt event.TypedUpdateEvent[T], item request) { + priorityQueue, isPriorityQueue := q.(priorityqueue.PriorityQueue[request]) + if !isPriorityQueue { + q.Add(item) + return + } + + var priority int + if evt.ObjectOld.GetResourceVersion() == evt.ObjectNew.GetResourceVersion() { + priority = LowPriority + } + priorityQueue.AddWithOpts(priorityqueue.AddOpts{Priority: priority}, item) +} diff --git a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go index cc734dfb617..3f8cfdaa092 100644 --- a/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go +++ b/cluster-api/providers/vsphere/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go @@ -31,6 +31,7 @@ import ( "k8s.io/apimachinery/pkg/util/uuid" "k8s.io/client-go/util/workqueue" + "sigs.k8s.io/controller-runtime/pkg/controller/priorityqueue" ctrlmetrics "sigs.k8s.io/controller-runtime/pkg/internal/controller/metrics" logf "sigs.k8s.io/controller-runtime/pkg/log" "sigs.k8s.io/controller-runtime/pkg/reconcile" @@ -60,7 +61,7 @@ type Controller[request comparable] struct { // Queue is an listeningQueue that listens for events from Informers and adds object keys to // the Queue for processing - Queue workqueue.TypedRateLimitingInterface[request] + Queue priorityqueue.PriorityQueue[request] // mu is used to synchronize Controller setup mu sync.Mutex @@ -157,7 +158,12 @@ func (c *Controller[request]) Start(ctx context.Context) error { // Set the internal context. c.ctx = ctx - c.Queue = c.NewQueue(c.Name, c.RateLimiter) + queue := c.NewQueue(c.Name, c.RateLimiter) + if priorityQueue, isPriorityQueue := queue.(priorityqueue.PriorityQueue[request]); isPriorityQueue { + c.Queue = priorityQueue + } else { + c.Queue = &priorityQueueWrapper[request]{TypedRateLimitingInterface: queue} + } go func() { <-ctx.Done() c.Queue.ShutDown() @@ -268,7 +274,7 @@ func (c *Controller[request]) Start(ctx context.Context) error { // processNextWorkItem will read a single work item off the workqueue and // attempt to process it, by calling the reconcileHandler. func (c *Controller[request]) processNextWorkItem(ctx context.Context) bool { - obj, shutdown := c.Queue.Get() + obj, priority, shutdown := c.Queue.GetWithPriority() if shutdown { // Stop working return false @@ -285,7 +291,7 @@ func (c *Controller[request]) processNextWorkItem(ctx context.Context) bool { ctrlmetrics.ActiveWorkers.WithLabelValues(c.Name).Add(1) defer ctrlmetrics.ActiveWorkers.WithLabelValues(c.Name).Add(-1) - c.reconcileHandler(ctx, obj) + c.reconcileHandler(ctx, obj, priority) return true } @@ -308,7 +314,7 @@ func (c *Controller[request]) initMetrics() { ctrlmetrics.ActiveWorkers.WithLabelValues(c.Name).Set(0) } -func (c *Controller[request]) reconcileHandler(ctx context.Context, req request) { +func (c *Controller[request]) reconcileHandler(ctx context.Context, req request, priority int) { // Update metrics after processing each item reconcileStartTS := time.Now() defer func() { @@ -331,7 +337,7 @@ func (c *Controller[request]) reconcileHandler(ctx context.Context, req request) if errors.Is(err, reconcile.TerminalError(nil)) { ctrlmetrics.TerminalReconcileErrors.WithLabelValues(c.Name).Inc() } else { - c.Queue.AddRateLimited(req) + c.Queue.AddWithOpts(priorityqueue.AddOpts{RateLimited: true, Priority: priority}, req) } ctrlmetrics.ReconcileErrors.WithLabelValues(c.Name).Inc() ctrlmetrics.ReconcileTotal.WithLabelValues(c.Name, labelError).Inc() @@ -346,11 +352,11 @@ func (c *Controller[request]) reconcileHandler(ctx context.Context, req request) // We need to drive to stable reconcile loops before queuing due // to result.RequestAfter c.Queue.Forget(req) - c.Queue.AddAfter(req, result.RequeueAfter) + c.Queue.AddWithOpts(priorityqueue.AddOpts{After: result.RequeueAfter, Priority: priority}, req) ctrlmetrics.ReconcileTotal.WithLabelValues(c.Name, labelRequeueAfter).Inc() case result.Requeue: log.V(5).Info("Reconcile done, requeueing") - c.Queue.AddRateLimited(req) + c.Queue.AddWithOpts(priorityqueue.AddOpts{RateLimited: true, Priority: priority}, req) ctrlmetrics.ReconcileTotal.WithLabelValues(c.Name, labelRequeue).Inc() default: log.V(5).Info("Reconcile successful") @@ -388,3 +394,25 @@ type reconcileIDKey struct{} func addReconcileID(ctx context.Context, reconcileID types.UID) context.Context { return context.WithValue(ctx, reconcileIDKey{}, reconcileID) } + +type priorityQueueWrapper[request comparable] struct { + workqueue.TypedRateLimitingInterface[request] +} + +func (p *priorityQueueWrapper[request]) AddWithOpts(opts priorityqueue.AddOpts, items ...request) { + for _, item := range items { + switch { + case opts.RateLimited: + p.TypedRateLimitingInterface.AddRateLimited(item) + case opts.After > 0: + p.TypedRateLimitingInterface.AddAfter(item, opts.After) + default: + p.TypedRateLimitingInterface.Add(item) + } + } +} + +func (p *priorityQueueWrapper[request]) GetWithPriority() (request, int, bool) { + item, shutdown := p.TypedRateLimitingInterface.Get() + return item, 0, shutdown +}