diff --git a/.devcontainer/Dockerfile b/.devcontainer/Dockerfile index 55423476d7e42..f5687d40bd6dc 100644 --- a/.devcontainer/Dockerfile +++ b/.devcontainer/Dockerfile @@ -5,7 +5,7 @@ ARG USER_UID=501 ARG USER_GID=$USER_UID ENV BUILD_DIR=/build -ENV ENVOY_STDLIB=libstdc++ +ENV ENVOY_STDLIB=libc++ ENV DEBIAN_FRONTEND=noninteractive RUN apt-get -y update \ diff --git a/.devcontainer/setup.sh b/.devcontainer/setup.sh index b50bb1190d661..421db0f0b61a2 100755 --- a/.devcontainer/setup.sh +++ b/.devcontainer/setup.sh @@ -5,7 +5,7 @@ BAZELRC_FILE=~/.bazelrc bazel/setup_clang.sh /opt/llvm # TODO(phlax): use user.bazelrc # Use generated toolchain config because we know the base container is the one we're using in RBE. # Not using libc++ here because clangd will raise some tidy issue in libc++ header as of version 9. -echo "build --config=rbe-toolchain-clang" >> ~/.bazelrc +echo "build --config=rbe-toolchain-clang-libc++" >> ~/.bazelrc echo "build ${BAZEL_BUILD_EXTRA_OPTIONS}" | tee -a ~/.bazelrc # Ideally we want this line so bazel doesn't pollute things outside of the devcontainer, but some of diff --git a/.github/workflows/_precheck_deps.yml b/.github/workflows/_precheck_deps.yml index 413f3dd8b2d0f..d50d62f0ed121 100644 --- a/.github/workflows/_precheck_deps.yml +++ b/.github/workflows/_precheck_deps.yml @@ -55,4 +55,4 @@ jobs: ref: ${{ fromJSON(inputs.request).request.sha }} persist-credentials: false - name: Dependency Review - uses: actions/dependency-review-action@c74b580d73376b7750d3d2a50bfb8adc2c937507 # v3.1.5 + uses: actions/dependency-review-action@4901385134134e04cec5fbe5ddfe3b2c5bd5d976 # v4.0.0 diff --git a/.github/workflows/envoy-macos.yml b/.github/workflows/envoy-macos.yml index f432d866ee82a..22d975afd7ce3 100644 --- a/.github/workflows/envoy-macos.yml +++ b/.github/workflows/envoy-macos.yml @@ -48,7 +48,7 @@ jobs: command: container-command: request: ${{ needs.load.outputs.request }} - runs-on: macos-12-xl + runs-on: macos-14-xlarge steps-post: steps-pre: ${{ matrix.steps-pre }} target: ${{ matrix.target }} diff --git a/CODEOWNERS b/CODEOWNERS index e9e3527b573e2..bd937e7a08ad8 100644 --- a/CODEOWNERS +++ b/CODEOWNERS @@ -4,6 +4,12 @@ # api /api/ @envoyproxy/api-shepherds + +# docs/examples +/docs/ @envoyproxy/docs-shepherds +/examples/ @envoyproxy/docs-shepherds +/changelogs/ @envoyproxy/docs-shepherds + # access loggers /*/extensions/access_loggers/common @auni53 @zuercher /*/extensions/access_loggers/open_telemetry @itamarkam @yanavlasov diff --git a/OWNERS.md b/OWNERS.md index 51a50bab403d9..a8137725f5966 100644 --- a/OWNERS.md +++ b/OWNERS.md @@ -6,6 +6,7 @@ This page lists all active maintainers and their areas of expertise. This can be routing PRs, questions, etc. to the right place. # Senior maintainers + * Matt Klein ([mattklein123](https://github.com/mattklein123)) (mattklein123@gmail.com) * Catch-all, "all the things", and generally trying to make himself obsolete as fast as @@ -33,6 +34,7 @@ routing PRs, questions, etc. to the right place. * Upstream, LB, tracing, logging, performance, and generic/dubbo proxy. # Maintainers + * Joshua Marantz ([jmarantz](https://github.com/jmarantz)) (jmarantz@google.com) * Stats, abseil, scalability, and performance. @@ -76,7 +78,7 @@ without further review. * Otto van der Schaaf ([oschaaf](https://github.com/oschaaf)) (oschaaf@redhat.com) * Tim Walsh ([twghu](https://github.com/twghu)) (twalsh@redhat.com) * Pradeep Rao ([pradeepcrao](https://github.com/pradeepcrao)) (pcrao@google.com) -* Kateryna Nezdolii ([nezdolik](https://github.com/nezdolik)) (nezdolik@spotify.com) +* Kateryna Nezdolii ([nezdolik](https://github.com/nezdolik)) (kateryna.nezdolii@gmail.com) * Boteng Yao ([botengyao](https://github.com/botengyao)) (boteng@google.com) * Kevin Baichoo ([KBaichoo](https://github.com/KBaichoo)) (kbaichoo@google.com) * Tianyu Xia ([tyxia](https://github.com/tyxia)) (tyxia@google.com) diff --git a/README.md b/README.md index 8be85d8fbeac0..87720cb45d3ee 100644 --- a/README.md +++ b/README.md @@ -10,6 +10,7 @@ involved and how Envoy plays a role, read the CNCF [![CII Best Practices](https://bestpractices.coreinfrastructure.org/projects/1266/badge)](https://bestpractices.coreinfrastructure.org/projects/1266) [![OpenSSF Scorecard](https://api.securityscorecards.dev/projects/github.com/envoyproxy/envoy/badge)](https://securityscorecards.dev/viewer/?uri=github.com/envoyproxy/envoy) +[![CLOMonitor](https://img.shields.io/endpoint?url=https://clomonitor.io/api/projects/cncf/envoy/badge)](https://clomonitor.io/projects/cncf/envoy) [![Azure Pipelines](https://dev.azure.com/cncf/envoy/_apis/build/status/11?branchName=main)](https://dev.azure.com/cncf/envoy/_build/latest?definitionId=11&branchName=main) [![Fuzzing Status](https://oss-fuzz-build-logs.storage.googleapis.com/badges/envoy.svg)](https://bugs.chromium.org/p/oss-fuzz/issues/list?sort=-opened&can=1&q=proj:envoy) [![Jenkins](https://powerci.osuosl.org/buildStatus/icon?job=build-envoy-static-master&subject=ppc64le%20build)](https://powerci.osuosl.org/job/build-envoy-static-master/) diff --git a/RELEASES.md b/RELEASES.md index 564a0bfb1d795..310775471f075 100644 --- a/RELEASES.md +++ b/RELEASES.md @@ -63,8 +63,8 @@ actual mechanics of the release itself. | 2022 Q1 | Otto van der Schaaf ([oschaaf](https://github.com/oschaaf)) | Ryan Hamilton ([RyanTheOptimist](https://github.com/RyanTheOptimist)) | | 2022 Q2 | Pradeep Rao ([pradeepcrao](https://github.com/pradeepcrao)) | Matt Klein ([mattklein123](https://github.com/mattklein123) | | 2022 Q4 | Can Cecen ([cancecen](https://github.com/cancecen)) | Tony Allen ([tonya11en](https://github.com/tonya11en)) | -| 2022 Q3 | Boteng Yao ([botengyao](https://github.com/botengyao)) | Kateryna Nezdolii ([nezdolik](https://github.com/nezdolik)) | -| 2022 Q4 | Paul Merrison ([pmerrison](https://github.com/pmerrison)) | Brian Sonnenberg ([briansonnenberg](https://github.com/briansonnenberg)) | +| 2023 Q3 | Boteng Yao ([botengyao](https://github.com/botengyao)) | Kateryna Nezdolii ([nezdolik](https://github.com/nezdolik)) | +| 2023 Q4 | Paul Merrison ([pmerrison](https://github.com/pmerrison)) | Brian Sonnenberg ([briansonnenberg](https://github.com/briansonnenberg)) | ## Major release schedule @@ -90,8 +90,9 @@ deadline of 3 weeks. | 1.25.0 | 2023/01/15 | 2023/01/18 | +3 days | 2024/01/18 | | 1.26.0 | 2023/04/15 | 2023/04/18 | +3 days | 2024/04/18 | | 1.27.0 | 2023/07/14 | 2023/07/27 | +13 days | 2024/07/27 | -| 1.28.0 | 2023/10/16 | 2023/10/19 | +3 days | 2024/10/19 | -| 1.29.0 | 2024/01/16 | | | | +| 1.28.0 | 2023/10/16 | 2023/10/19 | +3 days | 2024/10/19 | +| 1.29.0 | 2024/01/16 | 2024/01/16 | 0 days | 2025/01/16 | +| 1.30.0 | 2024/04/16 | | | | ### Cutting a major release @@ -106,24 +107,26 @@ deadline of 3 weeks. * Make any needed corrections (grammar, punctuation, formatting, etc.). * Check to see if any security/stable version release notes are duplicated in the major version release notes. These should not be duplicated. - * Switch the repo to "release" mode by running `bazel run @envoy_repo//:release`. See the [project - tool](tools/project/README.md#bazel-run-toolsprojectrelease) for further information. This tool + * Switch the repo to "release" mode by running `bazel run @envoy_repo//:release`. This tool will create a commit with the necessary changes for a release. * Update the [RELEASES](RELEASES.md) doc with the relevant dates. Now, or after you cut the release, please also make sure there's a stable maintainer signed up for next quarter, and the deadline for the next release is documented in the release schedule. * Get a review and merge. -* Create a pull request with the commit created by the project tool and **wait for tests to - pass**. +* Create a pull request with that commit and **wait for tests to pass**. * Once the tests have passed, and the PR has landed, CI will automatically create the tagged release and corresponding release branch. -* Craft a witty/uplifting email and send it to all the email aliases: envoy-announce@ envoy-users@ envoy-dev@ envoy-maintainers -* Make sure we tweet the new release: either have Matt do it or email social@cncf.io and ask them to do an Envoy account - post. -* Switch the repo back to "dev" mode by running `bazel run @envoy_repo//:dev`. See the [project - tool](tools/project/README.md#bazel-run-toolsprojectdev) for further information. This tool will create a commit with the +* Switch the repo back to "dev" mode by running `bazel run @envoy_repo//:dev`. This tool will create a commit with the necessary changes to continue development. -* Create a pull request with commit created by the project tool. +* Create a pull request with that commit. * Run the deprecate_versions.py script (`bazel run //tools/deprecate_version:deprecate_version`) +* If you haven't done this before, request posting permission from admins for all the groups in the next bullet. +* Craft a witty/uplifting email and send it to all the email aliases: +envoy-announce@googlegroups.com +envoy-users@googlegroups.com +envoy-dev@googlegroups.com +envoy-maintainers@googlegroups.com - +include in this email a link to the latest [release page](https://github.com/envoyproxy/envoy/releases) (ending in `tag/[version]`) +* Announce in [#envoy-dev](https://envoyproxy.slack.com/archives/C78HA81DH) and [#envoy-users](https://envoyproxy.slack.com/archives/C78M4KW76) slack channels. ## Security release schedule diff --git a/SECURITY-INSIGHTS.yml b/SECURITY-INSIGHTS.yml new file mode 100644 index 0000000000000..ba6f6d1b26086 --- /dev/null +++ b/SECURITY-INSIGHTS.yml @@ -0,0 +1,67 @@ +header: + schema-version: '1.0.0' + expiration-date: '2025-01-24T01:00:00.000Z' + last-updated: '2024-01-24' + last-reviewed: '2024-01-24' + project-url: https://github.com/envoyproxy/envoy + changelog: https://www.envoyproxy.io/docs/envoy/latest/version_history/version_history#version-history + license: https://github.com/envoyproxy/envoy/blob/main/LICENSE +project-lifecycle: + status: active + bug-fixes-only: false + core-maintainers: # from https://github.com/envoyproxy/envoy/blob/main/OWNERS.md +# Senior maintainers + - github:mattklein123 + - github:htuch + - github:alyssawilk + - github:zuercher + - github:lizan + - github:ggreenway + - github:yanavlasov + - github:phlax + - github:RyanTheOptimist + - github:wbpcode +# Maintainers + - github:jmarantz + - github:adisuissa + - github:KBaichoo + - github:keith + - github:kyessenov + - github:ravenblackx + - github:soulxu + - github:nezdolik +contribution-policy: + accepts-pull-requests: true + accepts-automated-pull-requests: true + code-of-conduct: https://github.com/envoyproxy/envoy/blob/main/CODE_OF_CONDUCT.md +dependencies: + third-party-packages: true + dependencies-lists: + - https://www.envoyproxy.io/docs/envoy/latest/intro/arch_overview/security/external_deps + env-dependencies-policy: + policy-url: https://github.com/envoyproxy/envoy/blob/main/DEPENDENCY_POLICY.md +distribution-points: + - https://github.com/envoyproxy/envoy +documentation: + - https://www.envoyproxy.io/docs +security-contacts: + - type: email + value: envoy-security@googlegroups.com +security-testing: +- tool-type: sca + tool-name: Dependabot + tool-version: latest + integration: + ad-hoc: false + ci: true + before-release: true +- tool-type: sast + tool-name: CodeQL + tool-version: '2.13.4' + integration: + ad-hoc: false + ci: true + before-release: true +vulnerability-reporting: + accepts-vulnerability-reports: true + security-policy: https://github.com/envoyproxy/envoy/security/policy diff --git a/api/BUILD b/api/BUILD index 16a0037cf8e85..2eadff1f606f7 100644 --- a/api/BUILD +++ b/api/BUILD @@ -203,6 +203,7 @@ proto_library( "//envoy/extensions/filters/http/oauth2/v3:pkg", "//envoy/extensions/filters/http/on_demand/v3:pkg", "//envoy/extensions/filters/http/original_src/v3:pkg", + "//envoy/extensions/filters/http/proto_message_logging/v3:pkg", "//envoy/extensions/filters/http/rate_limit_quota/v3:pkg", "//envoy/extensions/filters/http/ratelimit/v3:pkg", "//envoy/extensions/filters/http/rbac/v3:pkg", diff --git a/api/bazel/BUILD b/api/bazel/BUILD index c4116598f74c7..6a04bed1eb0cc 100644 --- a/api/bazel/BUILD +++ b/api/bazel/BUILD @@ -26,6 +26,15 @@ go_proto_compiler( visibility = ["//visibility:public"], ) +go_proto_compiler( + name = "vtprotobuf_plugin_go", + options = ["features=marshal_strict+size"], + plugin = "@com_github_planetscale_vtprotobuf//cmd/protoc-gen-go-vtproto", + suffix = "_vtproto.pb.go", + valid_archive = False, + visibility = ["//visibility:public"], +) + json_data( name = "repository_locations", data = load_repository_locations_spec(REPOSITORY_LOCATIONS_SPEC), diff --git a/api/bazel/api_build_system.bzl b/api/bazel/api_build_system.bzl index 1f24149b9f927..ea0e6fa6f59b4 100644 --- a/api/bazel/api_build_system.bzl +++ b/api/bazel/api_build_system.bzl @@ -146,9 +146,9 @@ def api_proto_package( has_services = has_services, ) - compilers = ["@io_bazel_rules_go//proto:go_proto", "@envoy_api//bazel:pgv_plugin_go"] + compilers = ["@io_bazel_rules_go//proto:go_proto", "@envoy_api//bazel:pgv_plugin_go", "@envoy_api//bazel:vtprotobuf_plugin_go"] if has_services: - compilers = ["@io_bazel_rules_go//proto:go_grpc", "@envoy_api//bazel:pgv_plugin_go"] + compilers = ["@io_bazel_rules_go//proto:go_grpc", "@envoy_api//bazel:pgv_plugin_go", "@envoy_api//bazel:vtprotobuf_plugin_go"] deps = ( [_go_proto_mapping(dep) for dep in deps] + @@ -162,6 +162,13 @@ def api_proto_package( "@io_bazel_rules_go//proto/wkt:struct_go_proto", "@io_bazel_rules_go//proto/wkt:timestamp_go_proto", "@io_bazel_rules_go//proto/wkt:wrappers_go_proto", + "@com_github_planetscale_vtprotobuf//types/known/anypb", + "@com_github_planetscale_vtprotobuf//types/known/durationpb", + "@com_github_planetscale_vtprotobuf//types/known/emptypb", + "@com_github_planetscale_vtprotobuf//types/known/fieldmaskpb", + "@com_github_planetscale_vtprotobuf//types/known/structpb", + "@com_github_planetscale_vtprotobuf//types/known/timestamppb", + "@com_github_planetscale_vtprotobuf//types/known/wrapperspb", ] ) go_proto_library( diff --git a/api/bazel/repository_locations.bzl b/api/bazel/repository_locations.bzl index 202a5f8fb07b7..15265b5218786 100644 --- a/api/bazel/repository_locations.bzl +++ b/api/bazel/repository_locations.bzl @@ -17,11 +17,11 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_desc = "protoc plugin to generate polyglot message validators", project_url = "https://github.com/bufbuild/protoc-gen-validate", use_category = ["api"], - sha256 = "0b1b1ea8c248dce8c7592dc1a93e4adebd116f0d68123f8eb34251e7ce410866", - version = "1.0.2", + sha256 = "9372f9ecde8fbadf83c8c7de3dbb49b11067aa26fb608c501106d0b4bf06c28f", + version = "1.0.4", urls = ["https://github.com/bufbuild/protoc-gen-validate/archive/refs/tags/v{version}.zip"], strip_prefix = "protoc-gen-validate-{version}", - release_date = "2023-06-26", + release_date = "2024-01-17", implied_untracked_deps = [ "com_github_iancoleman_strcase", "com_github_lyft_protoc_gen_star_v2", @@ -118,9 +118,9 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "OpenTelemetry Proto", project_desc = "Language Independent Interface Types For OpenTelemetry", project_url = "https://github.com/open-telemetry/opentelemetry-proto", - version = "1.0.0", - sha256 = "a13a1a7b76a1f22a0ca2e6c293e176ffef031413ab8ba653a82a1dbc286a3a33", - release_date = "2023-07-03", + version = "1.1.0", + sha256 = "df491a05f3fcbf86cc5ba5c9de81f6a624d74d4773d7009d573e37d6e2b6af64", + release_date = "2024-01-11", strip_prefix = "opentelemetry-proto-{version}", urls = ["https://github.com/open-telemetry/opentelemetry-proto/archive/v{version}.tar.gz"], use_category = ["api"], @@ -131,11 +131,11 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "buf", project_desc = "A new way of working with Protocol Buffers.", # Used for breaking change detection in API protobufs project_url = "https://buf.build", - version = "1.28.1", - sha256 = "870cf492d381a967d36636fdee9da44b524ea62aad163659b8dbf16a7da56987", + version = "1.29.0", + sha256 = "1033f26361e6fc30ffcfab9d4e4274ffd4af88d9c97de63d2e1721c4a07c1380", strip_prefix = "buf", urls = ["https://github.com/bufbuild/buf/releases/download/v{version}/buf-Linux-x86_64.tar.gz"], - release_date = "2023-11-15", + release_date = "2024-01-24", use_category = ["api"], license = "Apache-2.0", license_url = "https://github.com/bufbuild/buf/blob/v{version}/LICENSE", diff --git a/api/contrib/envoy/extensions/private_key_providers/cryptomb/v3alpha/cryptomb.proto b/api/contrib/envoy/extensions/private_key_providers/cryptomb/v3alpha/cryptomb.proto index 20290d8882c0b..cba32b76ab29f 100644 --- a/api/contrib/envoy/extensions/private_key_providers/cryptomb/v3alpha/cryptomb.proto +++ b/api/contrib/envoy/extensions/private_key_providers/cryptomb/v3alpha/cryptomb.proto @@ -21,10 +21,10 @@ option (udpa.annotations.file_status).package_version_status = ACTIVE; // A CryptoMbPrivateKeyMethodConfig message specifies how the CryptoMb private // key provider is configured. The private key provider provides ``SIMD`` -// processing for RSA sign and decrypt operations (ECDSA signing uses regular -// BoringSSL functions). The provider works by gathering the operations into a -// worker-thread specific queue, and processing the queue using ``ipp-crypto`` -// library when the queue is full or when a timer expires. +// processing for ECDSA sign operations and RSA sign and decrypt operations. +// The provider works by gathering the operations into a worker-thread specific +// queue, and processing the queue using ``ipp-crypto`` library when the queue +// is full or when a timer expires. // [#extension-category: envoy.tls.key_providers] message CryptoMbPrivateKeyMethodConfig { // Private key to use in the private key provider. If set to inline_bytes or diff --git a/api/envoy/config/cluster/v3/cluster.proto b/api/envoy/config/cluster/v3/cluster.proto index 9b847a33126b4..775f37d92a3fd 100644 --- a/api/envoy/config/cluster/v3/cluster.proto +++ b/api/envoy/config/cluster/v3/cluster.proto @@ -1236,6 +1236,26 @@ message UpstreamConnectionOptions { option (udpa.annotations.versioning).previous_message_type = "envoy.api.v2.UpstreamConnectionOptions"; + enum FirstAddressFamilyVersion { + // respect the native ranking of destination ip addresses returned from dns + // resolution + DEFAULT = 0; + + V4 = 1; + + V6 = 2; + } + + message HappyEyeballsConfig { + // Specify the IP address family to attempt connection first in happy + // eyeballs algorithm according to RFC8305#section-4. + FirstAddressFamilyVersion first_address_family_version = 1; + + // Specify the number of addresses of the first_address_family_version being + // attempted for connection before the other address family. + google.protobuf.UInt32Value first_address_family_count = 2 [(validate.rules).uint32 = {gte: 1}]; + } + // If set then set SO_KEEPALIVE on the socket to enable TCP Keepalives. core.v3.TcpKeepalive tcp_keepalive = 1; @@ -1243,6 +1263,11 @@ message UpstreamConnectionOptions { // This can be used by extensions during processing of requests. The association mechanism is // implementation specific. Defaults to false due to performance concerns. bool set_local_interface_name_on_upstream_connections = 2; + + // Configurations for happy eyeballs algorithm. + // Add configs for first_address_family_version and first_address_family_count + // when sorting destination ip addresses. + HappyEyeballsConfig happy_eyeballs_config = 3; } message TrackClusterStats { diff --git a/api/envoy/config/listener/v3/quic_config.proto b/api/envoy/config/listener/v3/quic_config.proto index 3a8ce2cd0a62a..8e7d8048d6a91 100644 --- a/api/envoy/config/listener/v3/quic_config.proto +++ b/api/envoy/config/listener/v3/quic_config.proto @@ -24,7 +24,7 @@ option (udpa.annotations.file_status).package_version_status = ACTIVE; // [#protodoc-title: QUIC listener config] // Configuration specific to the UDP QUIC listener. -// [#next-free-field: 10] +// [#next-free-field: 11] message QuicProtocolOptions { option (udpa.annotations.versioning).previous_message_type = "envoy.api.v2.listener.QuicProtocolOptions"; @@ -77,4 +77,8 @@ message QuicProtocolOptions { // [#extension-category: envoy.quic.server_preferred_address] core.v3.TypedExtensionConfig server_preferred_address_config = 9 [(xds.annotations.v3.field_status).work_in_progress = true]; + + // Configure the server to send transport parameter `disable_active_migration `_. + // Defaults to false (do not send this transport parameter). + google.protobuf.BoolValue send_disable_active_migration = 10; } diff --git a/api/envoy/config/rbac/v3/rbac.proto b/api/envoy/config/rbac/v3/rbac.proto index 3a9271c0015a6..8d98fd7155d87 100644 --- a/api/envoy/config/rbac/v3/rbac.proto +++ b/api/envoy/config/rbac/v3/rbac.proto @@ -194,7 +194,7 @@ message Policy { } // Permission defines an action (or actions) that a principal can take. -// [#next-free-field: 13] +// [#next-free-field: 14] message Permission { option (udpa.annotations.versioning).previous_message_type = "envoy.config.rbac.v2.Permission"; @@ -270,6 +270,10 @@ message Permission { // Extension for configuring custom matchers for RBAC. // [#extension-category: envoy.rbac.matchers] core.v3.TypedExtensionConfig matcher = 12; + + // URI template path matching. + // [#extension-category: envoy.path.match] + core.v3.TypedExtensionConfig uri_template = 13; } } diff --git a/api/envoy/config/route/v3/route_components.proto b/api/envoy/config/route/v3/route_components.proto index 1e2b486d288bf..3e755301d305c 100644 --- a/api/envoy/config/route/v3/route_components.proto +++ b/api/envoy/config/route/v3/route_components.proto @@ -1211,7 +1211,6 @@ message RouteAction { // :ref:`host_rewrite_path_regex `) // causes the original value of the host header, if any, to be appended to the // :ref:`config_http_conn_man_headers_x-forwarded-host` HTTP header if it is different to the last value appended. - // This can be disabled by setting the runtime guard ``envoy_reloadable_features_append_xfh_idempotent`` to false. bool append_x_forwarded_host = 38; // Specifies the upstream timeout for the route. If not specified, the default is 15s. This diff --git a/api/envoy/extensions/common/dynamic_forward_proxy/v3/dns_cache.proto b/api/envoy/extensions/common/dynamic_forward_proxy/v3/dns_cache.proto index d8f9b717fb004..eae3b8f742619 100644 --- a/api/envoy/extensions/common/dynamic_forward_proxy/v3/dns_cache.proto +++ b/api/envoy/extensions/common/dynamic_forward_proxy/v3/dns_cache.proto @@ -67,9 +67,9 @@ message DnsCacheConfig { // The minimum rate that DNS resolution will occur. Per ``dns_refresh_rate``, once a host is // resolved, the DNS TTL will be used, with a minimum set by ``dns_min_refresh_rate``. - // ``dns_min_refresh_rate`` defaults to 5s and must also be >= 5s. + // ``dns_min_refresh_rate`` defaults to 5s and must also be >= 1s. google.protobuf.Duration dns_min_refresh_rate = 14 - [(validate.rules).duration = {gte {seconds: 5}}]; + [(validate.rules).duration = {gte {seconds: 1}}]; // The TTL for hosts that are unused. Hosts that have not been used in the configured time // interval will be purged. If not specified defaults to 5m. diff --git a/api/envoy/extensions/filters/http/ext_proc/v3/ext_proc.proto b/api/envoy/extensions/filters/http/ext_proc/v3/ext_proc.proto index c9500486a3a52..ebcc53d774d44 100644 --- a/api/envoy/extensions/filters/http/ext_proc/v3/ext_proc.proto +++ b/api/envoy/extensions/filters/http/ext_proc/v3/ext_proc.proto @@ -28,8 +28,6 @@ option (udpa.annotations.file_status).package_version_status = ACTIVE; // **Current Implementation Status:** // All options and processing modes are implemented except for the following: // -// * Request and response attributes are not sent and not processed. -// * Dynamic metadata in responses from the external processor is ignored. // * "async mode" is not implemented. // The filter communicates with an external gRPC service called an "external processor" @@ -98,7 +96,7 @@ option (udpa.annotations.file_status).package_version_status = ACTIVE; // ` object in a namespace matching the filter // name. // -// [#next-free-field: 16] +// [#next-free-field: 17] message ExternalProcessor { // Configuration for the gRPC service that the filter will communicate with. // The filter supports both the "Envoy" and "Google" gRPC clients. @@ -125,7 +123,6 @@ message ExternalProcessor { // for a reply. bool async_mode = 4; - // [#not-implemented-hide:] // Envoy provides a number of :ref:`attributes ` // for expressive policies. Each attribute name provided in this field will be // matched against that list and populated in the request_headers message. @@ -133,7 +130,6 @@ message ExternalProcessor { // for the list of supported attributes and their types. repeated string request_attributes = 5; - // [#not-implemented-hide:] // Envoy provides a number of :ref:`attributes ` // for expressive policies. Each attribute name provided in this field will be // matched against that list and populated in the response_headers message. @@ -206,6 +202,35 @@ message ExternalProcessor { // Instead, the stream to the external processor will be closed. There will be no // more external processing for this stream from now on. bool disable_immediate_response = 15; + + // Options related to the sending and receiving of dynamic metadata. + MetadataOptions metadata_options = 16; +} + +// The MetadataOptions structure defines options for the sending and receiving of +// dynamic metadata. Specifically, which namespaces to send to the server, whether +// metadata returned by the server may be written, and how that metadata may be written. +message MetadataOptions { + message MetadataNamespaces { + // Specifies a list of metadata namespaces whose values, if present, + // will be passed to the ext_proc service as an opaque *protobuf::Struct*. + repeated string untyped = 1; + + // Specifies a list of metadata namespaces whose values, if present, + // will be passed to the ext_proc service as a *protobuf::Any*. This allows + // envoy and the external processing server to share the protobuf message + // definition for safe parsing. + repeated string typed = 2; + } + + // Describes which typed or untyped dynamic metadata namespaces to forward to + // the external processing server. + MetadataNamespaces forwarding_namespaces = 1; + + // Describes which typed or untyped dynamic metadata namespaces to accept from + // the external processing server. Set to empty or leave unset to disallow writing + // any received dynamic metadata. Receiving of typed metadata is not supported. + MetadataNamespaces receiving_namespaces = 2; } // The HeaderForwardingRules structure specifies what headers are @@ -248,7 +273,7 @@ message ExtProcPerRoute { } // Overrides that may be set on a per-route basis -// [#next-free-field: 6] +// [#next-free-field: 7] message ExtProcOverrides { // Set a different processing mode for this route than the default. ProcessingMode processing_mode = 1; @@ -269,4 +294,11 @@ message ExtProcOverrides { // Set a different gRPC service for this route than the default. config.core.v3.GrpcService grpc_service = 5; + + // Options related to the sending and receiving of dynamic metadata. + // Lists of forwarding and receiving namespaces will be overridden in their entirety, + // meaning the most-specific config that specifies this override will be the final + // config used. It is the prerogative of the control plane to ensure this + // most-specific config contains the correct final overrides. + MetadataOptions metadata_options = 6; } diff --git a/api/envoy/extensions/filters/http/proto_message_logging/v3/BUILD b/api/envoy/extensions/filters/http/proto_message_logging/v3/BUILD new file mode 100644 index 0000000000000..628f71321fba8 --- /dev/null +++ b/api/envoy/extensions/filters/http/proto_message_logging/v3/BUILD @@ -0,0 +1,13 @@ +# DO NOT EDIT. This file is generated by tools/proto_format/proto_sync.py. + +load("@envoy_api//bazel:api_build_system.bzl", "api_proto_package") + +licenses(["notice"]) # Apache 2 + +api_proto_package( + deps = [ + "//envoy/config/core/v3:pkg", + "@com_github_cncf_xds//udpa/annotations:pkg", + "@com_github_cncf_xds//xds/annotations/v3:pkg", + ], +) diff --git a/api/envoy/extensions/filters/http/proto_message_logging/v3/config.proto b/api/envoy/extensions/filters/http/proto_message_logging/v3/config.proto new file mode 100644 index 0000000000000..5b57e9c7d59a8 --- /dev/null +++ b/api/envoy/extensions/filters/http/proto_message_logging/v3/config.proto @@ -0,0 +1,255 @@ +syntax = "proto3"; + +package envoy.extensions.filters.http.proto_message_logging.v3; + +import "envoy/config/core/v3/base.proto"; + +import "xds/annotations/v3/status.proto"; + +import "udpa/annotations/status.proto"; + +option java_package = "io.envoyproxy.envoy.extensions.filters.http.proto_message_logging.v3"; +option java_outer_classname = "ConfigProto"; +option java_multiple_files = true; +option go_package = "github.com/envoyproxy/go-control-plane/envoy/extensions/filters/http/proto_message_logging/v3;proto_message_loggingv3"; +option (udpa.annotations.file_status).package_version_status = ACTIVE; +option (xds.annotations.v3.file_status).work_in_progress = true; + +// [#not-implemented-hide:] +// [#protodoc-title: Proto Message Logging] +// Proto Message Logging :ref:`configuration overview +// `. +// [#extension: envoy.filters.http.proto_message_logging] +// +// ProtoMessageLogging filter supports logging scrubbed gRPC requests/responses(proto messages) +// as google.protobuf.Struct and storing results +// in the dynamic metadata `envoy.filters.http.proto_message_logging` for later access. +// +// # Assumptions +// This filter assumes it is only applicable for gRPC with Protobuf as payload. +// +// # Process Flow +// On the request path, it will check +// +// 1. if the incoming gRPC request is configured, the filter tries to: +// +// a. buffer the incoming data to complete protobuf messages +// b. log individual protobuf messages according to directives +// c. write the result into the dynamic metadata. +// d. pass through the request data +// +// 2. otherwise, pass through the request. +// +// On the response path, it will check +// +// 1. if the incoming gRPC request is configured, the filter tries to: +// +// a. buffer the incoming data to complete protobuf messages +// b. log individual protobuf messages according to directives +// c. write the result into the dynamic metadata. +// d. pass through the response data +// +// 2. otherwise, pass through the response. +// +// # Config Requirements +// Here are config requirements +// +// 1. the log target field should be among the following primitive types: `string`, `uint32`, `uint64`, `int32`, `int64`, `sint32`, `sint64`, `fixed32`, `fixed64`, `sfixed32`, `sfixed64`, `float`, `double`. +// +// 2. the target field could be repeated. +// +// 3. the intermediate type could also be repeated. +// +// # Output Format +// The logged requests and responses will be will be added in the dynamic ``metadata`` with the same layout of the message. +// +// For the default `FIRST_AND_LAST` mode, it will be like: +// { +// "requests":{ +// "first":{ +// "foo": "val_foo1", +// ... +// } +// "last":{ +// "foo": "val_foo3", +// ... +// } +// }, +// "responses":{ +// "first":{ +// "baz": "val_baz1", +// ... +// } +// "last":{ +// "baz": "val_foo3", +// ... +// } +// } +// } +// +// +// # Example for `FIRST_AND_LAST` mode +// Let's say we have the following definition for the bi-streaming request +// `pkg.svc.Method`. +// +// .. code-block:: proto +// +// message MethodRequest { +// string foo = 1; +// Nested nested = 2; +// Msg redacted = 3; +// ... +// } +// +// message MethodResponse { +// string baz = 1; +// } +// +// message Nested { +// Msg double_nested = 2; +// } +// +// message Msg { +// string bar = 1; +// string not_logged = 2; +// } +// +// This is the filter config in JSON. +// +// .. code-block:: json +// +// { +// "descriptor_set":{}, +// "mode": "FIRST_AND_LAST", +// "logging_by_method":{ +// "pkg.svc.Method":{ +// "request_logging_by_field":{ +// "foo":"LOG", +// "nested.doubled_nested.bar":"LOG", +// "redacted":"LOG_REDACT" +// }, +// "response_logging_by_field":{ +// "bar":"LOG", +// } +// } +// } +// } +// +// During runtime, the filter receives the following `MethodRequest` message in +// JSON. +// +// .. code-block:: json +// +// { +// "foo": "val_foo1", +// "nested": { "double_nested": {"bar": "val_bar1", "not_logged": "val_not_logged1"}, +// "redacted": { "bar": "val_redacted_bar1"} +// } +// { +// "foo": "val_foo2", +// "nested": { "double_nested": {"bar": "val_bar2", "not_logged": "val_not_logged2"}, +// "redacted": { "bar": "val_redacted_bar2"} +// } +// { +// "foo": "val_foo3", +// "nested": { "double_nested": {"bar": "val_bar3", "not_logged": "val_not_logged3"}, +// "redacted": { "bar": "val_redacted_bar3"} +// } +// +// the filter receives the following `MethodResponse` message in +// JSON. +// +// .. code-block:: json +// +// { +// "baz": "val_baz1", +// } +// { +// "baz": "val_baz2", +// } +// { +// "baz": "val_baz3", +// } +// +// The filter will write the following dynamic +// metadata(`envoy.filters.http.proto_message_logging`) in JSON. +// +// .. code-block:: json +// +// { +// "requests":{ +// "first":{ +// "foo": "val_foo1", +// "nested": { "double_nested": {"bar": "val_bar1"}}, +// "redacted": {} +// } +// "last":{ +// "foo": "val_foo3", +// "nested": { "double_nested": {"bar": "val_bar3"}}, +// "redacted": {} +// } +// }, +// "responses":{ +// "first":{ +// "baz": "val_baz1" +// } +// "last":{ +// "baz": "val_foo3" +// } +// } +// } + +message ProtoMessageLoggingConfig { + enum LogMode { + LogMode_UNSPECIFIED = 0; + + // The filter will log the first and the last message for + // for streaming cases, containing + // client-side streaming, server-side streaming or bi-directional streaming. + FIRST_AND_LAST = 1; + } + + // The proto descriptor set binary for the gRPC services. + oneof descriptor_set { + // It could be passed by a local file through ``Datasource.filename`` or + // embedded in the ``Datasource.inline_bytes``. + config.core.v3.DataSource data_source = 1; + + // Unimplemented, the key of proto descriptor TypedMetadata. + // Among filters depending on the proto descriptor, we can have a TypedMetadata + // for proto descriptors, so that these filters can share one copy of proto + // descriptor in memory. + string proto_descriptor_typed_metadata = 2; + } + + LogMode mode = 3; + + // Specify the message logging info. + // The key is the fully qualified gRPC method name. + // ``${package}.${Service}.${Method}``, like + // ``endpoints.examples.bookstore.BookStore.GetShelf`` + // + // The value is the message logging information for individual gRPC methods. + map logging_by_method = 4; +} + +// This message can be used to support per route config approach later even +// though the Istio doesn't support that so far. +message MethodLogging { + enum LogDirective { + LogDirective_UNSPECIFIED = 0; + + // The value of this field will be logged. + LOG = 1; + + // It should be only annotated on Message type fields so if the field isn't + // empty, an empty Struct will be logged. + LOG_REDACT = 2; + } + + // The mapping of field path to its LogDirective for request messages + map request_logging_by_field = 2; + + // The mapping of field path to its LogDirective for response messages + map response_logging_by_field = 3; +} diff --git a/api/envoy/extensions/load_balancing_policies/least_request/v3/BUILD b/api/envoy/extensions/load_balancing_policies/least_request/v3/BUILD index b45c78410e7da..1ba2da7dfdc2d 100644 --- a/api/envoy/extensions/load_balancing_policies/least_request/v3/BUILD +++ b/api/envoy/extensions/load_balancing_policies/least_request/v3/BUILD @@ -6,6 +6,7 @@ licenses(["notice"]) # Apache 2 api_proto_package( deps = [ + "//envoy/annotations:pkg", "//envoy/config/core/v3:pkg", "//envoy/extensions/load_balancing_policies/common/v3:pkg", "@com_github_cncf_xds//udpa/annotations:pkg", diff --git a/api/envoy/extensions/load_balancing_policies/least_request/v3/least_request.proto b/api/envoy/extensions/load_balancing_policies/least_request/v3/least_request.proto index ebef61852e215..095f607528692 100644 --- a/api/envoy/extensions/load_balancing_policies/least_request/v3/least_request.proto +++ b/api/envoy/extensions/load_balancing_policies/least_request/v3/least_request.proto @@ -7,6 +7,7 @@ import "envoy/extensions/load_balancing_policies/common/v3/common.proto"; import "google/protobuf/wrappers.proto"; +import "envoy/annotations/deprecation.proto"; import "udpa/annotations/status.proto"; import "validate/validate.proto"; @@ -22,10 +23,34 @@ option (udpa.annotations.file_status).package_version_status = ACTIVE; // This configuration allows the built-in LEAST_REQUEST LB policy to be configured via the LB policy // extension point. See the :ref:`load balancing architecture overview // ` for more information. -// [#next-free-field: 6] +// [#next-free-field: 7] message LeastRequest { + // Available methods for selecting the host set from which to return the host with the + // fewest active requests. + enum SelectionMethod { + // Return host with fewest requests from a set of ``choice_count`` randomly selected hosts. + // Best selection method for most scenarios. + N_CHOICES = 0; + + // Return host with fewest requests from all hosts. + // Useful in some niche use cases involving low request rates and one of: + // (example 1) low request limits on workloads, or (example 2) few hosts. + // + // Example 1: Consider a workload type that can only accept one connection at a time. + // If such workloads are deployed across many hosts, only a small percentage of those + // workloads have zero connections at any given time, and the rate of new connections is low, + // the ``FULL_SCAN`` method is more likely to select a suitable host than ``N_CHOICES``. + // + // Example 2: Consider a workload type that is only deployed on 2 hosts. With default settings, + // the ``N_CHOICES`` method will return the host with more active requests 25% of the time. + // If the request rate is sufficiently low, the behavior of always selecting the host with least + // requests as of the last metrics refresh may be preferable. + FULL_SCAN = 1; + } + // The number of random healthy hosts from which the host with the fewest active requests will // be chosen. Defaults to 2 so that we perform two-choice selection if the field is not set. + // Only applies to the ``N_CHOICES`` selection method. google.protobuf.UInt32Value choice_count = 1 [(validate.rules).uint32 = {gte: 2}]; // The following formula is used to calculate the dynamic weights when hosts have different load @@ -61,8 +86,12 @@ message LeastRequest { common.v3.LocalityLbConfig locality_lb_config = 4; // [#not-implemented-hide:] - // Configuration for performing full scan on the list of hosts. - // If this configuration is set, when selecting the host a full scan on the list hosts will be - // used to select the one with least requests instead of using random choices. - google.protobuf.BoolValue enable_full_scan = 5; + // Unused. Replaced by the `selection_method` enum for better extensibility. + google.protobuf.BoolValue enable_full_scan = 5 + [deprecated = true, (envoy.annotations.deprecated_at_minor_version) = "3.0"]; + + // Method for selecting the host set from which to return the host with the fewest active requests. + // + // Defaults to ``N_CHOICES``. + SelectionMethod selection_method = 6 [(validate.rules).enum = {defined_only: true}]; } diff --git a/api/envoy/extensions/load_balancing_policies/ring_hash/v3/ring_hash.proto b/api/envoy/extensions/load_balancing_policies/ring_hash/v3/ring_hash.proto index b6583cc3a5cef..f154be55a7d1b 100644 --- a/api/envoy/extensions/load_balancing_policies/ring_hash/v3/ring_hash.proto +++ b/api/envoy/extensions/load_balancing_policies/ring_hash/v3/ring_hash.proto @@ -46,7 +46,8 @@ message RingHash { // provided host) the better the request distribution will reflect the desired weights. Defaults // to 1024 entries, and limited to 8M entries. See also // :ref:`maximum_ring_size`. - google.protobuf.UInt64Value minimum_ring_size = 2 [(validate.rules).uint64 = {lte: 8388608}]; + google.protobuf.UInt64Value minimum_ring_size = 2 + [(validate.rules).uint64 = {lte: 8388608 gte: 1}]; // Maximum hash ring size. Defaults to 8M entries, and limited to 8M entries, but can be lowered // to further constrain resource use. See also diff --git a/api/envoy/extensions/resource_monitors/downstream_connections/v3/BUILD b/api/envoy/extensions/resource_monitors/downstream_connections/v3/BUILD index d49202b74ab44..29ebf0741406e 100644 --- a/api/envoy/extensions/resource_monitors/downstream_connections/v3/BUILD +++ b/api/envoy/extensions/resource_monitors/downstream_connections/v3/BUILD @@ -5,8 +5,5 @@ load("@envoy_api//bazel:api_build_system.bzl", "api_proto_package") licenses(["notice"]) # Apache 2 api_proto_package( - deps = [ - "@com_github_cncf_xds//udpa/annotations:pkg", - "@com_github_cncf_xds//xds/annotations/v3:pkg", - ], + deps = ["@com_github_cncf_xds//udpa/annotations:pkg"], ) diff --git a/api/envoy/extensions/resource_monitors/downstream_connections/v3/downstream_connections.proto b/api/envoy/extensions/resource_monitors/downstream_connections/v3/downstream_connections.proto index 782acda56b4a0..5028fdf38208c 100644 --- a/api/envoy/extensions/resource_monitors/downstream_connections/v3/downstream_connections.proto +++ b/api/envoy/extensions/resource_monitors/downstream_connections/v3/downstream_connections.proto @@ -2,8 +2,6 @@ syntax = "proto3"; package envoy.extensions.resource_monitors.downstream_connections.v3; -import "xds/annotations/v3/status.proto"; - import "udpa/annotations/status.proto"; import "validate/validate.proto"; @@ -12,7 +10,6 @@ option java_outer_classname = "DownstreamConnectionsProto"; option java_multiple_files = true; option go_package = "github.com/envoyproxy/go-control-plane/envoy/extensions/resource_monitors/downstream_connections/v3;downstream_connectionsv3"; option (udpa.annotations.file_status).package_version_status = ACTIVE; -option (xds.annotations.v3.file_status).work_in_progress = true; // [#protodoc-title: Downstream connections] // [#extension: envoy.resource_monitors.downstream_connections] diff --git a/api/envoy/service/ext_proc/v3/external_processor.proto b/api/envoy/service/ext_proc/v3/external_processor.proto index 50fba503f8460..aa62ef74226da 100644 --- a/api/envoy/service/ext_proc/v3/external_processor.proto +++ b/api/envoy/service/ext_proc/v3/external_processor.proto @@ -56,7 +56,7 @@ service ExternalProcessor { // This represents the different types of messages that Envoy can send // to an external processing server. -// [#next-free-field: 8] +// [#next-free-field: 9] message ProcessingRequest { // Specify whether the filter that sent this request is running in synchronous // or asynchronous mode. The choice of synchronous or asynchronous mode @@ -91,30 +91,27 @@ message ProcessingRequest { // a BodyResponse message, an ImmediateResponse message, or close the stream. HttpBody request_body = 4; - // A chunk of the HTTP request body. Unless ``async_mode`` is ``true``, the server must send back + // A chunk of the HTTP response body. Unless ``async_mode`` is ``true``, the server must send back // a BodyResponse message or close the stream. HttpBody response_body = 5; // The HTTP trailers for the request path. Unless ``async_mode`` is ``true``, the server // must send back a TrailerResponse message or close the stream. // - // This message is only sent if the trailers processing mode is set to ``SEND``. - // If there are no trailers on the original downstream request, then this message - // will only be sent (with empty trailers waiting to be populated) if the - // processing mode is set before the request headers are sent, such as - // in the filter configuration. + // This message is only sent if the trailers processing mode is set to ``SEND`` and + // the original downstream request has trailers. HttpTrailers request_trailers = 6; // The HTTP trailers for the response path. Unless ``async_mode`` is ``true``, the server // must send back a TrailerResponse message or close the stream. // - // This message is only sent if the trailers processing mode is set to ``SEND``. - // If there are no trailers on the original downstream request, then this message - // will only be sent (with empty trailers waiting to be populated) if the - // processing mode is set before the request headers are sent, such as - // in the filter configuration. + // This message is only sent if the trailers processing mode is set to ``SEND`` and + // the original upstream response has trailers. HttpTrailers response_trailers = 7; } + + // Dynamic metadata associated with the request. + config.core.v3.Metadata metadata_context = 8; } // For every ProcessingRequest received by the server with the ``async_mode`` field @@ -158,9 +155,9 @@ message ProcessingResponse { ImmediateResponse immediate_response = 7; } - // [#not-implemented-hide:] - // Optional metadata that will be emitted as dynamic metadata to be consumed by the next - // filter. This metadata will be placed in the namespace ``envoy.filters.http.ext_proc``. + // Optional metadata that will be emitted as dynamic metadata to be consumed by + // following filters. This metadata will be placed in the namespace(s) specified by the top-level + // field name(s) of the struct. google.protobuf.Struct dynamic_metadata = 8; // Override how parts of the HTTP request and response are processed diff --git a/api/envoy/service/status/v3/csds.proto b/api/envoy/service/status/v3/csds.proto index b764f1cc3a4f7..1c51f2bac3795 100644 --- a/api/envoy/service/status/v3/csds.proto +++ b/api/envoy/service/status/v3/csds.proto @@ -185,6 +185,11 @@ message ClientConfig { // Represents generic xDS config and the exact config structure depends on // the type URL (like Cluster if it is CDS) repeated GenericXdsConfig generic_xds_configs = 3; + + // For xDS clients, the scope in which the data is used. + // For example, gRPC indicates the data plane target or that the data is + // associated with gRPC server(s). + string client_scope = 4; } message ClientStatusResponse { diff --git a/api/versioning/BUILD b/api/versioning/BUILD index 65ba4dc5c75f3..706d7d6f9d96b 100644 --- a/api/versioning/BUILD +++ b/api/versioning/BUILD @@ -141,6 +141,7 @@ proto_library( "//envoy/extensions/filters/http/oauth2/v3:pkg", "//envoy/extensions/filters/http/on_demand/v3:pkg", "//envoy/extensions/filters/http/original_src/v3:pkg", + "//envoy/extensions/filters/http/proto_message_logging/v3:pkg", "//envoy/extensions/filters/http/rate_limit_quota/v3:pkg", "//envoy/extensions/filters/http/ratelimit/v3:pkg", "//envoy/extensions/filters/http/rbac/v3:pkg", diff --git a/bazel/BUILD b/bazel/BUILD index 37eafa57eda10..775add0417bc3 100644 --- a/bazel/BUILD +++ b/bazel/BUILD @@ -699,6 +699,15 @@ selects.config_setting_group( ], ) +selects.config_setting_group( + name = "darwin_any", + match_any = [ + ":darwin", + ":darwin_arm64", + ":darwin_x86_64", + ], +) + selects.config_setting_group( name = "apple_dbg", match_all = [ diff --git a/bazel/dependency_imports.bzl b/bazel/dependency_imports.bzl index 2bd87a3717714..85843dc449725 100644 --- a/bazel/dependency_imports.bzl +++ b/bazel/dependency_imports.bzl @@ -27,7 +27,8 @@ def envoy_dependency_imports(go_version = GO_VERSION, jq_version = JQ_VERSION, y rules_foreign_cc_dependencies() go_rules_dependencies() go_register_toolchains(go_version) - envoy_download_go_sdks(go_version) + if go_version != "host": + envoy_download_go_sdks(go_version) gazelle_dependencies(go_sdk = "go_sdk") apple_rules_dependencies() pip_dependencies() @@ -146,6 +147,13 @@ def envoy_dependency_imports(go_version = GO_VERSION, jq_version = JQ_VERSION, y # use_category = ["api"], # source = "https://github.com/bufbuild/protoc-gen-validate/blob/v0.6.1/dependencies.bzl#L23-L28" ) + go_repository( + name = "com_github_planetscale_vtprotobuf", + importpath = "github.com/planetscale/vtprotobuf", + sum = "h1:nve54OLsoKDQhb8ZnnHHUyvAK3vjBiwTEJeC3UsqzJ8=", + version = "v0.5.1-0.20231205081218-d930d8ac92f8", + build_external = "external", + ) protoc_gen_jsonschema_go_dependencies() diff --git a/bazel/foreign_cc/BUILD b/bazel/foreign_cc/BUILD index eb9c9e81d2c4e..d80b6b2182937 100644 --- a/bazel/foreign_cc/BUILD +++ b/bazel/foreign_cc/BUILD @@ -498,17 +498,24 @@ envoy_cmake( envoy_cmake( name = "wamr", cache_entries = { + # interp by default + # if want to gain more performance advantage with JIT or AOT + # please refer to https://github.com/proxy-wasm/proxy-wasm-cpp-host "WAMR_BUILD_AOT": "0", "WAMR_BUILD_FAST_INTERP": "1", "WAMR_BUILD_INTERP": "1", "WAMR_BUILD_JIT": "0", + # disable WASI "WAMR_BUILD_LIBC_WASI": "0", - "WAMR_BUILD_MULTI_MODULE": "0", + "WAMR_BUILD_LIBC_BUILTIN": "0", + # MVP + "WAMR_BUILD_BULK_MEMORY": "1", + "WAMR_BUILD_REF_TYPES": "1", "WAMR_BUILD_SIMD": "0", "WAMR_BUILD_TAIL_CALL": "1", + # others "WAMR_BUILD_WASM_CACHE": "0", - "WAMR_DISABLE_HW_BOUND_CHECK": "0", - "WAMR_DISABLE_STACK_HW_BOUND_CHECK": "1", + "WAMR_BUILD_MULTI_MODULE": "0", }, lib_source = "@com_github_wamr//:all", out_static_libs = ["libvmlib.a"], @@ -617,10 +624,11 @@ envoy_cmake( ) envoy_cc_library( - name = "maxmind_linux", + name = "maxmind_linux_darwin", srcs = [], deps = select({ "//bazel:linux": [":maxmind"], + "//bazel:darwin_any": [":maxmind"], "//conditions:default": [], }), ) diff --git a/bazel/python_dependencies.bzl b/bazel/python_dependencies.bzl index c3af1865cad04..ea50bf30ba386 100644 --- a/bazel/python_dependencies.bzl +++ b/bazel/python_dependencies.bzl @@ -7,16 +7,6 @@ def envoy_python_dependencies(): load_packages() pip_parse( name = "base_pip3", - experimental_requirement_cycles = { - "sphinx": [ - "sphinx", - "sphinxcontrib-serializinghtml", - "sphinxcontrib-qthelp", - "sphinxcontrib-htmlhelp", - "sphinxcontrib-devhelp", - "sphinxcontrib-applehelp", - ], - }, python_interpreter_target = interpreter, requirements_lock = "@envoy//tools/base:requirements.txt", extra_pip_args = ["--require-hashes"], diff --git a/bazel/repositories.bzl b/bazel/repositories.bzl index aa93c9c838d8a..580dc80813a16 100644 --- a/bazel/repositories.bzl +++ b/bazel/repositories.bzl @@ -18,6 +18,7 @@ WINDOWS_SKIP_TARGETS = [ "envoy.access_loggers.extension_filters.cel", "envoy.rate_limit_descriptors.expr", "envoy.filters.http.rate_limit_quota", + "envoy.filters.http.ext_proc", "envoy.formatter.cel", "envoy.matching.inputs.cel_data_input", "envoy.matching.matchers.cel_matcher", @@ -1479,5 +1480,5 @@ def _com_github_maxmind_libmaxminddb(): ) native.bind( name = "maxmind", - actual = "@envoy//bazel/foreign_cc:maxmind_linux", + actual = "@envoy//bazel/foreign_cc:maxmind_linux_darwin", ) diff --git a/bazel/repository_locations.bzl b/bazel/repository_locations.bzl index 8f66e5f194db8..6ab8f8529fa99 100644 --- a/bazel/repository_locations.bzl +++ b/bazel/repository_locations.bzl @@ -148,12 +148,12 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "Aspect Bazel helpers", project_desc = "Base Starlark libraries and basic Bazel rules which are useful for constructing rulesets and BUILD files", project_url = "https://github.com/aspect-build/bazel-lib", - version = "2.2.0", - sha256 = "8d71a578e4e1b6a54aea7598ebfbd8fc9e3be5da881ff9d2b80249577b933a40", + version = "2.3.0", + sha256 = "bda4a69fa50411b5feef473b423719d88992514d259dadba7d8218a1d02c7883", strip_prefix = "bazel-lib-{version}", urls = ["https://github.com/aspect-build/bazel-lib/archive/v{version}.tar.gz"], use_category = ["build"], - release_date = "2024-01-08", + release_date = "2024-01-10", cpe = "N/A", license = "Apache-2.0", license_url = "https://github.com/aspect-build/bazel-lib/blob/v{version}/LICENSE", @@ -176,11 +176,11 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "Shellcheck rules for bazel", project_desc = "Now you do not need to depend on the system shellcheck version in your bazel-managed (mono)repos.", project_url = "https://github.com/aignas/rules_shellcheck", - version = "0.2.4", - sha256 = "ce4d0e7a9beb1fb3f0d37424465060491a91dae68de1ef1c92ee57d94c773b46", + version = "0.3.2", + sha256 = "798c7ff488a949e51d7d41d853d79164ce5c5335364ba32f972b79df8dd6be62", strip_prefix = "rules_shellcheck-{version}", urls = ["https://github.com/aignas/rules_shellcheck/archive/{version}.tar.gz"], - release_date = "2023-10-27", + release_date = "2024-01-10", use_category = ["build"], cpe = "N/A", license = "MIT", @@ -204,12 +204,12 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "Perfetto", project_desc = "Perfetto Tracing SDK", project_url = "https://perfetto.dev/", - version = "40.0", - sha256 = "bd78f0165e66026c31c8c39221ed2863697a8bba5cd39b12e4b43d0b7f71626f", + version = "41.0", + sha256 = "4c8fe8a609fcc77ca653ec85f387ab6c3a048fcd8df9275a1aa8087984b89db8", strip_prefix = "perfetto-{version}/sdk", urls = ["https://github.com/google/perfetto/archive/v{version}.tar.gz"], use_category = ["dataplane_core", "controlplane"], - release_date = "2023-12-05", + release_date = "2024-01-11", cpe = "N/A", license = "Apache-2.0", license_url = "https://github.com/google/perfetto/blob/v{version}/LICENSE", @@ -306,12 +306,12 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "spdlog", project_desc = "Very fast, header-only/compiled, C++ logging library", project_url = "https://github.com/gabime/spdlog", - version = "1.12.0", - sha256 = "4dccf2d10f410c1e2feaff89966bfc49a1abb29ef6f08246335b110e001e09a9", + version = "1.13.0", + sha256 = "534f2ee1a4dcbeb22249856edfb2be76a1cf4f708a20b0ac2ed090ee24cfdbc9", strip_prefix = "spdlog-{version}", urls = ["https://github.com/gabime/spdlog/archive/v{version}.tar.gz"], use_category = ["dataplane_core", "controlplane"], - release_date = "2023-07-08", + release_date = "2024-01-12", cpe = "N/A", license = "MIT", license_url = "https://github.com/gabime/spdlog/blob/v{version}/LICENSE", @@ -489,12 +489,12 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "Nghttp2", project_desc = "Implementation of HTTP/2 and its header compression algorithm HPACK in C", project_url = "https://nghttp2.org", - version = "1.58.0", - sha256 = "9ebdfbfbca164ef72bdf5fd2a94a4e6dfb54ec39d2ef249aeb750a91ae361dfb", + version = "1.59.0", + sha256 = "90fd27685120404544e96a60ed40398a3457102840c38e7215dc6dec8684470f", strip_prefix = "nghttp2-{version}", urls = ["https://github.com/nghttp2/nghttp2/releases/download/v{version}/nghttp2-{version}.tar.gz"], use_category = ["controlplane", "dataplane_core"], - release_date = "2023-10-27", + release_date = "2024-01-21", cpe = "cpe:2.3:a:nghttp2:nghttp2:*", license = "MIT", license_url = "https://github.com/nghttp2/nghttp2/blob/v{version}/LICENSE", @@ -988,9 +988,9 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "Python rules for Bazel", project_desc = "Bazel rules for the Python language", project_url = "https://github.com/bazelbuild/rules_python", - version = "0.28.0", - sha256 = "d70cd72a7a4880f0000a6346253414825c19cdd40a28289bdf67b8e6480edff8", - release_date = "2024-01-08", + version = "0.29.0", + sha256 = "d71d2c67e0bce986e1c5a7731b4693226867c45bfe0b7c5e0067228a536fc580", + release_date = "2024-01-22", strip_prefix = "rules_python-{version}", urls = ["https://github.com/bazelbuild/rules_python/archive/{version}.tar.gz"], use_category = ["build"], @@ -1048,11 +1048,11 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "Webassembly Micro Runtime", project_desc = "A standalone runtime with a small footprint for WebAssembly", project_url = "https://github.com/bytecodealliance/wasm-micro-runtime", - version = "WAMR-1.2.2", - sha256 = "d328fc1e19c54cfdb4248b861de54b62977b9b85c0a40eaaeb9cd9b628c0c788", + version = "WAMR-1.3.2", + sha256 = "58961ba387ed66ace2dd903597f1670a42b8154a409757ae6f06f43fe867a98c", strip_prefix = "wasm-micro-runtime-{version}", urls = ["https://github.com/bytecodealliance/wasm-micro-runtime/archive/{version}.tar.gz"], - release_date = "2023-05-16", + release_date = "2024-02-02", use_category = ["dataplane_ext"], extensions = ["envoy.wasm.runtime.wamr"], cpe = "N/A", @@ -1175,12 +1175,12 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "QUICHE", project_desc = "QUICHE (QUIC, HTTP/2, Etc) is Google‘s implementation of QUIC and related protocols", project_url = "https://github.com/google/quiche", - version = "83a9e81296b36898025bce1110db9f9c4f23afd3", - sha256 = "0bc1ca361439140b8c8add9bceb9478a037e87954bd9d22e819bf73818443026", + version = "b5d556774fb971506e5912a357f0f8fb8ef08d12", + sha256 = "f600af67bfccec4a0e8b88f721371756429975b1956269ae034ce08247ae55bd", urls = ["https://github.com/google/quiche/archive/{version}.tar.gz"], strip_prefix = "quiche-{version}", use_category = ["controlplane", "dataplane_core"], - release_date = "2024-01-12", + release_date = "2024-02-01", cpe = "N/A", license = "BSD-3-Clause", license_url = "https://github.com/google/quiche/blob/{version}/LICENSE", @@ -1214,6 +1214,7 @@ REPOSITORY_LOCATIONS_SPEC = dict( "envoy.access_loggers.wasm", "envoy.bootstrap.wasm", "envoy.rate_limit_descriptors.expr", + "envoy.filters.http.ext_proc", "envoy.filters.http.rate_limit_quota", "envoy.filters.http.rbac", "envoy.filters.http.wasm", @@ -1243,6 +1244,7 @@ REPOSITORY_LOCATIONS_SPEC = dict( "envoy.formatter.cel", "envoy.bootstrap.wasm", "envoy.rate_limit_descriptors.expr", + "envoy.filters.http.ext_proc", "envoy.filters.http.rate_limit_quota", "envoy.filters.http.rbac", "envoy.filters.http.wasm", @@ -1504,11 +1506,11 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "rules_license", project_desc = "Bazel rules for checking open source licenses", project_url = "https://github.com/bazelbuild/rules_license", - version = "0.0.7", - sha256 = "4531deccb913639c30e5c7512a054d5d875698daeb75d8cf90f284375fe7c360", + version = "0.0.8", + sha256 = "241b06f3097fd186ff468832150d6cc142247dc42a32aaefb56d0099895fd229", urls = ["https://github.com/bazelbuild/rules_license/releases/download/{version}/rules_license-{version}.tar.gz"], use_category = ["build", "dataplane_core", "controlplane"], - release_date = "2023-06-16", + release_date = "2024-01-24", cpe = "N/A", license = "Apache-2.0", license_url = "https://github.com/bazelbuild/rules_license/blob/{version}/LICENSE", @@ -1531,13 +1533,13 @@ REPOSITORY_LOCATIONS_SPEC = dict( project_name = "maxmind_libmaxminddb", project_desc = "C library for reading MaxMind DB files", project_url = "https://github.com/maxmind/libmaxminddb", - version = "1.8.0", - sha256 = "1107799f77be6aa3b9796ad0eed8ffcc334bf45f8bd18e6a984d8adf3e719c6d", + version = "1.9.1", + sha256 = "a80682a89d915fdf60b35d316232fb04ebf36fff27fda9bd39fe8a38d3cd3f12", strip_prefix = "libmaxminddb-{version}", urls = ["https://github.com/maxmind/libmaxminddb/releases/download/{version}/libmaxminddb-{version}.tar.gz"], use_category = ["dataplane_ext"], extensions = ["envoy.geoip_providers.maxmind"], - release_date = "2023-11-07", + release_date = "2024-01-10", cpe = "cpe:2.3:a:maxmind:libmaxminddb:*", license = "Apache-2.0", license_url = "https://github.com/maxmind/libmaxminddb/blob/{version}/LICENSE", diff --git a/changelogs/current.yaml b/changelogs/current.yaml index 9ecf0d6e48ce5..a390360cee069 100644 --- a/changelogs/current.yaml +++ b/changelogs/current.yaml @@ -5,13 +5,108 @@ behavior_changes: minor_behavior_changes: # *Changes that may cause incompatibilities for some users, but should not for most* +- area: adaptive concurrency filter stats + change: | + Multiply the gradient value stat by 1000 to make it more granular (values will range between 500 and 2000). +- area: dns + change: | + Allowing ` to go as low as 1s. +- area: upstream + change: | + Upstream now excludes hosts set to ``DRAINING`` state via EDS from load balancing and panic routing + threshold calculation. This feature can be disabled by setting + ``envoy.reloadable_features.exclude_host_in_eds_status_draining`` to false. +- area: golang + change: | + Change ``RegisterHttpFilterConfigFactoryAndParser`` to ``RegisterHttpFilterFactoryAndConfigParser``. bug_fixes: # *Changes expected to improve the state of the world and are unlikely to have negative effects* +- area: tracers + change: | + use unary RPC calls for OpenTelemetry trace exports, rather than client-side streaming connections. +- area: load balancing + change: | + Added randomization in locality load-balancing initialization. This helps desynchronizing Envoys across + a fleet by randomizing the scheduler starting point. This can be temporarily reverted by setting runtime guard + ``envoy.reloadable_features.edf_lb_locality_scheduler_init_fix`` to false. +- area: UDP and TCP tunneling + change: | + fixed a bug where second HTTP response headers received would cause Envoy to crash in cases where + ``propagate_response_headers`` and retry configurations are enabled at the same time, and an upstream + request is retried multiple times. removed_config_or_runtime: # *Normally occurs at the end of the* :ref:`deprecation period ` +- area: http + change: | + Removed ``envoy.reloadable_features.allow_absolute_url_with_mixed_scheme`` runtime flag and legacy code paths. +- area: active health check + change: | + Removed ``envoy.reloadable_features.keep_endpoint_active_hc_status_on_locality_update`` runtime flag and legacy code paths. +- area: http1 + change: | + Removed ``envoy.reloadable_features.http1_allow_codec_error_response_after_1xx_headers`` runtime flag and legacy code paths. +- area: overload manager + change: | + removed ``envoy.reloadable_features.overload_manager_error_unknown_action`` and legacy code paths. +- area: http + change: | + Removed ``envoy_reloadable_features_append_xfh_idempotent`` runtime flag and legacy code paths. +- area: resource_monitors + change: | + removed ``envoy.reloadable_features.count_unused_mapped_pages_as_free`` runtime flag and legacy code paths. new_features: +- area: aws_request_signing + change: | + Update ``aws_request_signing`` filter to support use as an upstream HTTP filter. This allows successful calculation of + signatures after the forwarding stage has completed, particularly if the path element is modified. +- area: grpc reverse bridge + change: | + Change HTTP status to 200 to respect the gRPC protocol. This may cause problems for incorrect gRPC clients expecting the filter + to preserve HTTP 1.1 responses. This behavioral change can be temporarily reverted by setting runtime guard + ``envoy.reloadable_features.grpc_http1_reverse_bridge_change_http_status`` to false. +- area: quic + change: | + Added QUIC protocol option :ref:`send_disable_active_migration + ` to make the server send clients a transport + parameter to discourage client endpoints from active migration. +- area: ext_proc + change: | + implemented + :ref:`request_attributes ` + and + :ref:`response_attributes ` + config APIs to enable sending and receiving attributes to/from the external processing server. +- area: access log + change: | + added support for :ref:`%UPSTREAM_CONNECTION_ID% ` for the upstream connection + identifier. +- area: ext_proc + change: | + added + :ref:`metadata_options ` + config API to enable sending and receiving metadata from/to the external processing server. Both typed and untyped dynamic + metadata may be sent to the server. If + :ref:`receiving_namespaces ` + is defined, returned metadata may be written to the specified allowed namespaces. +- area: monitoring + change: | + Add ``Envoy::ExecutionContext``, which is notified by ``ScopeTrackerScopeState``'s constructor and destructor. This feature is + disabled by default, it can be enabled by runtime feature flag ``envoy.restart_features.enable_execution_context``. For more details, + please see https://github.com/envoyproxy/envoy/issues/32012. +- area: rbac + change: | + Added :ref:`uri_template` which uses existing + :ref:`UriTemplateMatchConfig` + to allow use of glob patterns for URI path matching in RBAC. +- area: upstream + change: | + Added :ref:`selection_method ` + option to the least request load balancer. If set to ``FULL_SCAN``, + Envoy will select the host with the fewest active requests from the entire host set rather than + :ref:`choice_count ` + random choices. deprecated: diff --git a/ci/Dockerfile-envoy b/ci/Dockerfile-envoy index 10e95e2fbcfb2..06148a388eb0f 100644 --- a/ci/Dockerfile-envoy +++ b/ci/Dockerfile-envoy @@ -1,5 +1,5 @@ ARG BUILD_OS=ubuntu -ARG BUILD_TAG=22.04@sha256:6042500cf4b44023ea1894effe7890666b0c5c7871ed83a97c36c76ae560bb9b +ARG BUILD_TAG=22.04@sha256:e9569c25505f33ff72e88b2990887c9dcf230f23259da296eb814fc2b41af999 ARG ENVOY_VRP_BASE_IMAGE=envoy-base @@ -58,7 +58,7 @@ COPY --chown=0:0 --chmod=755 \ # STAGE: envoy-distroless -FROM gcr.io/distroless/base-nossl-debian12:nonroot@sha256:8c957f0c06030921ee439d028b5778dd1cee9e095092833fe8e4ee795d3a2298 AS envoy-distroless +FROM gcr.io/distroless/base-nossl-debian12:nonroot@sha256:51ab103bb161fdf8fee4c6311a2d41f484effc409d4f4c58342ab68b2da7ccc2 AS envoy-distroless EXPOSE 10000 ENTRYPOINT ["/usr/local/bin/envoy"] CMD ["-c", "/etc/envoy/envoy.yaml"] diff --git a/ci/do_ci.sh b/ci/do_ci.sh index e500dd8792a4e..1c04c4250292c 100755 --- a/ci/do_ci.sh +++ b/ci/do_ci.sh @@ -308,6 +308,13 @@ case $CI_TARGET in if [[ "$GO_FILE" = *.validate.go ]]; then sed -i '1s;^;//go:build !disable_pgv\n;' "$OUTPUT_DIR/$(basename "$GO_FILE")" fi + # TODO(https://github.com/planetscale/vtprotobuf/pull/122) do this directly in the generator. + # Make vtprotobuf opt-in as it has some impact on binary sizes + if [[ "$GO_FILE" = *_vtproto.pb.go ]]; then + if ! grep -q 'package ignore' "$GO_FILE"; then + sed -i '1s;^;//go:build vtprotobuf\n// +build vtprotobuf\n;' "$OUTPUT_DIR/$(basename "$GO_FILE")" + fi + fi done <<< "$(find "$INPUT_DIR" -name "*.go")" done ;; diff --git a/contrib/all_contrib_extensions.bzl b/contrib/all_contrib_extensions.bzl index 9d490cc790995..19c605b700bbd 100644 --- a/contrib/all_contrib_extensions.bzl +++ b/contrib/all_contrib_extensions.bzl @@ -28,5 +28,9 @@ PPC_SKIP_CONTRIB_TARGETS = [ "envoy.compression.qatzip.compressor", ] +FIPS_SKIP_CONTRIB_TARGETS = [ + "envoy.compression.qatzip.compressor", +] + def envoy_all_contrib_extensions(denylist = []): return [v + "_envoy_extension" for k, v in CONTRIB_EXTENSIONS.items() if not k in denylist] diff --git a/contrib/client_ssl_auth/filters/network/source/client_ssl_auth.cc b/contrib/client_ssl_auth/filters/network/source/client_ssl_auth.cc index f0c28dbd0d4d3..bb4cbcfa4976a 100644 --- a/contrib/client_ssl_auth/filters/network/source/client_ssl_auth.cc +++ b/contrib/client_ssl_auth/filters/network/source/client_ssl_auth.cc @@ -127,7 +127,7 @@ void ClientSslAuthFilter::onEvent(Network::ConnectionEvent event) { if (!config_->allowedPrincipals().allowed( read_callbacks_->connection().ssl()->sha256PeerCertificateDigest())) { read_callbacks_->connection().streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UpstreamProtocolError); + StreamInfo::CoreResponseFlag::UpstreamProtocolError); read_callbacks_->connection().streamInfo().setResponseCodeDetails(AuthDigestNoMatch); config_->stats().auth_digest_no_match_.inc(); read_callbacks_->connection().close(Network::ConnectionCloseType::NoFlush); diff --git a/contrib/client_ssl_auth/filters/network/test/client_ssl_auth_test.cc b/contrib/client_ssl_auth/filters/network/test/client_ssl_auth_test.cc index b6b1aa25a786a..69a3ddb0452e5 100644 --- a/contrib/client_ssl_auth/filters/network/test/client_ssl_auth_test.cc +++ b/contrib/client_ssl_auth/filters/network/test/client_ssl_auth_test.cc @@ -164,7 +164,7 @@ TEST_F(ClientSslAuthFilterTest, Ssl) { std::string expected_sha_1("digest"); EXPECT_CALL(*ssl_, sha256PeerCertificateDigest()).WillOnce(ReturnRef(expected_sha_1)); EXPECT_CALL(filter_callbacks_.connection_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamProtocolError)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamProtocolError)); EXPECT_CALL(filter_callbacks_.connection_.stream_info_, setResponseCodeDetails("auth_digest_no_match")); EXPECT_CALL(filter_callbacks_.connection_, close(Network::ConnectionCloseType::NoFlush)); diff --git a/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.cc b/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.cc index 82d1bd4a5a5c1..313f93099b90c 100644 --- a/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.cc +++ b/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.cc @@ -29,6 +29,57 @@ void CryptoMbContext::scheduleCallback(enum RequestStatus status) { schedulable_->scheduleCallbackNextIteration(); } +bool CryptoMbEcdsaContext::ecdsaInit(const uint8_t* in, size_t in_len) { + if (ec_key_ == nullptr) { + return false; + } + + const EC_GROUP* group = EC_KEY_get0_group(ec_key_.get()); + priv_key_ = EC_KEY_get0_private_key(ec_key_.get()); + if (group == nullptr || priv_key_ == nullptr) { + return false; + } + + const BIGNUM* order = EC_GROUP_get0_order(group); + if (order == nullptr) { + return false; + } + + // Create an ephemeral key. + ctx_ = bssl::UniquePtr(BN_CTX_new()); + if (ctx_ == nullptr) { + return false; + } + BN_CTX_start(ctx_.get()); + k_ = BN_CTX_get(ctx_.get()); + if (!k_) { + return false; + } + do { + if (!BN_rand_range(k_, order)) { + return false; + } + } while (BN_is_zero(k_)); + + // Extent with zero paddings as CryptoMB expects in_buf_ being sign length. + int len = BN_num_bits(order); + size_t buf_len = (len + 7) / 8; + if (8 * in_len < static_cast(len)) { + in_buf_ = std::make_unique(buf_len); + memcpy(in_buf_.get() + buf_len - in_len, in, in_len); // NOLINT(safe-memcpy) + } else { + in_buf_ = std::make_unique(in_len); + memcpy(in_buf_.get(), in, in_len); // NOLINT(safe-memcpy) + } + + sig_len_ = ECDSA_size(ec_key_.get()); + if (sig_len_ > MAX_SIGNATURE_SIZE) { + return false; + } + + return true; +} + bool CryptoMbRsaContext::rsaInit(const uint8_t* in, size_t in_len) { if (rsa_ == nullptr) { return false; @@ -70,13 +121,11 @@ int calculateDigest(const EVP_MD* md, const uint8_t* in, size_t in_len, unsigned return 1; } -ssl_private_key_result_t ecdsaPrivateKeySignInternal(CryptoMbPrivateKeyConnection* ops, - uint8_t* out, size_t* out_len, size_t max_out, - uint16_t signature_algorithm, +ssl_private_key_result_t ecdsaPrivateKeySignInternal(CryptoMbPrivateKeyConnection* ops, uint8_t*, + size_t*, size_t, uint16_t signature_algorithm, const uint8_t* in, size_t in_len) { unsigned char hash[EVP_MAX_MD_SIZE]; unsigned int hash_len; - unsigned int out_len_unsigned; if (ops == nullptr) { return ssl_private_key_failure; @@ -105,20 +154,17 @@ ssl_private_key_result_t ecdsaPrivateKeySignInternal(CryptoMbPrivateKeyConnectio return ssl_private_key_failure; } - if (max_out < ECDSA_size(ec_key.get())) { - return ssl_private_key_failure; - } + // Create MB context which will be used for this particular + // signing/decryption. + CryptoMbEcdsaContextSharedPtr mb_ctx = + std::make_shared(std::move(ec_key), ops->dispatcher_, ops->cb_); - // Borrow "out" because it has been already initialized to the max_out size. - if (!ECDSA_sign(0, hash, hash_len, out, &out_len_unsigned, ec_key.get())) { + if (!mb_ctx->ecdsaInit(hash, hash_len)) { return ssl_private_key_failure; } - if (out_len_unsigned > max_out) { - return ssl_private_key_failure; - } - *out_len = out_len_unsigned; - return ssl_private_key_success; + ops->addToQueue(mb_ctx); + return ssl_private_key_retry; } ssl_private_key_result_t ecdsaPrivateKeySign(SSL* ssl, uint8_t* out, size_t* out_len, @@ -386,10 +432,16 @@ void CryptoMbQueue::addAndProcessEightRequests(CryptoMbContextSharedPtr mb_ctx) } void CryptoMbQueue::processRequests() { - if (type_ == KeyType::Rsa) { + switch (type_) { + case KeyType::Rsa: // Record queue size statistic value for histogram. stats_.rsa_queue_sizes_.recordValue(request_queue_.size()); processRsaRequests(); + break; + case KeyType::Ec: + // Record queue size statistic value for histogram. + stats_.ecdsa_queue_sizes_.recordValue(request_queue_.size()); + processEcdsaRequests(); } request_queue_.clear(); } @@ -466,6 +518,80 @@ void CryptoMbQueue::processRsaRequests() { } } +void CryptoMbQueue::processEcdsaRequests() { + uint8_t sig_r[MULTIBUFF_BATCH][32]; + uint8_t sig_s[MULTIBUFF_BATCH][32]; + uint8_t* pa_sig_r[MULTIBUFF_BATCH] = {sig_r[0], sig_r[1], sig_r[2], sig_r[3], + sig_r[4], sig_r[5], sig_r[6], sig_r[7]}; + uint8_t* pa_sig_s[MULTIBUFF_BATCH] = {sig_s[0], sig_s[1], sig_s[2], sig_s[3], + sig_s[4], sig_s[5], sig_s[6], sig_s[7]}; + const unsigned char* digest[MULTIBUFF_BATCH] = {nullptr}; + const BIGNUM* eph_key[MULTIBUFF_BATCH] = {nullptr}; + const BIGNUM* priv_key[MULTIBUFF_BATCH] = {nullptr}; + + /* Build arrays of pointers for call */ + for (unsigned req_num = 0; req_num < request_queue_.size(); req_num++) { + CryptoMbEcdsaContextSharedPtr mb_ctx = + std::static_pointer_cast(request_queue_[req_num]); + digest[req_num] = mb_ctx->in_buf_.get(); + eph_key[req_num] = mb_ctx->k_; + priv_key[req_num] = mb_ctx->priv_key_; + } + + ENVOY_LOG(debug, "Multibuffer ECDSA process {} requests", request_queue_.size()); + + uint32_t ecdsa_sts = + ipp_->mbxNistp256EcdsaSignSslMb8(pa_sig_r, pa_sig_s, digest, eph_key, priv_key); + + enum RequestStatus status[MULTIBUFF_BATCH] = {RequestStatus::Retry}; + + for (unsigned req_num = 0; req_num < request_queue_.size(); req_num++) { + CryptoMbEcdsaContextSharedPtr mb_ctx = + std::static_pointer_cast(request_queue_[req_num]); + enum RequestStatus ctx_status; + if (ipp_->mbxGetSts(ecdsa_sts, req_num)) { + ENVOY_LOG(debug, "Multibuffer ECDSA request {} success", req_num); + if (postprocessEcdsaRequest(mb_ctx, pa_sig_r[req_num], pa_sig_s[req_num])) { + status[req_num] = RequestStatus::Success; + } else { + status[req_num] = RequestStatus::Error; + } + } else { + ENVOY_LOG(debug, "Multibuffer ECDSA request {} failure", req_num); + status[req_num] = RequestStatus::Error; + } + + ctx_status = status[req_num]; + mb_ctx->scheduleCallback(ctx_status); + + // End context to invalid the ephemeral key. + BN_CTX_end(mb_ctx->ctx_.get()); + } +} + +bool CryptoMbQueue::postprocessEcdsaRequest(CryptoMbEcdsaContextSharedPtr mb_ctx, + const uint8_t* pa_sig_r, const uint8_t* pa_sig_s) { + ECDSA_SIG* sig = ECDSA_SIG_new(); + if (sig == nullptr) { + return false; + } + BIGNUM* sig_r = BN_bin2bn(pa_sig_r, 32, nullptr); + BIGNUM* sig_s = BN_bin2bn(pa_sig_s, 32, nullptr); + ECDSA_SIG_set0(sig, sig_r, sig_s); + + // Marshal signature into out_buf_. + CBB cbb; + if (!CBB_init_fixed(&cbb, mb_ctx->out_buf_, mb_ctx->sig_len_) || !ECDSA_SIG_marshal(&cbb, sig) || + !CBB_finish(&cbb, nullptr, &mb_ctx->out_len_)) { + CBB_cleanup(&cbb); + ECDSA_SIG_free(sig); + return false; + } + + ECDSA_SIG_free(sig); + return true; +} + CryptoMbPrivateKeyConnection::CryptoMbPrivateKeyConnection(Ssl::PrivateKeyConnectionCallbacks& cb, Event::Dispatcher& dispatcher, bssl::UniquePtr pkey, diff --git a/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.h b/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.h index cbd7a42d53662..b3da76dab5a8e 100644 --- a/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.h +++ b/contrib/cryptomb/private_key_providers/source/cryptomb_private_key_provider.h @@ -57,6 +57,26 @@ class CryptoMbContext { Event::SchedulableCallbackPtr schedulable_{}; }; +// CryptoMbEcdsaContext is a CryptoMbContext which holds the extra ECDSA parameters and has +// custom initialization function. +class CryptoMbEcdsaContext : public CryptoMbContext { +public: + CryptoMbEcdsaContext(bssl::UniquePtr ec_key, Event::Dispatcher& dispatcher, + Ssl::PrivateKeyConnectionCallbacks& cb) + : CryptoMbContext(dispatcher, cb), ec_key_(std::move(ec_key)) {} + bool ecdsaInit(const uint8_t* in, size_t in_len); + + // ECDSA key. + bssl::UniquePtr ec_key_{}; + // ECDSA context to create the ephemeral key k_. + bssl::UniquePtr ctx_{}; + BIGNUM* k_{}; + // ECDSA parameters, which will contain values whose memory is managed within + // BoringSSL ECDSA key structure, so not wrapped in smart pointers. + const BIGNUM* priv_key_{}; + size_t sig_len_{}; +}; + // CryptoMbRsaContext is a CryptoMbContext which holds the extra RSA parameters and has // custom initialization function. It also has a separate buffer for RSA result // verification. @@ -86,6 +106,7 @@ class CryptoMbRsaContext : public CryptoMbContext { }; using CryptoMbContextSharedPtr = std::shared_ptr; +using CryptoMbEcdsaContextSharedPtr = std::shared_ptr; using CryptoMbRsaContextSharedPtr = std::shared_ptr; // CryptoMbQueue maintains the request queue and is able to process it. @@ -101,6 +122,9 @@ class CryptoMbQueue : public Logger::Loggable { private: void processRequests(); void processRsaRequests(); + void processEcdsaRequests(); + bool postprocessEcdsaRequest(CryptoMbEcdsaContextSharedPtr mb_ctx, const uint8_t* sign_r, + const uint8_t* sign_s); void startTimer(); void stopTimer(); diff --git a/contrib/cryptomb/private_key_providers/source/cryptomb_stats.h b/contrib/cryptomb/private_key_providers/source/cryptomb_stats.h index ac47256bf756c..a1dea004d5464 100644 --- a/contrib/cryptomb/private_key_providers/source/cryptomb_stats.h +++ b/contrib/cryptomb/private_key_providers/source/cryptomb_stats.h @@ -8,7 +8,9 @@ namespace Extensions { namespace PrivateKeyMethodProvider { namespace CryptoMb { -#define ALL_CRYPTOMB_STATS(HISTOGRAM) HISTOGRAM(rsa_queue_sizes, Unspecified) +#define ALL_CRYPTOMB_STATS(HISTOGRAM) \ + HISTOGRAM(ecdsa_queue_sizes, Unspecified) \ + HISTOGRAM(rsa_queue_sizes, Unspecified) /** * CryptoMb stats struct definition. @see stats_macros.h diff --git a/contrib/cryptomb/private_key_providers/source/ipp_crypto.h b/contrib/cryptomb/private_key_providers/source/ipp_crypto.h index d33d02270b4aa..ed0ef7bf3162d 100644 --- a/contrib/cryptomb/private_key_providers/source/ipp_crypto.h +++ b/contrib/cryptomb/private_key_providers/source/ipp_crypto.h @@ -14,6 +14,10 @@ class IppCrypto { virtual ~IppCrypto() = default; virtual int mbxIsCryptoMbApplicable(uint64_t features) PURE; + virtual uint32_t mbxNistp256EcdsaSignSslMb8(uint8_t* pa_sign_r[8], uint8_t* pa_sign_s[8], + const uint8_t* const pa_msg[8], + const BIGNUM* const pa_eph_skey[8], + const BIGNUM* const pa_reg_skey[8]) PURE; virtual uint32_t mbxRsaPrivateCrtSslMb8(const uint8_t* const from_pa[8], uint8_t* const to_pa[8], const BIGNUM* const p_pa[8], const BIGNUM* const q_pa[8], const BIGNUM* const dp_pa[8], diff --git a/contrib/cryptomb/private_key_providers/source/ipp_crypto_impl.h b/contrib/cryptomb/private_key_providers/source/ipp_crypto_impl.h index e27576ead61af..f905e47ad1e9d 100644 --- a/contrib/cryptomb/private_key_providers/source/ipp_crypto_impl.h +++ b/contrib/cryptomb/private_key_providers/source/ipp_crypto_impl.h @@ -15,6 +15,13 @@ class IppCryptoImpl : public virtual IppCrypto { int mbxIsCryptoMbApplicable(uint64_t features) override { return ::mbx_is_crypto_mb_applicable(features); } + uint32_t mbxNistp256EcdsaSignSslMb8(uint8_t* pa_sign_r[8], uint8_t* pa_sign_s[8], + const uint8_t* const pa_msg[8], + const BIGNUM* const pa_eph_skey[8], + const BIGNUM* const pa_reg_skey[8]) override { + return ::mbx_nistp256_ecdsa_sign_ssl_mb8(pa_sign_r, pa_sign_s, pa_msg, pa_eph_skey, pa_reg_skey, + nullptr); + } uint32_t mbxRsaPrivateCrtSslMb8(const uint8_t* const from_pa[8], uint8_t* const to_pa[8], const BIGNUM* const p_pa[8], const BIGNUM* const q_pa[8], const BIGNUM* const dp_pa[8], const BIGNUM* const dq_pa[8], diff --git a/contrib/cryptomb/private_key_providers/test/fake_factory.cc b/contrib/cryptomb/private_key_providers/test/fake_factory.cc index ddd2a5d363e89..b5a1a0cdae0d5 100644 --- a/contrib/cryptomb/private_key_providers/test/fake_factory.cc +++ b/contrib/cryptomb/private_key_providers/test/fake_factory.cc @@ -42,6 +42,39 @@ bool FakeIppCryptoImpl::mbxGetSts(uint32_t status, unsigned req_num) { return !((status >> req_num) & 1UL); } +uint32_t FakeIppCryptoImpl::mbxNistp256EcdsaSignSslMb8(uint8_t* pa_sign_r[8], uint8_t* pa_sign_s[8], + const uint8_t* const pa_msg[8], + const BIGNUM* const pa_eph_skey[8], + const BIGNUM* const pa_reg_skey[8]) { + + uint32_t status = 0xff; + + for (int i = 0; i < 8; i++) { + EC_KEY* key; + ECDSA_SIG* sig; + + if (pa_eph_skey[i] == nullptr) { + break; + } + + key = EC_KEY_new_by_curve_name(NID_X9_62_prime256v1); + EC_KEY_set_private_key(key, pa_reg_skey[i]); + + // Length of the message representative is equal to length of r (order of EC subgroup). + sig = ECDSA_do_sign(pa_msg[i], 32, key); + + BN_bn2bin(sig->r, pa_sign_r[i]); + BN_bn2bin(sig->s, pa_sign_s[i]); + + ECDSA_SIG_free(sig); + EC_KEY_free(key); + + status = mbxSetSts(status, i, !inject_errors_); + } + + return status; +} + uint32_t FakeIppCryptoImpl::mbxRsaPrivateCrtSslMb8( const uint8_t* const from_pa[8], uint8_t* const to_pa[8], const BIGNUM* const p_pa[8], const BIGNUM* const q_pa[8], const BIGNUM* const dp_pa[8], const BIGNUM* const dq_pa[8], diff --git a/contrib/cryptomb/private_key_providers/test/fake_factory.h b/contrib/cryptomb/private_key_providers/test/fake_factory.h index 721f2426b9dde..180e62b60f148 100644 --- a/contrib/cryptomb/private_key_providers/test/fake_factory.h +++ b/contrib/cryptomb/private_key_providers/test/fake_factory.h @@ -16,6 +16,10 @@ class FakeIppCryptoImpl : public virtual IppCrypto { FakeIppCryptoImpl(bool supported_instruction_set); int mbxIsCryptoMbApplicable(uint64_t features) override; + uint32_t mbxNistp256EcdsaSignSslMb8(uint8_t* pa_sign_r[8], uint8_t* pa_sign_s[8], + const uint8_t* const pa_msg[8], + const BIGNUM* const pa_eph_skey[8], + const BIGNUM* const pa_reg_skey[8]) override; uint32_t mbxRsaPrivateCrtSslMb8(const uint8_t* const from_pa[8], uint8_t* const to_pa[8], const BIGNUM* const p_pa[8], const BIGNUM* const q_pa[8], const BIGNUM* const dp_pa[8], const BIGNUM* const dq_pa[8], diff --git a/contrib/cryptomb/private_key_providers/test/ops_test.cc b/contrib/cryptomb/private_key_providers/test/ops_test.cc index f8e18d06cd080..f25e5fcfbe847 100644 --- a/contrib/cryptomb/private_key_providers/test/ops_test.cc +++ b/contrib/cryptomb/private_key_providers/test/ops_test.cc @@ -53,31 +53,31 @@ class CryptoMbProviderTest : public testing::Test { fakeIpp_(std::make_shared(true)), stats_(generateCryptoMbStats("cryptomb", *store_.rootScope())) {} - bssl::UniquePtr makeRsaKey() { + bssl::UniquePtr makeEcdsaKey() { std::string file = TestEnvironment::readFileToStringForTest(TestEnvironment::substitute( - "{{ test_rundir }}/contrib/cryptomb/private_key_providers/test/test_data/rsa-1024.pem")); + "{{ test_rundir " + "}}/contrib/cryptomb/private_key_providers/test/test_data/ecdsa-p256.pem")); bssl::UniquePtr bio(BIO_new_mem_buf(file.data(), file.size())); bssl::UniquePtr key(EVP_PKEY_new()); - RSA* rsa = PEM_read_bio_RSAPrivateKey(bio.get(), nullptr, nullptr, nullptr); - RELEASE_ASSERT(rsa != nullptr, "PEM_read_bio_RSAPrivateKey failed."); - RELEASE_ASSERT(1 == EVP_PKEY_assign_RSA(key.get(), rsa), "EVP_PKEY_assign_RSA failed."); + EC_KEY* ec = PEM_read_bio_ECPrivateKey(bio.get(), nullptr, nullptr, nullptr); + + RELEASE_ASSERT(ec != nullptr, "PEM_read_bio_ECPrivateKey failed."); + RELEASE_ASSERT(1 == EVP_PKEY_assign_EC_KEY(key.get(), ec), "EVP_PKEY_assign_EC_KEY failed."); return key; } - bssl::UniquePtr makeEcdsaKey() { + bssl::UniquePtr makeRsaKey() { std::string file = TestEnvironment::readFileToStringForTest(TestEnvironment::substitute( - "{{ test_rundir " - "}}/contrib/cryptomb/private_key_providers/test/test_data/ecdsa-p256.pem")); + "{{ test_rundir }}/contrib/cryptomb/private_key_providers/test/test_data/rsa-1024.pem")); bssl::UniquePtr bio(BIO_new_mem_buf(file.data(), file.size())); bssl::UniquePtr key(EVP_PKEY_new()); - EC_KEY* ec = PEM_read_bio_ECPrivateKey(bio.get(), nullptr, nullptr, nullptr); - - RELEASE_ASSERT(ec != nullptr, "PEM_read_bio_ECPrivateKey failed."); - RELEASE_ASSERT(1 == EVP_PKEY_assign_EC_KEY(key.get(), ec), "EVP_PKEY_assign_EC_KEY failed."); + RSA* rsa = PEM_read_bio_RSAPrivateKey(bio.get(), nullptr, nullptr, nullptr); + RELEASE_ASSERT(rsa != nullptr, "PEM_read_bio_RSAPrivateKey failed."); + RELEASE_ASSERT(1 == EVP_PKEY_assign_RSA(key.get(), rsa), "EVP_PKEY_assign_RSA failed."); return key; } @@ -102,8 +102,17 @@ class CryptoMbProviderTest : public testing::Test { // Size of output in out_ from an operation. size_t out_len_ = 0; +}; - const std::string queue_size_histogram_name_ = "cryptomb.rsa_queue_sizes"; +class CryptoMbProviderEcdsaTest : public CryptoMbProviderTest { +protected: + CryptoMbProviderEcdsaTest() + : queue_(std::chrono::milliseconds(200), KeyType::Ec, 256, fakeIpp_, *dispatcher_, stats_), + pkey_(makeEcdsaKey()) {} + CryptoMbQueue queue_; + bssl::UniquePtr pkey_; + + const std::string queue_size_histogram_name_ = "cryptomb.ecdsa_queue_sizes"; }; class CryptoMbProviderRsaTest : public CryptoMbProviderTest { @@ -116,23 +125,39 @@ class CryptoMbProviderRsaTest : public CryptoMbProviderTest { } CryptoMbQueue queue_; bssl::UniquePtr pkey_; -}; -class CryptoMbProviderEcdsaTest : public CryptoMbProviderTest { -protected: - CryptoMbProviderEcdsaTest() - : queue_(std::chrono::milliseconds(200), KeyType::Ec, 256, fakeIpp_, *dispatcher_, stats_), - pkey_(makeEcdsaKey()) {} - CryptoMbQueue queue_; - bssl::UniquePtr pkey_; + const std::string queue_size_histogram_name_ = "cryptomb.rsa_queue_sizes"; }; TEST_F(CryptoMbProviderEcdsaTest, TestEcdsaSigning) { - TestCallbacks cb; - CryptoMbPrivateKeyConnection op(cb, *dispatcher_, bssl::UpRef(pkey_), queue_); - res_ = ecdsaPrivateKeySignForTest(&op, out_, &out_len_, max_out_len_, - SSL_SIGN_ECDSA_SECP256R1_SHA256, in_, in_len_); + // Initialize connections. + TestCallbacks cbs[CryptoMbQueue::MULTIBUFF_BATCH]; + std::vector> connections; + for (auto& cb : cbs) { + connections.push_back(std::make_unique( + cb, *dispatcher_, bssl::UpRef(pkey_), queue_)); + } + + // Create MULTIBUFF_BATCH amount of signing operations. + for (uint32_t i = 0; i < CryptoMbQueue::MULTIBUFF_BATCH; i++) { + // Create request. + res_ = ecdsaPrivateKeySignForTest(connections[i].get(), nullptr, nullptr, max_out_len_, + SSL_SIGN_ECDSA_SECP256R1_SHA256, in_, in_len_); + EXPECT_EQ(res_, ssl_private_key_retry); + + // No processing done after first requests. + // After the last request, the status is set only from the event loop which is not run. This + // should still be "retry", the cryptographic result is present anyway. + res_ = privateKeyCompleteForTest(connections[i].get(), nullptr, nullptr, max_out_len_); + EXPECT_EQ(res_, ssl_private_key_retry); + } + + // Timeout does not have to be triggered when queue is at maximum size. + dispatcher_->run(Event::Dispatcher::RunType::NonBlock); + + res_ = privateKeyCompleteForTest(connections[0].get(), out_, &out_len_, max_out_len_); EXPECT_EQ(res_, ssl_private_key_success); + EXPECT_NE(out_len_, 0); } TEST_F(CryptoMbProviderRsaTest, TestRsaPkcs1Signing) { @@ -299,7 +324,48 @@ TEST_F(CryptoMbProviderTest, TestErrors) { EXPECT_EQ(res_, ssl_private_key_failure); } -TEST_F(CryptoMbProviderRsaTest, TestRSATimer) { +TEST_F(CryptoMbProviderEcdsaTest, TestEcdsaTimer) { + TestCallbacks cbs[2]; + + // Successful operation with timer. + CryptoMbPrivateKeyConnection op0(cbs[0], *dispatcher_, bssl::UpRef(pkey_), queue_); + res_ = ecdsaPrivateKeySignForTest(&op0, nullptr, nullptr, max_out_len_, + SSL_SIGN_ECDSA_SECP256R1_SHA256, in_, in_len_); + EXPECT_EQ(res_, ssl_private_key_retry); + + res_ = privateKeyCompleteForTest(&op0, nullptr, nullptr, max_out_len_); + // No processing done yet after first request + EXPECT_EQ(res_, ssl_private_key_retry); + + time_system_.advanceTimeAndRun(std::chrono::seconds(1), *dispatcher_, + Event::Dispatcher::RunType::NonBlock); + + res_ = privateKeyCompleteForTest(&op0, out_, &out_len_, max_out_len_); + EXPECT_EQ(res_, ssl_private_key_success); + EXPECT_NE(out_len_, 0); + + // Unsuccessful operation with timer. + // Add crypto library errors + fakeIpp_->injectErrors(true); + + CryptoMbPrivateKeyConnection op1(cbs[1], *dispatcher_, bssl::UpRef(pkey_), queue_); + + res_ = ecdsaPrivateKeySignForTest(&op1, nullptr, nullptr, max_out_len_, + SSL_SIGN_ECDSA_SECP256R1_SHA256, in_, in_len_); + EXPECT_EQ(res_, ssl_private_key_retry); + + res_ = privateKeyCompleteForTest(&op1, nullptr, nullptr, max_out_len_); + // No processing done yet after first request + EXPECT_EQ(res_, ssl_private_key_retry); + + time_system_.advanceTimeAndRun(std::chrono::seconds(1), *dispatcher_, + Event::Dispatcher::RunType::NonBlock); + + res_ = privateKeyCompleteForTest(&op1, out_, &out_len_, max_out_len_); + EXPECT_EQ(res_, ssl_private_key_failure); +} + +TEST_F(CryptoMbProviderRsaTest, TestRsaTimer) { TestCallbacks cbs[2]; // Successful operation with timer. @@ -340,7 +406,62 @@ TEST_F(CryptoMbProviderRsaTest, TestRSATimer) { EXPECT_EQ(res_, ssl_private_key_failure); } -TEST_F(CryptoMbProviderRsaTest, TestRSAQueueSizeStatistics) { +TEST_F(CryptoMbProviderEcdsaTest, TestEcdsaQueueSizeStatistics) { + // Initialize connections. + TestCallbacks cbs[CryptoMbQueue::MULTIBUFF_BATCH]; + std::vector> connections; + for (auto& cb : cbs) { + connections.push_back(std::make_unique( + cb, *dispatcher_, bssl::UpRef(pkey_), queue_)); + } + + // Increment all but the last queue size once inside the loop. + for (uint32_t i = 1; i < CryptoMbQueue::MULTIBUFF_BATCH; i++) { + // Create correct amount of signing operations for current index. + for (uint32_t j = 0; j < i; j++) { + res_ = ecdsaPrivateKeySignForTest(connections[j].get(), nullptr, nullptr, max_out_len_, + SSL_SIGN_ECDSA_SECP256R1_SHA256, in_, in_len_); + EXPECT_EQ(res_, ssl_private_key_retry); + } + + time_system_.advanceTimeAndRun(std::chrono::seconds(1), *dispatcher_, + Event::Dispatcher::RunType::NonBlock); + + out_len_ = 0; + res_ = privateKeyCompleteForTest(connections[0].get(), out_, &out_len_, max_out_len_); + EXPECT_EQ(res_, ssl_private_key_success); + EXPECT_NE(out_len_, 0); + + // Check that current queue size is recorded. + std::vector histogram_values( + store_.histogramValues(queue_size_histogram_name_, true)); + EXPECT_EQ(histogram_values.size(), 1); + EXPECT_EQ(histogram_values[0], i); + } + + // Increment last queue size once. + // Create an amount of signing operations equal to maximum queue size. + for (uint32_t j = 0; j < CryptoMbQueue::MULTIBUFF_BATCH; j++) { + res_ = ecdsaPrivateKeySignForTest(connections[j].get(), nullptr, nullptr, max_out_len_, + SSL_SIGN_ECDSA_SECP256R1_SHA256, in_, in_len_); + EXPECT_EQ(res_, ssl_private_key_retry); + } + + // Timeout does not have to be triggered when queue is at maximum size. + dispatcher_->run(Event::Dispatcher::RunType::NonBlock); + + out_len_ = 0; + res_ = privateKeyCompleteForTest(connections[0].get(), out_, &out_len_, max_out_len_); + EXPECT_EQ(res_, ssl_private_key_success); + EXPECT_NE(out_len_, 0); + + // Check that last queue size is recorded. + std::vector histogram_values(store_.histogramValues(queue_size_histogram_name_, true)); + EXPECT_EQ(histogram_values.size(), 1); + EXPECT_EQ(histogram_values[0], CryptoMbQueue::MULTIBUFF_BATCH); +} + +TEST_F(CryptoMbProviderRsaTest, TestRsaQueueSizeStatistics) { // Initialize connections. TestCallbacks cbs[CryptoMbQueue::MULTIBUFF_BATCH]; std::vector> connections; diff --git a/contrib/exe/BUILD b/contrib/exe/BUILD index f6029dccc224c..1210422f895d0 100644 --- a/contrib/exe/BUILD +++ b/contrib/exe/BUILD @@ -7,6 +7,7 @@ load( load( "//contrib:all_contrib_extensions.bzl", "ARM64_SKIP_CONTRIB_TARGETS", + "FIPS_SKIP_CONTRIB_TARGETS", "PPC_SKIP_CONTRIB_TARGETS", "envoy_all_contrib_extensions", ) @@ -20,11 +21,18 @@ alias( actual = ":envoy-static", ) +SELECTED_CONTRIB_EXTENSIONS = select({ + "//bazel:linux_aarch64": envoy_all_contrib_extensions(ARM64_SKIP_CONTRIB_TARGETS), + "//bazel:linux_ppc": envoy_all_contrib_extensions(PPC_SKIP_CONTRIB_TARGETS), + "//bazel:boringssl_fips": envoy_all_contrib_extensions(FIPS_SKIP_CONTRIB_TARGETS), + "//conditions:default": envoy_all_contrib_extensions(), +}) + envoy_cc_binary( name = "envoy-static", stamped = True, visibility = ["//visibility:public"], - deps = ["//source/exe:envoy_main_entry_lib"] + envoy_all_contrib_extensions(), + deps = ["//source/exe:envoy_main_entry_lib"] + SELECTED_CONTRIB_EXTENSIONS, ) envoy_cc_test( @@ -41,9 +49,5 @@ envoy_cc_test( }, deps = [ "//test/config_test:example_configs_test_lib", - ] + select({ - "//bazel:linux_aarch64": envoy_all_contrib_extensions(ARM64_SKIP_CONTRIB_TARGETS), - "//bazel:linux_ppc": envoy_all_contrib_extensions(PPC_SKIP_CONTRIB_TARGETS), - "//conditions:default": envoy_all_contrib_extensions(), - }), + ] + SELECTED_CONTRIB_EXTENSIONS, ) diff --git a/contrib/generic_proxy/filters/network/source/access_log.cc b/contrib/generic_proxy/filters/network/source/access_log.cc index 1e1f70feb8686..a4f0c4cbda33c 100644 --- a/contrib/generic_proxy/filters/network/source/access_log.cc +++ b/contrib/generic_proxy/filters/network/source/access_log.cc @@ -41,6 +41,31 @@ class StringValueFormatterProvider : public FormatterProvider { absl::optional max_length_; }; +class GenericStatusCodeFormatterProvider : public FormatterProvider { +public: + GenericStatusCodeFormatterProvider() = default; + + // FormatterProvider + absl::optional formatWithContext(const FormatterContext& context, + const StreamInfo::StreamInfo&) const override { + if (context.response_ == nullptr) { + return absl::nullopt; + } + + const int code = context.response_->status().code(); + return std::to_string(code); + } + ProtobufWkt::Value formatValueWithContext(const FormatterContext& context, + const StreamInfo::StreamInfo&) const override { + if (context.response_ == nullptr) { + return ValueUtil::nullValue(); + } + + const int code = context.response_->status().code(); + return ValueUtil::numberValue(code); + } +}; + class SimpleCommandParser : public CommandParser { public: using ProviderFunc = @@ -139,6 +164,13 @@ class SimpleCommandParser : public CommandParser { return std::string(optional_view.value()); }); }}, + // A formatter for the response status code. This supports the case where the response + // code is minus value and will override the common RESPONSE_CODE formatter for generic + // proxy. + {"RESPONSE_CODE", + [](absl::string_view, absl::optional) -> FormatterProviderPtr { + return std::make_unique(); + }}, }); } }; diff --git a/contrib/generic_proxy/filters/network/source/interface/config.h b/contrib/generic_proxy/filters/network/source/interface/config.h index c724f6286c017..f3716cd1e08ae 100644 --- a/contrib/generic_proxy/filters/network/source/interface/config.h +++ b/contrib/generic_proxy/filters/network/source/interface/config.h @@ -51,6 +51,16 @@ class NamedFilterConfigFactory : public Config::TypedFactory { virtual absl::Status validateCodec(const TypedExtensionConfig& /*config*/) { return absl::OkStatus(); } + + std::set configTypes() override { + auto config_types = TypedFactory::configTypes(); + + if (auto message = createEmptyRouteConfigProto(); message != nullptr) { + config_types.insert(createReflectableMessage(*message)->GetDescriptor()->full_name()); + } + + return config_types; + } }; } // namespace GenericProxy diff --git a/contrib/generic_proxy/filters/network/source/interface/stream.h b/contrib/generic_proxy/filters/network/source/interface/stream.h index fcd7debb76605..a345be85261bf 100644 --- a/contrib/generic_proxy/filters/network/source/interface/stream.h +++ b/contrib/generic_proxy/filters/network/source/interface/stream.h @@ -247,7 +247,7 @@ using StatusCode = absl::StatusCode; struct StreamStatus { public: StreamStatus() = default; - StreamStatus(uint32_t code, bool ok) : code_(code), ok_(ok) {} + StreamStatus(int code, bool ok) : code_(code), ok_(ok) {} // Returns true if the status indicates success. This will be used for tracing, logging // or stats purposes. @@ -255,10 +255,10 @@ struct StreamStatus { // Returns the status code value. The code will be used for tracing, logging or stats // purposes. The specific code value is application protocol specific. - ABSL_MUST_USE_RESULT uint32_t code() const { return code_; } + ABSL_MUST_USE_RESULT int code() const { return code_; } private: - uint32_t code_{}; + int code_{}; bool ok_{true}; }; diff --git a/contrib/generic_proxy/filters/network/source/proxy.cc b/contrib/generic_proxy/filters/network/source/proxy.cc index bd447e8b298e5..0cb95ec293103 100644 --- a/contrib/generic_proxy/filters/network/source/proxy.cc +++ b/contrib/generic_proxy/filters/network/source/proxy.cc @@ -31,15 +31,15 @@ Tracing::Decision tracingDecision(const Tracing::ConnectionManagerTracingConfig& return {Tracing::Reason::NotTraceable, false}; } -StreamInfo::ResponseFlag +StreamInfo::CoreResponseFlag responseFlagFromDownstreamReasonReason(DownstreamStreamResetReason reason) { switch (reason) { case DownstreamStreamResetReason::ConnectionTermination: - return StreamInfo::ResponseFlag::DownstreamConnectionTermination; + return StreamInfo::CoreResponseFlag::DownstreamConnectionTermination; case DownstreamStreamResetReason::LocalConnectionTermination: - return StreamInfo::ResponseFlag::LocalReset; + return StreamInfo::CoreResponseFlag::LocalReset; case DownstreamStreamResetReason::ProtocolError: - return StreamInfo::ResponseFlag::DownstreamProtocolError; + return StreamInfo::CoreResponseFlag::DownstreamProtocolError; } PANIC("Unknown reset reason"); } diff --git a/contrib/generic_proxy/filters/network/source/route.cc b/contrib/generic_proxy/filters/network/source/route.cc index f58998f18925a..a5223020e1f85 100644 --- a/contrib/generic_proxy/filters/network/source/route.cc +++ b/contrib/generic_proxy/filters/network/source/route.cc @@ -17,26 +17,45 @@ namespace Extensions { namespace NetworkFilters { namespace GenericProxy { +RouteSpecificFilterConfigConstSharedPtr RouteEntryImpl::createRouteSpecificFilterConfig( + const std::string& name, const ProtobufWkt::Any& typed_config, + Server::Configuration::ServerFactoryContext& factory_context, + ProtobufMessage::ValidationVisitor& validator) { + + auto* factory = Config::Utility::getFactoryByType(typed_config); + if (factory == nullptr) { + if (!Runtime::runtimeFeatureEnabled("envoy.reloadable_features.no_extension_lookup_by_name")) { + factory = Config::Utility::getFactoryByName(name); + } + } + + if (factory == nullptr) { + ExceptionUtil::throwEnvoyException( + fmt::format("Didn't find a registered implementation for '{}' with type URL: '{}'", name, + Config::Utility::getFactoryType(typed_config))); + } + + ProtobufTypes::MessagePtr message = factory->createEmptyRouteConfigProto(); + if (message == nullptr) { + return nullptr; + } + + Envoy::Config::Utility::translateOpaqueConfig(typed_config, validator, *message); + return factory->createRouteSpecificFilterConfig(*message, factory_context, validator); +} + RouteEntryImpl::RouteEntryImpl(const ProtoRouteAction& route_action, Envoy::Server::Configuration::ServerFactoryContext& context) : name_(route_action.name()), cluster_name_(route_action.cluster()), metadata_(route_action.metadata()), typed_metadata_(metadata_) { for (const auto& proto_filter_config : route_action.per_filter_config()) { - auto& factory = Config::Utility::getAndCheckFactoryByName( - proto_filter_config.first); - - ProtobufTypes::MessagePtr message = factory.createEmptyRouteConfigProto(); - if (message == nullptr) { - continue; + auto route_config = + createRouteSpecificFilterConfig(proto_filter_config.first, proto_filter_config.second, + context, context.messageValidationVisitor()); + if (route_config != nullptr) { + per_filter_configs_.emplace(proto_filter_config.first, std::move(route_config)); } - - Envoy::Config::Utility::translateOpaqueConfig(proto_filter_config.second, - context.messageValidationVisitor(), *message); - - auto route_config = factory.createRouteSpecificFilterConfig(*message, context, - context.messageValidationVisitor()); - per_filter_configs_.emplace(proto_filter_config.first, std::move(route_config)); } } diff --git a/contrib/generic_proxy/filters/network/source/route.h b/contrib/generic_proxy/filters/network/source/route.h index 010a6ec0be17c..6a90521dd5013 100644 --- a/contrib/generic_proxy/filters/network/source/route.h +++ b/contrib/generic_proxy/filters/network/source/route.h @@ -46,6 +46,11 @@ class RouteEntryImpl : public RouteEntry { const Envoy::Config::TypedMetadata& typedMetadata() const override { return typed_metadata_; }; + RouteSpecificFilterConfigConstSharedPtr + createRouteSpecificFilterConfig(const std::string& name, const ProtobufWkt::Any& typed_config, + Server::Configuration::ServerFactoryContext& factory_context, + ProtobufMessage::ValidationVisitor& validator); + private: static const uint64_t DEFAULT_ROUTE_TIMEOUT_MS = 15000; diff --git a/contrib/generic_proxy/filters/network/source/router/router.cc b/contrib/generic_proxy/filters/network/source/router/router.cc index 9fce97d284ad2..2a7cbd69900bf 100644 --- a/contrib/generic_proxy/filters/network/source/router/router.cc +++ b/contrib/generic_proxy/filters/network/source/router/router.cc @@ -286,7 +286,8 @@ UpstreamRequest::UpstreamRequest(RouterFilter& parent, GenericUpstreamSharedPtr expects_response_ = !options.oneWayStream(); // Set tracing config. - if (tracing_config_ = parent_.callbacks_->tracingConfig(); tracing_config_.has_value()) { + tracing_config_ = parent_.callbacks_->tracingConfig(); + if (tracing_config_.has_value() && tracing_config_->spawnUpstreamSpan()) { span_ = parent_.callbacks_->activeSpan().spawnChild( tracing_config_.value().get(), absl::StrCat("router ", parent_.cluster_->observabilityName(), " egress"), @@ -555,20 +556,21 @@ void RouterFilter::resetStream(StreamResetReason reason) { callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, resetReasonToStringView(reason))); break; case StreamResetReason::ProtocolError: - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamProtocolError); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamProtocolError); callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, resetReasonToStringView(reason))); break; case StreamResetReason::ConnectionFailure: - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + callbacks_->streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, resetReasonToStringView(reason))); break; case StreamResetReason::ConnectionTermination: callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UpstreamConnectionTermination); + StreamInfo::CoreResponseFlag::UpstreamConnectionTermination); callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, resetReasonToStringView(reason))); break; case StreamResetReason::Overflow: - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, resetReasonToStringView(reason))); break; } @@ -580,7 +582,7 @@ void RouterFilter::kickOffNewUpstreamRequest() { auto thread_local_cluster = cluster_manager_.getThreadLocalCluster(cluster_name); if (thread_local_cluster == nullptr) { filter_complete_ = true; - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoClusterFound); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoClusterFound); callbacks_->sendLocalReply(Status(StatusCode::kNotFound, "cluster_not_found")); return; } @@ -612,7 +614,7 @@ void RouterFilter::kickOffNewUpstreamRequest() { auto pool_data = thread_local_cluster->tcpConnPool(Upstream::ResourcePriority::Default, this); if (!pool_data.has_value()) { filter_complete_ = true; - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream); callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, "no_healthy_upstream")); return; } @@ -632,7 +634,7 @@ void RouterFilter::kickOffNewUpstreamRequest() { auto pool_data = thread_local_cluster->tcpConnPool(Upstream::ResourcePriority::Default, this); if (!pool_data.has_value()) { filter_complete_ = true; - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream); callbacks_->sendLocalReply(Status(StatusCode::kUnavailable, "no_healthy_upstream")); return; } @@ -671,7 +673,7 @@ FilterStatus RouterFilter::onStreamDecoded(StreamRequest& request) { ENVOY_LOG(debug, "No route for current request and send local reply"); filter_complete_ = true; - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); callbacks_->sendLocalReply(Status(StatusCode::kNotFound, "route_not_found")); return FilterStatus::StopIteration; } diff --git a/contrib/generic_proxy/filters/network/source/stats.cc b/contrib/generic_proxy/filters/network/source/stats.cc index c1363cb24821d..dd9e61977810b 100644 --- a/contrib/generic_proxy/filters/network/source/stats.cc +++ b/contrib/generic_proxy/filters/network/source/stats.cc @@ -18,8 +18,10 @@ CodeOrFlags::CodeOrFlags(Server::Configuration::ServerFactoryContext& context) code_stat_names_.push_back(pool_.add(std::to_string(i))); } - for (const auto& flag : StreamInfo::ResponseFlagUtils::ALL_RESPONSE_STRINGS_FLAGS) { - flag_stat_names_.emplace(flag.second, pool_.add(flag.first.short_string_)); + flag_stat_names_.reserve(StreamInfo::ResponseFlagUtils::responseFlagsVec().size()); + + for (const auto& flag : StreamInfo::ResponseFlagUtils::responseFlagsVec()) { + flag_stat_names_.push_back(pool_.add(flag.short_string_)); } unknown_code_or_flag_ = pool_.add("-"); @@ -33,27 +35,10 @@ Stats::StatName CodeOrFlags::statNameFromCode(uint32_t code) const { } Stats::StatName CodeOrFlags::statNameFromFlag(StreamInfo::ResponseFlag flag) const { - const auto iter = flag_stat_names_.find(flag); - if (iter != flag_stat_names_.end()) { - return iter->second; - } - return unknown_code_or_flag_; -} - -absl::InlinedVector -getResponseFlags(const StreamInfo::StreamInfo& info) { - if (info.responseFlags() == 0) { - return {}; - } - - absl::InlinedVector flags; - - for (const auto& flag : StreamInfo::ResponseFlagUtils::ALL_RESPONSE_STRINGS_FLAGS) { - if (info.hasResponseFlag(flag.second)) { - flags.push_back(flag.second); - } - } - return flags; + // Any flag value should be less than the size of flag_stat_names_. Because flag_stat_names_ + // is initialized with all possible flags. + ASSERT(flag.value() < flag_stat_names_.size()); + return flag_stat_names_[flag.value()]; } void GenericFilterStatsHelper::onRequestReset() { stats_.downstream_rq_reset_.inc(); } @@ -93,7 +78,7 @@ void GenericFilterStatsHelper::onRequestComplete(const StreamInfo::StreamInfo& i } const auto response_code = info.responseCode().value_or(0); - const auto response_flags = getResponseFlags(info); + const auto response_flags = info.responseFlags(); if (last_code_counter_.second.has_value() && response_code == last_code_counter_.first) { last_code_counter_.second->inc(); diff --git a/contrib/generic_proxy/filters/network/source/stats.h b/contrib/generic_proxy/filters/network/source/stats.h index d4b58476bd019..59c2b88b167d7 100644 --- a/contrib/generic_proxy/filters/network/source/stats.h +++ b/contrib/generic_proxy/filters/network/source/stats.h @@ -28,7 +28,10 @@ class CodeOrFlags : public Singleton::Instance { Stats::StatNamePool pool_; std::vector code_stat_names_; - absl::flat_hash_map flag_stat_names_; + // The flag_stat_names_ contains stat names of all response flags. The index of each flag + // is the same as the value of the flag. Size of this vector is the same as the size of + // StreamInfo::ResponseFlagUtils::responseFlagsVec(). + std::vector flag_stat_names_; Stats::StatName unknown_code_or_flag_; }; diff --git a/contrib/generic_proxy/filters/network/test/BUILD b/contrib/generic_proxy/filters/network/test/BUILD index afd72e504d0c5..e57a54439024b 100644 --- a/contrib/generic_proxy/filters/network/test/BUILD +++ b/contrib/generic_proxy/filters/network/test/BUILD @@ -34,6 +34,7 @@ envoy_cc_test( "//source/common/buffer:buffer_lib", "//test/mocks/server:factory_context_mocks", "//test/test_common:registry_lib", + "//test/test_common:test_runtime_lib", "//test/test_common:utility_lib", ], ) @@ -72,6 +73,7 @@ envoy_cc_test( "//test/mocks/network:network_mocks", "//test/mocks/server:factory_context_mocks", "//test/test_common:registry_lib", + "//test/test_common:test_runtime_lib", "//test/test_common:utility_lib", "@envoy_api//contrib/envoy/extensions/filters/network/generic_proxy/v3:pkg_cc_proto", "@envoy_api//envoy/admin/v3:pkg_cc_proto", @@ -119,3 +121,15 @@ envoy_cc_test( "//test/mocks/server:factory_context_mocks", ], ) + +envoy_cc_test( + name = "access_log_test", + srcs = [ + "access_log_test.cc", + ], + deps = [ + ":fake_codec_lib", + "//contrib/generic_proxy/filters/network/source:access_log_lib", + "//test/mocks/stream_info:stream_info_mocks", + ], +) diff --git a/contrib/generic_proxy/filters/network/test/access_log_test.cc b/contrib/generic_proxy/filters/network/test/access_log_test.cc new file mode 100644 index 0000000000000..ab2f9470ada11 --- /dev/null +++ b/contrib/generic_proxy/filters/network/test/access_log_test.cc @@ -0,0 +1,133 @@ +#include "test/mocks/stream_info/mocks.h" + +#include "contrib/generic_proxy/filters/network/source/access_log.h" +#include "contrib/generic_proxy/filters/network/test/fake_codec.h" +#include "gtest/gtest.h" + +namespace Envoy { +namespace Extensions { +namespace NetworkFilters { +namespace GenericProxy { +namespace { + +TEST(AccessLogFormatterTest, AccessLogFormatterTest) { + + { + // Test for %METHOD%. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter("%METHOD%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeRequest request; + request.method_ = "FAKE_METHOD"; + context.request_ = &request; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "FAKE_METHOD"); + } + + { + // Test for %HOST%. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter("%HOST%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeRequest request; + request.host_ = "FAKE_HOST"; + context.request_ = &request; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "FAKE_HOST"); + } + + { + // Test for %PATH%. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter("%PATH%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeRequest request; + request.path_ = "FAKE_PATH"; + context.request_ = &request; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "FAKE_PATH"); + } + + { + // Test for %PROTOCOL%. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter("%PROTOCOL%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeRequest request; + request.protocol_ = "FAKE_PROTOCOL"; + context.request_ = &request; + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "FAKE_PROTOCOL"); + } + + { + // Test for %REQUEST_PROPERTY%. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter("%REQUEST_PROPERTY(FAKE_KEY)%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeRequest request; + + context.request_ = &request; + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + request.data_["FAKE_KEY"] = "FAKE_VALUE"; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "FAKE_VALUE"); + } + + { + // Test for %RESPONSE_PROPERTY%. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter( + "%RESPONSE_PROPERTY(FAKE_KEY)%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeResponse response; + + context.response_ = &response; + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + response.data_["FAKE_KEY"] = "FAKE_VALUE"; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "FAKE_VALUE"); + } + + { + // Test for %RESPONSE_CODE%. + // This command overrides the default one which is defined in the + // source/common/formatter/stream_info_formatter.cc. + FormatterContext context; + Envoy::Formatter::FormatterBaseImpl formatter("%RESPONSE_CODE%"); + StreamInfo::MockStreamInfo stream_info; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-"); + + FakeStreamCodecFactory::FakeResponse response; + response.status_ = {-1234, false}; + context.response_ = &response; + + EXPECT_EQ(formatter.formatWithContext(context, stream_info), "-1234"); + } +} + +} // namespace +} // namespace GenericProxy +} // namespace NetworkFilters +} // namespace Extensions +} // namespace Envoy diff --git a/contrib/generic_proxy/filters/network/test/fake_codec.h b/contrib/generic_proxy/filters/network/test/fake_codec.h index 702abb47d25e3..e5e241075efb1 100644 --- a/contrib/generic_proxy/filters/network/test/fake_codec.h +++ b/contrib/generic_proxy/filters/network/test/fake_codec.h @@ -152,7 +152,7 @@ class FakeStreamCodecFactory : public CodecFactory { } // Additional 4 bytes for status. encoding_buffer_.writeBEInt(body.size() + 4); - encoding_buffer_.writeBEInt(static_cast(typed_response->status_.code())); + encoding_buffer_.writeBEInt(typed_response->status_.code()); encoding_buffer_.add(body); callback.onEncodingSuccess(encoding_buffer_, response.frameFlags().endStream()); @@ -160,8 +160,7 @@ class FakeStreamCodecFactory : public CodecFactory { ResponsePtr respond(Status status, absl::string_view, const Request&) override { auto response = std::make_unique(); - response->status_ = {static_cast(status.code()), - status.code() == absl::StatusCode::kOk}; + response->status_ = {status.raw_code(), status.ok()}; response->message_ = status.message(); response->protocol_ = "fake_protocol_for_test"; return response; @@ -192,7 +191,7 @@ class FakeStreamCodecFactory : public CodecFactory { } auto response = std::make_unique(); - response->status_ = {static_cast(status_code), + response->status_ = {status_code, static_cast(status_code) == absl::StatusCode::kOk}; response->protocol_ = std::string(result[0]); for (absl::string_view pair_str : absl::StrSplit(result[2], ';', absl::SkipEmpty())) { diff --git a/contrib/generic_proxy/filters/network/test/mocks/filter.cc b/contrib/generic_proxy/filters/network/test/mocks/filter.cc index aa94963b5b2cd..9fd2568b15610 100644 --- a/contrib/generic_proxy/filters/network/test/mocks/filter.cc +++ b/contrib/generic_proxy/filters/network/test/mocks/filter.cc @@ -22,7 +22,9 @@ MockStreamFilterConfig::MockStreamFilterConfig() { ON_CALL(*this, createFilterFactoryFromProto(_, _, _)) .WillByDefault(Return([](FilterChainFactoryCallbacks&) {})); ON_CALL(*this, name()).WillByDefault(Return("envoy.filters.generic.mock_filter")); - ON_CALL(*this, configTypes()).WillByDefault(Return(std::set{})); + ON_CALL(*this, configTypes()).WillByDefault(Invoke([this]() { + return NamedFilterConfigFactory::configTypes(); + })); } MockFilterChainManager::MockFilterChainManager() { diff --git a/contrib/generic_proxy/filters/network/test/proxy_test.cc b/contrib/generic_proxy/filters/network/test/proxy_test.cc index 2fe8b80c98b9e..01db410cc19cd 100644 --- a/contrib/generic_proxy/filters/network/test/proxy_test.cc +++ b/contrib/generic_proxy/filters/network/test/proxy_test.cc @@ -658,8 +658,7 @@ TEST_F(FilterTest, ActiveStreamSendLocalReply) { EXPECT_CALL(*server_codec_, respond(_, _, _)) .WillOnce(Invoke([&](Status status, absl::string_view, const Request&) -> ResponsePtr { auto response = std::make_unique(); - response->status_ = {static_cast(status.code()), - status.code() == StatusCode::kOk}; + response->status_ = {static_cast(status.code()), status.code() == StatusCode::kOk}; response->message_ = status.message(); return response; })); @@ -907,7 +906,7 @@ TEST_F(FilterTest, NewStreamAndReplyNormallyWithDrainClose) { auto response = std::make_unique(); response->status_ = {234, false}; // Response non-OK. - active_stream->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamProtocolError); + active_stream->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamProtocolError); active_stream->onResponseStart(std::move(response)); EXPECT_EQ(filter_config_->stats().downstream_rq_total_.value(), 1); diff --git a/contrib/generic_proxy/filters/network/test/route_test.cc b/contrib/generic_proxy/filters/network/test/route_test.cc index b1377849c2288..c202e137ef4b1 100644 --- a/contrib/generic_proxy/filters/network/test/route_test.cc +++ b/contrib/generic_proxy/filters/network/test/route_test.cc @@ -4,6 +4,7 @@ #include "test/mocks/server/factory_context.h" #include "test/test_common/registry.h" +#include "test/test_common/test_runtime.h" #include "test/test_common/utility.h" #include "contrib/generic_proxy/filters/network/source/match.h" @@ -126,10 +127,11 @@ TEST_F(RouteEntryImplTest, RouteTypedMetadata) { * verifies that the proto per filter config can be loaded correctly. */ TEST_F(RouteEntryImplTest, RoutePerFilterConfig) { - Registry::InjectFactory registration(filter_config_); ON_CALL(filter_config_, createEmptyRouteConfigProto()).WillByDefault(Invoke([]() { return std::make_unique(); })); + Registry::InjectFactory registration(filter_config_); + ON_CALL(filter_config_, createRouteSpecificFilterConfig(_, _, _)) .WillByDefault( Invoke([this](const Protobuf::Message&, Server::Configuration::ServerFactoryContext&, @@ -153,9 +155,44 @@ TEST_F(RouteEntryImplTest, RoutePerFilterConfig) { }; /** - * Test the case where there is no route level proto available for the filter. + * Test the method that get route level per filter config from the route entry. In this case, + * unexpected type is used to find the filter factory and finally an exception is thrown. */ -TEST_F(RouteEntryImplTest, NullRouteEmptyProto) { +TEST_F(RouteEntryImplTest, RoutePerFilterConfigWithUnknownType) { + ON_CALL(filter_config_, createEmptyRouteConfigProto()).WillByDefault(Invoke([]() { + return std::make_unique(); + })); + Registry::InjectFactory registration(filter_config_); + + const std::string yaml_config = R"EOF( + cluster: cluster_0 + per_filter_config: + envoy.filters.generic.mock_filter: + # The mock filter is registered with the type of google.protobuf.Struct. + # So the google.protobuf.Value cannot be used to find the mock filter. + "@type": type.googleapis.com/google.protobuf.Value + value: { "key_0": "value_0" } + )EOF"; + + // The configuraton will be rejected because the extension cannot be found. + EXPECT_THROW_WITH_MESSAGE( + { initialize(yaml_config); }, EnvoyException, + "Didn't find a registered implementation for 'envoy.filters.generic.mock_filter' with type " + "URL: 'google.protobuf.Value'"); +} + +/** + * Test the method that get route level per filter config from the route entry. In this case, + * unexpected type is used to find the filter factory. But the extension lookup by name is enabled + * and the mock filter is found. + */ +TEST_F(RouteEntryImplTest, RoutePerFilterConfigWithUnknownTypeButEnableExtensionLookupByName) { + TestScopedRuntime scoped_runtime; + scoped_runtime.mergeValues({{"envoy.reloadable_features.no_extension_lookup_by_name", "false"}}); + + ON_CALL(filter_config_, createEmptyRouteConfigProto()).WillByDefault(Invoke([]() { + return std::make_unique(); + })); Registry::InjectFactory registration(filter_config_); ON_CALL(filter_config_, createRouteSpecificFilterConfig(_, _, _)) @@ -167,6 +204,33 @@ TEST_F(RouteEntryImplTest, NullRouteEmptyProto) { return route_config; })); + const std::string yaml_config = R"EOF( + cluster: cluster_0 + per_filter_config: + envoy.filters.generic.mock_filter: + # The mock filter is registered with the type of google.protobuf.Struct. + # So the google.protobuf.Value cannot be used to find the mock filter. + "@type": type.googleapis.com/xds.type.v3.TypedStruct + type_url: type.googleapis.com/google.protobuf.Value + value: + value: { "key_0": "value_0" } + )EOF"; + + initialize(yaml_config); + + EXPECT_EQ(route_->perFilterConfig("envoy.filters.generic.mock_filter"), + route_config_map_.at("envoy.filters.generic.mock_filter").get()); +} + +/** + * Test the case where there is no route level proto available for the filter. + */ +TEST_F(RouteEntryImplTest, NullRouteEmptyProto) { + ON_CALL(filter_config_, createEmptyRouteConfigProto()).WillByDefault(Invoke([]() { + return nullptr; + })); + Registry::InjectFactory registration(filter_config_); + const std::string yaml_config = R"EOF( cluster: cluster_0 per_filter_config: diff --git a/contrib/generic_proxy/filters/network/test/router/router_test.cc b/contrib/generic_proxy/filters/network/test/router/router_test.cc index 295567495c062..8d98a4229f85d 100644 --- a/contrib/generic_proxy/filters/network/test/router/router_test.cc +++ b/contrib/generic_proxy/filters/network/test/router/router_test.cc @@ -251,6 +251,7 @@ class RouterFilterTest : public testing::TestWithParam { if (with_tracing_) { EXPECT_CALL(mock_filter_callback_, tracingConfig()) .WillOnce(Return(OptRef{tracing_config_})); + EXPECT_CALL(tracing_config_, spawnUpstreamSpan()).WillOnce(Return(true)); EXPECT_CALL(active_span_, spawnChild_(_, "router observability_name egress", _)) .WillOnce(Invoke([this](const Tracing::Config&, const std::string&, SystemTime) { child_span_ = new NiceMock(); diff --git a/contrib/golang/common/go/api/api.h b/contrib/golang/common/go/api/api.h index 504d412d3e148..66d9f5f1cc271 100644 --- a/contrib/golang/common/go/api/api.h +++ b/contrib/golang/common/go/api/api.h @@ -17,6 +17,7 @@ typedef struct { // NOLINT(modernize-use-using) Cstring plugin_name; uint64_t configId; int phase; + uint32_t worker_id; } httpRequest; typedef struct { // NOLINT(modernize-use-using) @@ -25,6 +26,7 @@ typedef struct { // NOLINT(modernize-use-using) uint64_t config_ptr; uint64_t config_len; int is_route_config; + uint32_t concurrency; } httpConfig; typedef enum { // NOLINT(modernize-use-using) diff --git a/contrib/golang/common/go/api/filter.go b/contrib/golang/common/go/api/filter.go index 20e913cbb8ac2..8bf79b2d1eb4d 100644 --- a/contrib/golang/common/go/api/filter.go +++ b/contrib/golang/common/go/api/filter.go @@ -103,12 +103,17 @@ func (*PassThroughStreamFilter) OnDestroy(DestroyReason) { } type StreamFilterConfigParser interface { + // Parse the proto message to any Go value, and return error to reject the config. + // This is called when Envoy receives the config from the control plane. + // Also, you can define Metrics through the callbacks, and the callbacks will be nil when parsing the route config. Parse(any *anypb.Any, callbacks ConfigCallbackHandler) (interface{}, error) + // Merge the two configs(filter level config or route level config) into one. + // May merge multi-level configurations, i.e. filter level, virtualhost level, router level and weighted cluster level, + // into a single one recursively, by invoking this method multiple times. Merge(parentConfig interface{}, childConfig interface{}) interface{} } -type StreamFilterConfigFactory func(config interface{}) StreamFilterFactory -type StreamFilterFactory func(callbacks FilterCallbackHandler) StreamFilter +type StreamFilterFactory func(config interface{}, callbacks FilterCallbackHandler) StreamFilter // stream info // refer https://github.com/envoyproxy/envoy/blob/main/envoy/stream_info/stream_info.h @@ -139,7 +144,8 @@ type StreamInfo interface { FilterState() FilterState // VirtualClusterName returns the name of the virtual cluster which got matched VirtualClusterName() (string, bool) - + // WorkerID returns the ID of the Envoy worker thread + WorkerID() uint32 // Some fields in stream info can be fetched via GetProperty // For example, startTime() is equal to GetProperty("request.time") } diff --git a/contrib/golang/filters/http/source/config.cc b/contrib/golang/filters/http/source/config.cc index 6bd9a5bf77c17..91d7eddc32c70 100644 --- a/contrib/golang/filters/http/source/config.cc +++ b/contrib/golang/filters/http/source/config.cc @@ -1,5 +1,7 @@ #include "contrib/golang/filters/http/source/config.h" +#include + #include "envoy/registry/registry.h" #include "source/common/common/fmt.h" @@ -33,7 +35,14 @@ Http::FilterFactoryCb GolangFilterConfig::createFilterFactoryFromProtoTyped( proto_config, dso_lib, fmt::format("{}golang.", stats_prefix), context); config->newGoPluginConfig(); return [config, dso_lib](Http::FilterChainFactoryCallbacks& callbacks) { - auto filter = std::make_shared(config, dso_lib); + const std::string& worker_name = callbacks.dispatcher().name(); + auto pos = worker_name.find_first_of('_'); + ENVOY_BUG(pos != std::string::npos, "worker name is not in expected format worker_{id}"); + uint32_t worker_id; + if (!absl::SimpleAtoi(worker_name.substr(pos + 1), &worker_id)) { + IS_ENVOY_BUG("failed to parse worker id from name"); + } + auto filter = std::make_shared(config, dso_lib, worker_id); callbacks.addStreamFilter(filter); callbacks.addAccessLogHandler(filter); }; diff --git a/contrib/golang/filters/http/source/go/pkg/http/capi_impl.go b/contrib/golang/filters/http/source/go/pkg/http/capi_impl.go index a195c3b261624..a9a91abd921a3 100644 --- a/contrib/golang/filters/http/source/go/pkg/http/capi_impl.go +++ b/contrib/golang/filters/http/source/go/pkg/http/capi_impl.go @@ -35,7 +35,6 @@ import ( "errors" "runtime" "strings" - "sync/atomic" "unsafe" "google.golang.org/protobuf/proto" @@ -321,17 +320,16 @@ func (c *httpCApiImpl) HttpGetDynamicMetadata(rr unsafe.Pointer, filterName stri r := (*httpRequest)(rr) r.mutex.Lock() defer r.mutex.Unlock() - r.sema.Add(1) + r.markMayWaitingCallback() var valueData C.uint64_t var valueLen C.int res := C.envoyGoFilterHttpGetDynamicMetadata(unsafe.Pointer(r.req), unsafe.Pointer(unsafe.StringData(filterName)), C.int(len(filterName)), &valueData, &valueLen) if res == C.CAPIYield { - atomic.AddInt32(&r.waitingOnEnvoy, 1) - r.sema.Wait() + r.checkOrWaitCallback() } else { - r.sema.Done() + r.markNoWaitingCallback() handleCApiStatus(res) } buf := unsafe.Slice((*byte)(unsafe.Pointer(uintptr(valueData))), int(valueLen)) @@ -394,14 +392,13 @@ func (c *httpCApiImpl) HttpGetStringFilterState(rr unsafe.Pointer, key string) s var valueLen C.int r.mutex.Lock() defer r.mutex.Unlock() - r.sema.Add(1) + r.markMayWaitingCallback() res := C.envoyGoFilterHttpGetStringFilterState(unsafe.Pointer(r.req), unsafe.Pointer(unsafe.StringData(key)), C.int(len(key)), &valueData, &valueLen) if res == C.CAPIYield { - atomic.AddInt32(&r.waitingOnEnvoy, 1) - r.sema.Wait() + r.checkOrWaitCallback() } else { - r.sema.Done() + r.markNoWaitingCallback() handleCApiStatus(res) } @@ -416,15 +413,14 @@ func (c *httpCApiImpl) HttpGetStringProperty(rr unsafe.Pointer, key string) (str var rc C.int r.mutex.Lock() defer r.mutex.Unlock() - r.sema.Add(1) + r.markMayWaitingCallback() res := C.envoyGoFilterHttpGetStringProperty(unsafe.Pointer(r.req), unsafe.Pointer(unsafe.StringData(key)), C.int(len(key)), &valueData, &valueLen, &rc) if res == C.CAPIYield { - atomic.AddInt32(&r.waitingOnEnvoy, 1) - r.sema.Wait() + r.checkOrWaitCallback() res = C.CAPIStatus(rc) } else { - r.sema.Done() + r.markNoWaitingCallback() handleCApiStatus(res) } diff --git a/contrib/golang/filters/http/source/go/pkg/http/config.go b/contrib/golang/filters/http/source/go/pkg/http/config.go index 99e231e98520b..21c461ca25d6b 100644 --- a/contrib/golang/filters/http/source/go/pkg/http/config.go +++ b/contrib/golang/filters/http/source/go/pkg/http/config.go @@ -73,27 +73,26 @@ func envoyGoFilterNewHttpPluginConfig(c *C.httpConfig) uint64 { var any anypb.Any proto.Unmarshal(buf, &any) + Requests.initialize(uint32(c.concurrency)) + configNum := atomic.AddUint64(&configNumGenerator, 1) name := utils.BytesToString(uint64(c.plugin_name_ptr), uint64(c.plugin_name_len)) configParser := getHttpFilterConfigParser(name) - if configParser != nil { - var parsedConfig interface{} - var err error - if c.is_route_config == 1 { - parsedConfig, err = configParser.Parse(&any, nil) - } else { - http_config := createConfig(c) - parsedConfig, err = configParser.Parse(&any, http_config) - } - if err != nil { - cAPI.HttpLog(api.Error, fmt.Sprintf("failed to parse golang plugin config: %v", err)) - return 0 - } - configCache.Store(configNum, parsedConfig) + + var parsedConfig interface{} + var err error + if c.is_route_config == 1 { + parsedConfig, err = configParser.Parse(&any, nil) } else { - configCache.Store(configNum, &any) + config := createConfig(c) + parsedConfig, err = configParser.Parse(&any, config) + } + if err != nil { + cAPI.HttpLog(api.Error, fmt.Sprintf("failed to parse golang plugin config: %v", err)) + return 0 } + configCache.Store(configNum, parsedConfig) return configNum } @@ -119,24 +118,17 @@ func envoyGoFilterMergeHttpPluginConfig(namePtr, nameLen, parentId, childId uint name := utils.BytesToString(namePtr, nameLen) configParser := getHttpFilterConfigParser(name) - if configParser != nil { - parent, ok := configCache.Load(parentId) - if !ok { - panic(fmt.Sprintf("merge config: get parentId: %d config failed", parentId)) - } - child, ok := configCache.Load(childId) - if !ok { - panic(fmt.Sprintf("merge config: get childId: %d config failed", childId)) - } - - new := configParser.Merge(parent, child) - configNum := atomic.AddUint64(&configNumGenerator, 1) - configCache.Store(configNum, new) - return configNum - - } else { - // child override parent by default. - // It's safe to reuse the childId, since the merged config have the same life time with the child config. - return childId + parent, ok := configCache.Load(parentId) + if !ok { + panic(fmt.Sprintf("merge config: get parentId: %d config failed", parentId)) } + child, ok := configCache.Load(childId) + if !ok { + panic(fmt.Sprintf("merge config: get childId: %d config failed", childId)) + } + + new := configParser.Merge(parent, child) + configNum := atomic.AddUint64(&configNumGenerator, 1) + configCache.Store(configNum, new) + return configNum } diff --git a/contrib/golang/filters/http/source/go/pkg/http/filter.go b/contrib/golang/filters/http/source/go/pkg/http/filter.go index c9b1d3424c75b..029ebf612198a 100644 --- a/contrib/golang/filters/http/source/go/pkg/http/filter.go +++ b/contrib/golang/filters/http/source/go/pkg/http/filter.go @@ -35,6 +35,7 @@ import ( "fmt" "runtime" "sync" + "sync/atomic" "unsafe" "github.com/envoyproxy/envoy/contrib/golang/common/go/api" @@ -47,6 +48,11 @@ const ( HTTP30 = "HTTP/3.0" ) +const ( + NoWaitingCallback = 0 + MayWaitingCallback = 1 +) + var protocolsIdToName = map[uint64]string{ 0: HTTP10, 1: HTTP11, @@ -59,12 +65,57 @@ type panicInfo struct { details string } type httpRequest struct { - req *C.httpRequest - httpFilter api.StreamFilter - pInfo panicInfo - sema sync.WaitGroup - waitingOnEnvoy int32 - mutex sync.Mutex + req *C.httpRequest + httpFilter api.StreamFilter + pInfo panicInfo + waitingLock sync.Mutex // protect waitingCallback + cond sync.Cond + waitingCallback int32 + + // protect multiple cases: + // 1. protect req_->strValue in the C++ side from being used concurrently. + // 2. protect waitingCallback from being modified in markMayWaitingCallback concurrently. + mutex sync.Mutex +} + +// markWaitingOnEnvoy marks the request may be waiting a callback from envoy. +// Must be the NoWaitingCallback state since it's invoked under the r.mutex lock. +// We do not do lock waitingCallback here, to reduce lock contention. +func (r *httpRequest) markMayWaitingCallback() { + if !atomic.CompareAndSwapInt32(&r.waitingCallback, NoWaitingCallback, MayWaitingCallback) { + panic("markWaitingCallback: unexpected state") + } +} + +// markNoWaitingOnEnvoy marks the request is not waiting a callback from envoy. +// Can not make sure it's in the MayWaitingCallback state, since the state maybe changed by OnDestroy. +func (r *httpRequest) markNoWaitingCallback() { + atomic.StoreInt32(&r.waitingCallback, NoWaitingCallback) +} + +// checkOrWaitCallback checks if we need to wait a callback from envoy, and wait it. +func (r *httpRequest) checkOrWaitCallback() { + // need acquire the lock, since there might be concurrency race with resumeWaitCallback. + r.cond.L.Lock() + defer r.cond.L.Unlock() + + // callback or OnDestroy already called, no need to wait. + if atomic.LoadInt32(&r.waitingCallback) == NoWaitingCallback { + return + } + r.cond.Wait() +} + +// resumeWaitCallback resumes the goroutine that waiting for the callback from envoy. +func (r *httpRequest) resumeWaitCallback() { + // need acquire the lock, since there might be concurrency race with checkOrWaitCallback. + r.cond.L.Lock() + defer r.cond.L.Unlock() + + if atomic.CompareAndSwapInt32(&r.waitingCallback, MayWaitingCallback, NoWaitingCallback) { + // Broadcast is safe even there is no waiters. + r.cond.Broadcast() + } } func (r *httpRequest) pluginName() string { @@ -230,6 +281,10 @@ func (s *streamInfo) VirtualClusterName() (string, bool) { return cAPI.HttpGetStringValue(unsafe.Pointer(s.request), ValueVirtualClusterName) } +func (s *streamInfo) WorkerID() uint32 { + return uint32(s.request.req.worker_id) +} + type filterState struct { request *httpRequest } diff --git a/contrib/golang/filters/http/source/go/pkg/http/filtermanager.go b/contrib/golang/filters/http/source/go/pkg/http/filtermanager.go index ce8c65c88f666..550cc53264f34 100644 --- a/contrib/golang/filters/http/source/go/pkg/http/filtermanager.go +++ b/contrib/golang/filters/http/source/go/pkg/http/filtermanager.go @@ -22,44 +22,68 @@ import ( "sync" "github.com/envoyproxy/envoy/contrib/golang/common/go/api" + "google.golang.org/protobuf/types/known/anypb" ) -var httpFilterConfigFactoryAndParser = sync.Map{} +var httpFilterFactoryAndParser = sync.Map{} -type filterConfigFactoryAndParser struct { - configFactory api.StreamFilterConfigFactory +type filterFactoryAndParser struct { + filterFactory api.StreamFilterFactory configParser api.StreamFilterConfigParser } -// Register config factory and config parser for the specified plugin. -// The "factory" parameter is required, should not be nil, -// and the "parser" parameter is optional, could be nil. -func RegisterHttpFilterConfigFactoryAndParser(name string, factory api.StreamFilterConfigFactory, parser api.StreamFilterConfigParser) { +// nullParser is a no-op implementation of the StreamFilterConfigParser interface. +type nullParser struct{} + +// Parse does nothing, returns the input `any` as is. +func (p *nullParser) Parse(any *anypb.Any, callbacks api.ConfigCallbackHandler) (interface{}, error) { + return any, nil +} + +// Merge only uses the childConfig, ignore the parentConfig. +func (p *nullParser) Merge(parentConfig interface{}, childConfig interface{}) interface{} { + return childConfig +} + +var NullParser api.StreamFilterConfigParser = &nullParser{} + +// RegisterHttpFilterFactoryAndConfigParser registers the http filter factory and config parser for the specified plugin. +// The factory and parser should not be nil. +// Use the NullParser if the plugin does not care about config. +func RegisterHttpFilterFactoryAndConfigParser(name string, factory api.StreamFilterFactory, parser api.StreamFilterConfigParser) { if factory == nil { - panic("config factory should not be nil") + panic("filter factory should not be nil") + } + if parser == nil { + panic("config parser should not be nil") } - httpFilterConfigFactoryAndParser.Store(name, &filterConfigFactoryAndParser{factory, parser}) + httpFilterFactoryAndParser.Store(name, &filterFactoryAndParser{factory, parser}) } -func getOrCreateHttpFilterFactory(name string, configId uint64) api.StreamFilterFactory { +func getHttpFilterFactoryAndConfig(name string, configId uint64) (api.StreamFilterFactory, interface{}) { config, ok := configCache.Load(configId) if !ok { panic(fmt.Sprintf("config not found, plugin: %s, configId: %d", name, configId)) } - if v, ok := httpFilterConfigFactoryAndParser.Load(name); ok { - return (v.(*filterConfigFactoryAndParser)).configFactory(config) + if v, ok := httpFilterFactoryAndParser.Load(name); ok { + return (v.(*filterFactoryAndParser)).filterFactory, config } api.LogErrorf("plugin %s not found, pass through by default", name) - // pass through by default - return PassThroughFactory(config) + // return PassThroughFactory when no factory found + return PassThroughFactory, config } func getHttpFilterConfigParser(name string) api.StreamFilterConfigParser { - if v, ok := httpFilterConfigFactoryAndParser.Load(name); ok { - return (v.(*filterConfigFactoryAndParser)).configParser + if v, ok := httpFilterFactoryAndParser.Load(name); ok { + parser := (v.(*filterFactoryAndParser)).configParser + if parser == nil { + panic(fmt.Sprintf("config parser not found, plugin: %s", name)) + } + return parser } - return nil + // return NullParser when no parser found + return NullParser } diff --git a/contrib/golang/filters/http/source/go/pkg/http/passthrough.go b/contrib/golang/filters/http/source/go/pkg/http/passthrough.go index 2cffbd5c8a8db..6d000e37f79db 100644 --- a/contrib/golang/filters/http/source/go/pkg/http/passthrough.go +++ b/contrib/golang/filters/http/source/go/pkg/http/passthrough.go @@ -26,10 +26,8 @@ type passThroughFilter struct { callbacks api.FilterCallbackHandler } -func PassThroughFactory(interface{}) api.StreamFilterFactory { - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &passThroughFilter{ - callbacks: callbacks, - } +func PassThroughFactory(config interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { + return &passThroughFilter{ + callbacks: callbacks, } } diff --git a/contrib/golang/filters/http/source/go/pkg/http/shim.go b/contrib/golang/filters/http/source/go/pkg/http/shim.go index 45d4cf1d4fb64..d79a80659ab71 100644 --- a/contrib/golang/filters/http/source/go/pkg/http/shim.go +++ b/contrib/golang/filters/http/source/go/pkg/http/shim.go @@ -37,7 +37,6 @@ import ( "fmt" "runtime" "sync" - "sync/atomic" "github.com/envoyproxy/envoy/contrib/golang/common/go/api" ) @@ -46,33 +45,60 @@ var ErrDupRequestKey = errors.New("dup request key") var Requests = &requestMap{} +var ( + initialized = false + envoyConcurrency uint32 +) + +// EnvoyConcurrency returns the concurrency Envoy was set to run at. This can be used to optimize HTTP filters that need +// memory per worker thread to avoid locks. +// +// Note: Do not use inside of an `init()` function, the value will not be populated yet. Use within the filters +// `StreamFilterFactory` or `StreamFilterConfigParser` +func EnvoyConcurrency() uint32 { + if !initialized { + panic("concurrency has not yet been initialized, do not access within an init()") + } + return envoyConcurrency +} + type requestMap struct { - m sync.Map // *C.httpRequest -> *httpRequest + initOnce sync.Once + requests []map[*C.httpRequest]*httpRequest +} + +func (f *requestMap) initialize(concurrency uint32) { + f.initOnce.Do(func() { + initialized = true + envoyConcurrency = concurrency + f.requests = make([]map[*C.httpRequest]*httpRequest, concurrency) + for i := uint32(0); i < concurrency; i++ { + f.requests[i] = map[*C.httpRequest]*httpRequest{} + } + }) } func (f *requestMap) StoreReq(key *C.httpRequest, req *httpRequest) error { - if _, loaded := f.m.LoadOrStore(key, req); loaded { + m := f.requests[key.worker_id] + if _, ok := m[key]; ok { return ErrDupRequestKey } + m[key] = req return nil } func (f *requestMap) GetReq(key *C.httpRequest) *httpRequest { - if v, ok := f.m.Load(key); ok { - return v.(*httpRequest) - } - return nil + return f.requests[key.worker_id][key] } func (f *requestMap) DeleteReq(key *C.httpRequest) { - f.m.Delete(key) + delete(f.requests[key.worker_id], key) } func (f *requestMap) Clear() { - f.m.Range(func(key, _ interface{}) bool { - f.m.Delete(key) - return true - }) + for idx := range f.requests { + f.requests[idx] = map[*C.httpRequest]*httpRequest{} + } } func requestFinalize(r *httpRequest) { @@ -83,6 +109,7 @@ func createRequest(r *C.httpRequest) *httpRequest { req := &httpRequest{ req: r, } + req.cond.L = &req.waitingLock // NP: make sure filter will be deleted. runtime.SetFinalizer(req, requestFinalize) @@ -92,8 +119,8 @@ func createRequest(r *C.httpRequest) *httpRequest { } configId := uint64(r.configId) - filterFactory := getOrCreateHttpFilterFactory(req.pluginName(), configId) - f := filterFactory(req) + filterFactory, config := getHttpFilterFactoryAndConfig(req.pluginName(), configId) + f := filterFactory(config, req) req.httpFilter = f return req @@ -214,9 +241,6 @@ func envoyGoFilterOnHttpLog(r *C.httpRequest, logType uint64) { } defer req.RecoverPanic() - if atomic.CompareAndSwapInt32(&req.waitingOnEnvoy, 1, 0) { - req.sema.Done() - } v := api.AccessLogType(logType) @@ -238,9 +262,8 @@ func envoyGoFilterOnHttpDestroy(r *C.httpRequest, reason uint64) { req := getRequest(r) // do nothing even when req.panic is true, since filter is already destroying. defer req.RecoverPanic() - if atomic.CompareAndSwapInt32(&req.waitingOnEnvoy, 1, 0) { - req.sema.Done() - } + + req.resumeWaitCallback() v := api.DestroyReason(reason) @@ -259,7 +282,5 @@ func envoyGoFilterOnHttpDestroy(r *C.httpRequest, reason uint64) { func envoyGoRequestSemaDec(r *C.httpRequest) { req := getRequest(r) defer req.RecoverPanic() - if atomic.CompareAndSwapInt32(&req.waitingOnEnvoy, 1, 0) { - req.sema.Done() - } + req.resumeWaitCallback() } diff --git a/contrib/golang/filters/http/source/golang_filter.cc b/contrib/golang/filters/http/source/golang_filter.cc index 306336fc60001..edfab63a4e9c1 100644 --- a/contrib/golang/filters/http/source/golang_filter.cc +++ b/contrib/golang/filters/http/source/golang_filter.cc @@ -1458,6 +1458,7 @@ void Filter::initRequest(ProcessorState& state) { req_->configId = getMergedConfigId(state); req_->plugin_name.data = config_->pluginName().data(); req_->plugin_name.len = config_->pluginName().length(); + req_->worker_id = worker_id_; } /* ConfigId */ @@ -1491,6 +1492,7 @@ FilterConfig::FilterConfig( Server::Configuration::FactoryContext& context) : plugin_name_(proto_config.plugin_name()), so_id_(proto_config.library_id()), so_path_(proto_config.library_path()), plugin_config_(proto_config.plugin_config()), + concurrency_(context.serverFactoryContext().options().concurrency()), stats_(GolangFilterStats::generateStats(stats_prefix, context.scope())), dso_lib_(dso_lib), metric_store_(std::make_shared(context.scope().createScope(""))){}; @@ -1508,6 +1510,7 @@ void FilterConfig::newGoPluginConfig() { config_->config_ptr = buf_ptr; config_->config_len = buf.length(); config_->is_route_config = 0; + config_->concurrency = concurrency_; config_id_ = dso_lib_->envoyGoFilterNewHttpPluginConfig(config_); diff --git a/contrib/golang/filters/http/source/golang_filter.h b/contrib/golang/filters/http/source/golang_filter.h index cb342c437327b..cd90766e13369 100644 --- a/contrib/golang/filters/http/source/golang_filter.h +++ b/contrib/golang/filters/http/source/golang_filter.h @@ -85,6 +85,7 @@ class FilterConfig : public std::enable_shared_from_this, const std::string so_id_; const std::string so_path_; const ProtobufWkt::Any plugin_config_; + uint32_t concurrency_; GolangFilterStats stats_; @@ -170,9 +171,10 @@ class Filter : public Http::StreamFilter, Logger::Loggable, public AccessLog::Instance { public: - explicit Filter(FilterConfigSharedPtr config, Dso::HttpFilterDsoPtr dynamic_lib) - : config_(config), dynamic_lib_(dynamic_lib), decoding_state_(*this), encoding_state_(*this) { - } + explicit Filter(FilterConfigSharedPtr config, Dso::HttpFilterDsoPtr dynamic_lib, + uint32_t worker_id) + : config_(config), dynamic_lib_(dynamic_lib), decoding_state_(*this), encoding_state_(*this), + worker_id_(worker_id) {} // Http::StreamFilterBase void onDestroy() ABSL_LOCKS_EXCLUDED(mutex_) override; @@ -314,6 +316,10 @@ class Filter : public Http::StreamFilter, // the filter enter encoding phase bool enter_encoding_{false}; + + // The ID of the worker that is processing this request, this enables the go filter to dedicate + // memory to each worker and not require locks + uint32_t worker_id_ = 0; }; // Go code only touch the fields in httpRequest diff --git a/contrib/golang/filters/http/test/config_test.cc b/contrib/golang/filters/http/test/config_test.cc index 6bef239ec22da..315f815c8c422 100644 --- a/contrib/golang/filters/http/test/config_test.cc +++ b/contrib/golang/filters/http/test/config_test.cc @@ -59,7 +59,9 @@ TEST(GolangFilterConfigTest, GolangFilterWithValidConfig) { GolangFilterConfig factory; Http::FilterFactoryCb cb = factory.createFilterFactoryFromProto(proto_config, "stats", context).value(); - Http::MockFilterChainFactoryCallbacks filter_callback; + NiceMock filter_callback; + NiceMock dispatcher{"worker_0"}; + ON_CALL(filter_callback, dispatcher()).WillByDefault(ReturnRef(dispatcher)); EXPECT_CALL(filter_callback, addStreamFilter(_)); EXPECT_CALL(filter_callback, addAccessLogHandler(_)); auto plugin_config = proto_config.plugin_config(); @@ -83,7 +85,9 @@ TEST(GolangFilterConfigTest, GolangFilterWithNilPluginConfig) { GolangFilterConfig factory; Http::FilterFactoryCb cb = factory.createFilterFactoryFromProto(proto_config, "stats", context).value(); - Http::MockFilterChainFactoryCallbacks filter_callback; + NiceMock filter_callback; + NiceMock dispatcher{"worker_0"}; + ON_CALL(filter_callback, dispatcher()).WillByDefault(ReturnRef(dispatcher)); EXPECT_CALL(filter_callback, addStreamFilter(_)); EXPECT_CALL(filter_callback, addAccessLogHandler(_)); auto plugin_config = proto_config.plugin_config(); diff --git a/contrib/golang/filters/http/test/golang_filter_fuzz_test.cc b/contrib/golang/filters/http/test/golang_filter_fuzz_test.cc index e16ca408fa24a..6773ec59a174d 100644 --- a/contrib/golang/filters/http/test/golang_filter_fuzz_test.cc +++ b/contrib/golang/filters/http/test/golang_filter_fuzz_test.cc @@ -79,7 +79,7 @@ DEFINE_PROTO_FUZZER(const envoy::extensions::filters::http::golang::GolangFilter // Prepare filter. NiceMock context; FilterConfigSharedPtr config = std::make_shared(proto_config, dso_lib, "", context); - std::unique_ptr filter = std::make_unique(config, dso_lib); + std::unique_ptr filter = std::make_unique(config, dso_lib, 0); filter->setDecoderFilterCallbacks(mocks.decoder_callbacks_); filter->setEncoderFilterCallbacks(mocks.encoder_callbacks_); diff --git a/contrib/golang/filters/http/test/golang_filter_test.cc b/contrib/golang/filters/http/test/golang_filter_test.cc index f8bbbb05ee6e1..a5e785edd40ca 100644 --- a/contrib/golang/filters/http/test/golang_filter_test.cc +++ b/contrib/golang/filters/http/test/golang_filter_test.cc @@ -131,7 +131,7 @@ class GolangHttpFilterTest : public testing::Test { test_time.setSystemTime(std::chrono::microseconds(1583879145572237)); filter_ = std::make_unique( - config_, Dso::DsoManager::getDsoByPluginName(plugin_name)); + config_, Dso::DsoManager::getDsoByPluginName(plugin_name), 0); filter_->setDecoderFilterCallbacks(decoder_callbacks_); filter_->setEncoderFilterCallbacks(encoder_callbacks_); } diff --git a/contrib/golang/filters/http/test/test_data/access_log/config.go b/contrib/golang/filters/http/test/test_data/access_log/config.go index bad4d96e1d2b3..b51ab871eafe3 100644 --- a/contrib/golang/filters/http/test/test_data/access_log/config.go +++ b/contrib/golang/filters/http/test/test_data/access_log/config.go @@ -10,7 +10,7 @@ import ( const Name = "access_log" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } type config struct { @@ -28,16 +28,14 @@ func (p *parser) Merge(parent interface{}, child interface{}) interface{} { return child } -func ConfigFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - config: conf, - } + return &filter{ + callbacks: callbacks, + config: conf, } } diff --git a/contrib/golang/filters/http/test/test_data/action/config.go b/contrib/golang/filters/http/test/test_data/action/config.go index f02a961673f14..87b48690ac7f5 100644 --- a/contrib/golang/filters/http/test/test_data/action/config.go +++ b/contrib/golang/filters/http/test/test_data/action/config.go @@ -8,18 +8,12 @@ import ( const Name = "action" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, nil) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, http.NullParser) } -type config struct { - decodeHeadersRet api.StatusType -} - -func ConfigFactory(c interface{}) api.StreamFilterFactory { - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - } +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { + return &filter{ + callbacks: callbacks, } } diff --git a/contrib/golang/filters/http/test/test_data/basic/config.go b/contrib/golang/filters/http/test/test_data/basic/config.go index eed23a10748e7..cb099a60d70c6 100644 --- a/contrib/golang/filters/http/test/test_data/basic/config.go +++ b/contrib/golang/filters/http/test/test_data/basic/config.go @@ -11,14 +11,12 @@ func init() { api.LogCritical("init") api.LogCritical(api.GetLogLevel().String()) - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, nil) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, http.NullParser) } -func ConfigFactory(interface{}) api.StreamFilterFactory { - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - } +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { + return &filter{ + callbacks: callbacks, } } diff --git a/contrib/golang/filters/http/test/test_data/buffer/config.go b/contrib/golang/filters/http/test/test_data/buffer/config.go index cb88f346652b3..e2a5b75a207ce 100644 --- a/contrib/golang/filters/http/test/test_data/buffer/config.go +++ b/contrib/golang/filters/http/test/test_data/buffer/config.go @@ -10,7 +10,7 @@ import ( const Name = "buffer" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } type config struct { @@ -28,16 +28,14 @@ func (p *parser) Merge(parent interface{}, child interface{}) interface{} { return child } -func ConfigFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - config: conf, - } + return &filter{ + callbacks: callbacks, + config: conf, } } diff --git a/contrib/golang/filters/http/test/test_data/dummy/plugin.go b/contrib/golang/filters/http/test/test_data/dummy/plugin.go index 2fbb9bac79519..29e3978337749 100644 --- a/contrib/golang/filters/http/test/test_data/dummy/plugin.go +++ b/contrib/golang/filters/http/test/test_data/dummy/plugin.go @@ -7,7 +7,7 @@ import ( ) func init() { - http.RegisterHttpFilterConfigFactoryAndParser("", http.PassThroughFactory, nil) + http.RegisterHttpFilterFactoryAndConfigParser("", http.PassThroughFactory, http.NullParser) } func main() { diff --git a/contrib/golang/filters/http/test/test_data/echo/config.go b/contrib/golang/filters/http/test/test_data/echo/config.go index c98b1a636d5d7..3e501a0d0e148 100644 --- a/contrib/golang/filters/http/test/test_data/echo/config.go +++ b/contrib/golang/filters/http/test/test_data/echo/config.go @@ -11,7 +11,7 @@ import ( const Name = "echo" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } type config struct { @@ -43,16 +43,14 @@ func (p *parser) Merge(parent interface{}, child interface{}) interface{} { panic("TODO") } -func ConfigFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - config: conf, - } + return &filter{ + callbacks: callbacks, + config: conf, } } diff --git a/contrib/golang/filters/http/test/test_data/metric/config.go b/contrib/golang/filters/http/test/test_data/metric/config.go index e9ff554d45012..fcb2343a33578 100644 --- a/contrib/golang/filters/http/test/test_data/metric/config.go +++ b/contrib/golang/filters/http/test/test_data/metric/config.go @@ -13,7 +13,7 @@ func init() { api.LogCritical("init") api.LogCritical(api.GetLogLevel().String()) - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } type config struct { @@ -37,16 +37,14 @@ func (p *parser) Merge(parent interface{}, child interface{}) interface{} { panic("TODO") } -func ConfigFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - config: conf, - } + return &filter{ + callbacks: callbacks, + config: conf, } } diff --git a/contrib/golang/filters/http/test/test_data/passthrough/filter.go b/contrib/golang/filters/http/test/test_data/passthrough/filter.go index 17b40b0e459e5..3c90dbcd10598 100644 --- a/contrib/golang/filters/http/test/test_data/passthrough/filter.go +++ b/contrib/golang/filters/http/test/test_data/passthrough/filter.go @@ -5,7 +5,7 @@ import ( ) func init() { - http.RegisterHttpFilterConfigFactoryAndParser("passthrough", http.PassThroughFactory, nil) + http.RegisterHttpFilterFactoryAndConfigParser("passthrough", http.PassThroughFactory, http.NullParser) } func main() { diff --git a/contrib/golang/filters/http/test/test_data/property/config.go b/contrib/golang/filters/http/test/test_data/property/config.go index 21cc3ccd1fd80..60f10c98602c9 100644 --- a/contrib/golang/filters/http/test/test_data/property/config.go +++ b/contrib/golang/filters/http/test/test_data/property/config.go @@ -10,7 +10,7 @@ import ( const Name = "property" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } type config struct { @@ -28,16 +28,14 @@ func (p *parser) Merge(parent interface{}, child interface{}) interface{} { return child } -func ConfigFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - config: conf, - } + return &filter{ + callbacks: callbacks, + config: conf, } } diff --git a/contrib/golang/filters/http/test/test_data/routeconfig/config.go b/contrib/golang/filters/http/test/test_data/routeconfig/config.go index 73f3a2e02bd52..6b77040fd2a8b 100644 --- a/contrib/golang/filters/http/test/test_data/routeconfig/config.go +++ b/contrib/golang/filters/http/test/test_data/routeconfig/config.go @@ -13,19 +13,17 @@ import ( const Name = "routeconfig" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, configFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } -func configFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - config: conf, - callbacks: callbacks, - } + return &filter{ + config: conf, + callbacks: callbacks, } } diff --git a/contrib/golang/filters/network/source/go/pkg/network/filter.go b/contrib/golang/filters/network/source/go/pkg/network/filter.go index 6a113fd5c6625..22d1cf9aa63ff 100644 --- a/contrib/golang/filters/network/source/go/pkg/network/filter.go +++ b/contrib/golang/filters/network/source/go/pkg/network/filter.go @@ -113,6 +113,10 @@ func (n *connectionCallback) VirtualClusterName() (string, bool) { panic("implement me") } +func (n *connectionCallback) WorkerID() uint32 { + panic("implement me") +} + type filterState struct { wrapper unsafe.Pointer setFunc func(envoyFilter unsafe.Pointer, key string, value string, stateType api.StateType, lifeSpan api.LifeSpan, streamSharing api.StreamSharing) diff --git a/contrib/postgres_proxy/filters/network/source/postgres_decoder.cc b/contrib/postgres_proxy/filters/network/source/postgres_decoder.cc index 1ebf1491a37b5..6289a094fa089 100644 --- a/contrib/postgres_proxy/filters/network/source/postgres_decoder.cc +++ b/contrib/postgres_proxy/filters/network/source/postgres_decoder.cc @@ -76,7 +76,7 @@ void DecoderImpl::initialize() { BE_known_msgs['D'] = MessageProcessor{"DataRow", BODY_FORMAT(Array), {}}; BE_known_msgs['I'] = MessageProcessor{"EmptyQueryResponse", NO_BODY, {}}; BE_known_msgs['E'] = MessageProcessor{ - "ErrorResponse", BODY_FORMAT(Byte1, String), {&DecoderImpl::decodeBackendErrorResponse}}; + "ErrorResponse", BODY_FORMAT(ZeroTCodes), {&DecoderImpl::decodeBackendErrorResponse}}; BE_known_msgs['V'] = MessageProcessor{"FunctionCallResponse", BODY_FORMAT(VarByteN), {}}; BE_known_msgs['v'] = MessageProcessor{"NegotiateProtocolVersion", BODY_FORMAT(ByteN), {}}; BE_known_msgs['n'] = MessageProcessor{"NoData", NO_BODY, {}}; diff --git a/contrib/postgres_proxy/filters/network/source/postgres_message.h b/contrib/postgres_proxy/filters/network/source/postgres_message.h index 584662f0b7546..2dca99e6ee4d2 100644 --- a/contrib/postgres_proxy/filters/network/source/postgres_message.h +++ b/contrib/postgres_proxy/filters/network/source/postgres_message.h @@ -95,6 +95,11 @@ template class Int { T get() const { return value_; } + T& operator=(const T& other) { + value_ = other; + return value_; + } + private: T value_{}; }; @@ -287,6 +292,69 @@ template class Repeated { std::vector> value_; }; +// ZeroTCodes (Zero Terminated Codes) is a structure which represents sequence of: +// [code][value] +// [code][value] +// ... +// [code][value] +// zero +// Where code is 1 Byte. +template class ZeroTCodes { +public: + bool read(const Buffer::Instance& data, uint64_t& pos, uint64_t& left) { + for (size_t i = 0; i < values_.size(); i++) { + if (!values_[i].first.read(data, pos, left)) { + return false; + } + if (!values_[i].second->read(data, pos, left)) { + return false; + } + } + return true; + } + + std::string toString() const { + std::string out; + for (const auto& value : values_) { + out += fmt::format("[{}:{}]", value.first.toString(), value.second->toString()); + } + return out; + } + + Message::ValidationResult validate(const Buffer::Instance& data, const uint64_t start_offset, + uint64_t& pos, uint64_t& left) { + uint64_t orig_pos = pos; + uint64_t orig_left = left; + // Check if one byte of code can be read. + while (left >= sizeof(Byte1)) { + // Read 1 byte code and exit when terminating zero is found. + Byte1 code; + code = data.peekBEInt(pos); + // Advance the position by 1 byte (code). + pos += sizeof(Byte1); + left -= sizeof(Byte1); + if (code.get() == 0) { + return Message::ValidationOK; + } + + // Validate the value found after the code. + auto item = std::make_unique(); + Message::ValidationResult result = item->validate(data, start_offset, pos, left); + if (Message::ValidationOK != result) { + pos = orig_pos; + left = orig_left; + values_.clear(); + return result; + } + values_.push_back(std::make_pair(code, std::move(item))); + } + + return Message::ValidationFailed; + } + + std::vector>> values_; +}; + // Sequence is tuple like structure, which binds together // set of several fields of different types. template class Sequence; @@ -330,8 +398,8 @@ template <> class Sequence<> { std::string toString() const { return ""; } bool read(const Buffer::Instance&, uint64_t&, uint64_t&) { return true; } Message::ValidationResult validate(const Buffer::Instance&, const uint64_t, uint64_t&, - uint64_t& left) { - return left == 0 ? Message::ValidationOK : Message::ValidationFailed; + uint64_t&) { + return Message::ValidationOK; } }; @@ -350,6 +418,13 @@ template class MessageImpl : public Message, public Sequence uint64_t pos = start_pos; uint64_t left = length; validation_result_ = Sequence::validate(data, start_pos, pos, left); + if (validation_result_ != Message::ValidationOK) { + return validation_result_; + } + // verify that parser iterated over entire message and nothing is left. + if (left != 0) { + validation_result_ = Message::ValidationFailed; + } return validation_result_; } std::string toString() const override { return Sequence::toString(); } diff --git a/contrib/postgres_proxy/filters/network/test/postgres_decoder_test.cc b/contrib/postgres_proxy/filters/network/test/postgres_decoder_test.cc index 4101ea89df645..fbf6f57504faf 100644 --- a/contrib/postgres_proxy/filters/network/test/postgres_decoder_test.cc +++ b/contrib/postgres_proxy/filters/network/test/postgres_decoder_test.cc @@ -9,6 +9,8 @@ namespace Extensions { namespace NetworkFilters { namespace PostgresProxy { +using namespace std::literals::string_literals; + class DecoderCallbacksMock : public DecoderCallbacks { public: MOCK_METHOD(void, incMessagesBackend, (), (override)); @@ -519,21 +521,28 @@ TEST_P(PostgresProxyErrorTest, ParseErrorMsgs) { INSTANTIATE_TEST_SUITE_P( PostgresProxyErrorTestSuite, PostgresProxyErrorTest, ::testing::Values( - std::make_tuple("blah blah", DecoderCallbacks::ErrorType::Unknown), - std::make_tuple("SERRORC1234", DecoderCallbacks::ErrorType::Error), - std::make_tuple("SERRORVERRORC1234", DecoderCallbacks::ErrorType::Error), - std::make_tuple("SFATALVFATALC22012", DecoderCallbacks::ErrorType::Fatal), - std::make_tuple("SPANICVPANICC22012", DecoderCallbacks::ErrorType::Panic), + // Error is encoded as sequence of 1-byte code, string. + // The sequence is terminated by 1-byte code equal to zero. + // That is the reason why each string contains 'zero' at the end. + // Each string literal is packed in std::string and std::string will add + // another 'zero' which will be interpreted as 1-byte terminating code. + std::make_tuple("blah blah\0"s, DecoderCallbacks::ErrorType::Unknown), + std::make_tuple("SERRORC1234\0"s, DecoderCallbacks::ErrorType::Error), + std::make_tuple("SERRORVERRORC1234\0"s, DecoderCallbacks::ErrorType::Error), + std::make_tuple("SFATALVFATALC22012\0"s, DecoderCallbacks::ErrorType::Fatal), + std::make_tuple("SPANICVPANICC22012\0"s, DecoderCallbacks::ErrorType::Panic), + std::make_tuple("SERROR\0VERROR\0C22012\0Mdivision by zero\0Fint.c\0L820\0Rint4div\0"s, + DecoderCallbacks::ErrorType::Error), // This is the real German message in Postgres > 9.6. It contains keyword // in English with V prefix. std::make_tuple("SPANIKVPANICC42501Mkonnte Datei »pg_wal/000000010000000100000096« nicht " - "öffnen: Permission deniedFxlog.cL3229RXLogFileInit", + "öffnen: Permission denAiedFxlog.cL3229RXLogFileInit\0"s, DecoderCallbacks::ErrorType::Panic), // This is German message indicating error. The comment field contains word PANIC. // Since we do not decode other languages, it should go into Other bucket. // This situation can only happen in Postgres < 9.6. Starting with version 9.6 // messages must have severity in English with prefix V. - std::make_tuple("SFEHLERCP0001MMy PANIC ugly messageFpl_exec.cL3216Rexec_stmt_raise", + std::make_tuple("SFEHLERCP0001MMy PANIC ugly messageFpl_exec.cL3216Rexec_stmt_raise\0"s, DecoderCallbacks::ErrorType::Unknown))); // Test parsing N message. It indicate notice diff --git a/contrib/postgres_proxy/filters/network/test/postgres_filter_test.cc b/contrib/postgres_proxy/filters/network/test/postgres_filter_test.cc index 6911a0c0facc5..bb148621c3664 100644 --- a/contrib/postgres_proxy/filters/network/test/postgres_filter_test.cc +++ b/contrib/postgres_proxy/filters/network/test/postgres_filter_test.cc @@ -18,6 +18,8 @@ namespace PostgresProxy { using testing::ReturnRef; using ::testing::WithArgs; +using namespace std::literals::string_literals; + // Decoder mock. class MockDecoderTest : public Decoder { public: @@ -239,22 +241,22 @@ TEST_F(PostgresFilterTest, ErrorMsgsStats) { // Pretend that startup message has been received. static_cast(filter_->getDecoder())->state(DecoderImpl::State::InSyncState); - createPostgresMsg(data_, "E", "SERRORVERRORC22012"); + createPostgresMsg(data_, "E", "SERRORVERRORC22012\0"s); filter_->onWrite(data_, false); ASSERT_THAT(filter_->getStats().errors_.value(), 1); ASSERT_THAT(filter_->getStats().errors_error_.value(), 1); - createPostgresMsg(data_, "E", "SFATALVFATALC22012"); + createPostgresMsg(data_, "E", "SFATALVFATALC22012\0"s); filter_->onWrite(data_, false); ASSERT_THAT(filter_->getStats().errors_.value(), 2); ASSERT_THAT(filter_->getStats().errors_fatal_.value(), 1); - createPostgresMsg(data_, "E", "SPANICVPANICC22012"); + createPostgresMsg(data_, "E", "SPANICVPANICC22012\0Mmessage\0"s); filter_->onWrite(data_, false); ASSERT_THAT(filter_->getStats().errors_.value(), 3); ASSERT_THAT(filter_->getStats().errors_panic_.value(), 1); - createPostgresMsg(data_, "E", "SBLAHBLAHC22012"); + createPostgresMsg(data_, "E", "SBLAHBLAHC22012\0"s); filter_->onWrite(data_, false); ASSERT_THAT(filter_->getStats().errors_.value(), 4); ASSERT_THAT(filter_->getStats().errors_unknown_.value(), 1); diff --git a/contrib/postgres_proxy/filters/network/test/postgres_message_test.cc b/contrib/postgres_proxy/filters/network/test/postgres_message_test.cc index 91980d376748c..d9d77666a01f4 100644 --- a/contrib/postgres_proxy/filters/network/test/postgres_message_test.cc +++ b/contrib/postgres_proxy/filters/network/test/postgres_message_test.cc @@ -1010,6 +1010,41 @@ TEST(PostgresMessage, ArraySet6) { ASSERT_TRUE(out.find("114") != std::string::npos); } +TEST(PostgresMessage, ArraySet7) { + // Array of Sequences + std::unique_ptr msg = createMsgBodyReader>>(); + + Buffer::OwnedImpl data; + // There will be 3 sequences in the array. + data.writeBEInt(3); + + // 1st sequence. + data.add("seq1"); + data.writeBEInt(0); + data.writeBEInt(111); + + // 2nd sequence. + data.add("seq2"); + data.writeBEInt(0); + data.writeBEInt(222); + + // 3rd sequence. + data.add("seq3"); + data.writeBEInt(0); + data.writeBEInt(333); + + const uint64_t length = 2 + 3 * (5 + 2); + ASSERT_THAT(msg->validate(data, 0, length), Message::ValidationOK); + ASSERT_TRUE(msg->read(data, length)); + auto out = msg->toString(); + ASSERT_TRUE(out.find("seq1") != std::string::npos); + ASSERT_TRUE(out.find("seq2") != std::string::npos); + ASSERT_TRUE(out.find("seq3") != std::string::npos); + ASSERT_TRUE(out.find("111") != std::string::npos); + ASSERT_TRUE(out.find("222") != std::string::npos); + ASSERT_TRUE(out.find("333") != std::string::npos); +} + TEST(PostgresMessage, Repeated1) { std::unique_ptr msg = createMsgBodyReader>(); diff --git a/contrib/qat/compression/qatzip/compressor/source/BUILD b/contrib/qat/compression/qatzip/compressor/source/BUILD index 099bb2906651e..fe18d6d9240f0 100644 --- a/contrib/qat/compression/qatzip/compressor/source/BUILD +++ b/contrib/qat/compression/qatzip/compressor/source/BUILD @@ -39,7 +39,8 @@ configure_make( "//bazel/foreign_cc:lz4", "//bazel/foreign_cc:zlib", "//contrib/qat:qatlib", - "@boringssl//:ssl", + # Use boringssl alias to select fips vs non-fips version. + "//bazel:boringssl", ], alwayslink = False, ) diff --git a/docs/root/configuration/http/cluster_specifier/lua.rst b/docs/root/configuration/http/cluster_specifier/lua.rst index 0cab42c25cd03..da53f3d502d08 100644 --- a/docs/root/configuration/http/cluster_specifier/lua.rst +++ b/docs/root/configuration/http/cluster_specifier/lua.rst @@ -6,10 +6,15 @@ Lua cluster specifier Overview -------- -The HTTP Lua cluster specifier allows `Lua `_ scripts to select router cluster -during the request flows. `LuaJIT `_ is used as the runtime. Because of this, the -supported Lua version is mostly 5.1 with some 5.2 features. See the `LuaJIT documentation -`_ for more details. +The HTTP Lua cluster specifier allows `Lua `_ scripts to select a router cluster +during the request flow. + +.. note:: + `LuaJIT `_ is used as the runtime. + + This means that the currently supported Lua version is mostly 5.1 with some 5.2 features. + + See the `LuaJIT documentation `_ for more details. Configuration ------------- @@ -17,61 +22,52 @@ Configuration * This filter should be configured with the type URL ``type.googleapis.com/envoy.extensions.router.cluster_specifiers.lua.v3.LuaConfig``. * :ref:`v3 API reference ` -A simple example of configuring Lua cluster specifier is as follow: - -.. code-block:: yaml - - routes: - - match: - prefix: "/" - route: - inline_cluster_specifier_plugin: - extension: - name: envoy.router.cluster_specifier_plugin.lua - typed_config: - "@type": type.googleapis.com/envoy.extensions.router.cluster_specifiers.lua.v3.LuaConfig - source_code: - inline_string: | - function envoy_on_route(route_handle) - local header_value = route_handle:headers():get("header_key") - if header_value == "fake" then - return "fake_service" - end - return "web_service" - end - default_cluster: web_service - -Lua script defined in ``source_code`` will be executed to select router cluster, and just as cluster specifier -plugin in C++, Lua script can also select router cluster based on request headers. If Lua script execute failure, -``default_cluster`` will be used. +A simple example configuration of a Lua cluster: + +.. literalinclude:: /start/sandboxes/_include/lua-cluster-specifier/envoy.yaml + :language: yaml + :lines: 22-40 + :emphasize-lines: 3-17 + :linenos: + :caption: :download:`lua-cluster-specifier.yaml ` + +The Lua script defined in +:ref:`source_code ` +will be executed to select the routed cluster. + +It can also select a cluster based on matched request headers. + +If execution of the Lua script results in failure, the +:ref:`default_cluster ` +will be used. Complete example ---------------- -A complete example using Docker is available in :repo:`/examples/lua-cluster-specifier`. +A complete example using Docker is available in the :ref:`Lua cluster specifier sandbox `. Route handle API ---------------- -When Envoy loads the script in the configuration, it looks for a global function that the script defines: +When Envoy loads the script in the configuration, it looks for a global function defined by the script: .. code-block:: lua function envoy_on_route(route_handle) end -During the route path, Envoy will run *envoy_on_route* as a coroutine, passing a handle to the route API. +Following the route path, Envoy will run ``envoy_on_route`` as a coroutine, passing a handle to the route API. -The following methods on the stream handle are supported: +The following method on the stream handle is supported: -headers() -^^^^^^^^^ +``headers()`` ++++++++++++++ .. code-block:: lua - local headers = handle:headers() + local headers = route_handle:headers() -Returns the stream's headers. The headers can be used to match to select a specific cluster. +Returns the stream's headers. The headers can be used to select a specific cluster. Returns a :ref:`header object `. @@ -80,13 +76,17 @@ Returns a :ref:`header object `. Header object API ----------------- -get() -^^^^^ +``get()`` ++++++++++ .. code-block:: lua headers:get(key) -Gets a header. *key* is a string that supplies the header key. Returns a string that is the header -value or nil if there is no such header. If there are multiple headers in the same case-insensitive -key, their values will be combined with a *,* separator and returned as a string. +This method gets a header. + +``key`` is a string that specifies the header key. + +Returns either a string containing the header value, or ``nil`` if the header does not exist. + +If there are multiple headers in the same case-insensitive key, their values will be concatenated to a string separated by ``,``. diff --git a/docs/root/configuration/http/http_filters/_include/aws-request-signing-filter-upstream.yaml b/docs/root/configuration/http/http_filters/_include/aws-request-signing-filter-upstream.yaml new file mode 100644 index 0000000000000..0ef1de1b51284 --- /dev/null +++ b/docs/root/configuration/http/http_filters/_include/aws-request-signing-filter-upstream.yaml @@ -0,0 +1,63 @@ +static_resources: + listeners: + - address: + socket_address: + address: 0.0.0.0 + port_value: 10000 + filter_chains: + - filters: + - name: envoy.filters.network.http_connection_manager + typed_config: + '@type': type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager + stat_prefix: ingress_http + http_filters: + - name: envoy.filters.http.router + typed_config: + '@type': type.googleapis.com/envoy.extensions.filters.http.router.v3.Router + route_config: + name: local_route + virtual_hosts: + - domains: + - '*' + name: local_service + routes: + - match: {prefix: "/"} + route: {cluster: default_service} + clusters: + - name: default_service + load_assignment: + cluster_name: default_service + endpoints: + - lb_endpoints: + - endpoint: + address: + socket_address: + address: 127.0.0.1 + port_value: 10001 + typed_extension_protocol_options: + envoy.extensions.upstreams.http.v3.HttpProtocolOptions: + "@type": type.googleapis.com/envoy.extensions.upstreams.http.v3.HttpProtocolOptions + upstream_http_protocol_options: + auto_sni: true + auto_san_validation: true + auto_config: + http2_protocol_options: {} + http_filters: + - name: envoy.filters.http.aws_request_signing + typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.http.aws_request_signing.v3.AwsRequestSigning + service_name: vpc-lattice-svcs + region: '*' + signing_algorithm: AWS_SIGV4A + use_unsigned_payload: true + match_excluded_headers: + - prefix: x-envoy + - prefix: x-forwarded + - exact: x-amzn-trace-id + - name: envoy.filters.http.upstream_codec + typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.http.upstream_codec.v3.UpstreamCodec + transport_socket: + name: envoy.transport_sockets.tls + typed_config: + "@type": type.googleapis.com/envoy.extensions.transport_sockets.tls.v3.UpstreamTlsContext diff --git a/docs/root/configuration/http/http_filters/adaptive_concurrency_filter.rst b/docs/root/configuration/http/http_filters/adaptive_concurrency_filter.rst index 440de1b987517..a66d2907c55af 100644 --- a/docs/root/configuration/http/http_filters/adaptive_concurrency_filter.rst +++ b/docs/root/configuration/http/http_filters/adaptive_concurrency_filter.rst @@ -202,7 +202,7 @@ The gradient controller uses the namespace rq_blocked, Counter, Total requests that were blocked by the filter. min_rtt_calculation_active, Gauge, Set to 1 if the controller is in the process of a minRTT calculation. 0 otherwise. concurrency_limit, Gauge, The current concurrency limit. - gradient, Gauge, The current gradient value. + gradient, Gauge, The current gradient value multiplied by 1000 (values will range between 500 and 2000). burst_queue_size, Gauge, The current headroom value in the concurrency limit calculation. min_rtt_msecs, Gauge, The current measured minRTT value. sample_rtt_msecs, Gauge, The current measured sampleRTT aggregate. diff --git a/docs/root/configuration/http/http_filters/aws_request_signing_filter.rst b/docs/root/configuration/http/http_filters/aws_request_signing_filter.rst index 2cc45b72030d5..cbb5be867bbda 100644 --- a/docs/root/configuration/http/http_filters/aws_request_signing_filter.rst +++ b/docs/root/configuration/http/http_filters/aws_request_signing_filter.rst @@ -52,7 +52,7 @@ Example filter configuration: :linenos: :caption: :download:`aws-request-signing-filter.yaml <_include/aws-request-signing-filter.yaml>` -Note that this filter also supports per route configuration: +This filter also supports per route configuration. Below is an example of route-level config overriding the config at the virtual-host level. .. literalinclude:: _include/aws-request-signing-filter-route-level-override.yaml :language: yaml @@ -61,9 +61,7 @@ Note that this filter also supports per route configuration: :linenos: :caption: :download:`aws-request-signing-filter-route-level-override.yaml <_include/aws-request-signing-filter-route-level-override.yaml>` -Above shows an example of route-level config overriding the config on the virtual-host level. - -An example of configuring this filter to use ``AWS_SIGV4A`` signing with a wildcarded region set, to a AWS VPC Lattice service: +An example of configuring this filter to use ``AWS_SIGV4A`` signing with a wildcarded region set, to an Amazon VPC Lattice service: .. literalinclude:: _include/aws-request-signing-filter-sigv4a.yaml :language: yaml @@ -72,6 +70,27 @@ An example of configuring this filter to use ``AWS_SIGV4A`` signing with a wildc :linenos: :caption: :download:`aws-request-signing-filter-sigv4a.yaml <_include/aws-request-signing-filter-sigv4a.yaml>` + +Configuration as an upstream HTTP filter +---------------------------------------- +SigV4 or SigV4A request signatures are calculated using the HTTP host, URL and payload as input. Depending on the configuration, Envoy may modify one or more of +these prior to forwarding to the Cluster subsystem, but after the signature has been calculated and inserted into the HTTP headers. Modifying fields in a SigV4 or SigV4A +signed request will result in an invalid signature. + +To avoid invalid signatures, the AWS Request Signing Filter can be configured as an upstream HTTP filter. This allows signatures to be +calculated as a final step before the HTTP request is forwarded upstream, ensuring signatures are correctly calculated over the updated +HTTP fields. + +Configuring this filter as an upstream HTTP filter is done in a similar way to the downstream case, but using the :ref:`http_filters ` +filter chain within the cluster configuration. + +.. literalinclude:: _include/aws-request-signing-filter-upstream.yaml + :language: yaml + :lines: 47-57 + :lineno-start: 47 + :linenos: + :caption: :download:`aws-request-signing-filter-upstream.yaml <_include/aws-request-signing-filter-upstream.yaml>` + .. include:: _include/aws_credentials.rst Statistics diff --git a/docs/root/configuration/observability/access_log/usage.rst b/docs/root/configuration/observability/access_log/usage.rst index 498fc923e0e31..30ea630e5b19e 100644 --- a/docs/root/configuration/observability/access_log/usage.rst +++ b/docs/root/configuration/observability/access_log/usage.rst @@ -679,6 +679,15 @@ UDP is unique with high likelihood within an execution, but can duplicate across multiple instances or between restarts. +.. _config_access_log_format_upstream_connection_id: + +%UPSTREAM_CONNECTION_ID% + An identifier for the upstream connection. It can be used to + cross-reference TCP access logs across multiple log sinks, or to + cross-reference timer-based reports for the same connection. The identifier + is unique with high likelihood within an execution, but can duplicate across + multiple instances or between restarts. + .. _config_access_log_format_stream_id: %STREAM_ID% diff --git a/docs/root/configuration/other_protocols/thrift_filters/router_filter.rst b/docs/root/configuration/other_protocols/thrift_filters/router_filter.rst index 48772f66b464c..e2f782a6af321 100644 --- a/docs/root/configuration/other_protocols/thrift_filters/router_filter.rst +++ b/docs/root/configuration/other_protocols/thrift_filters/router_filter.rst @@ -50,6 +50,10 @@ Since these stats utilize the underlying cluster scope, we prefix with the ``thr thrift.upstream_cx_drain_close, Counter, Total upstream connections that were closed due to draining. thrift.downstream_cx_partial_response_close, Counter, Total downstream connections that were closed due to the partial response. thrift.downstream_cx_underflow_response_close, Counter, Total downstream connections that were closed due to the underflow response. + thrift.upstream_resp_exception_local.overflow, Counter, Total responses with the "Exception" message type generated locally by connection pool overflow. + thrift.upstream_resp_exception_local.local_connection_failure, Counter, Total responses with the "Exception" message type generated locally by local connection failure. + thrift.upstream_resp_exception_local.remote_connection_failure", Counter, Total responses with the "Exception" message type generated locally by remote connection failure. + thrift.upstream_resp_exception_local.timeout, Counter, Total responses with the "Exception" message type generated locally by timeout while creating a new connection. If the service zone is available for both the local service (via :option:`--service-zone`) and the :ref:`upstream cluster `, diff --git a/docs/root/faq/configuration/sni.rst b/docs/root/faq/configuration/sni.rst index d4aa61c56808d..d01586e429e1a 100644 --- a/docs/root/faq/configuration/sni.rst +++ b/docs/root/faq/configuration/sni.rst @@ -19,6 +19,8 @@ The following is a YAML example of the above requirement. socket_address: { address: 127.0.0.1, port_value: 1234 } listener_filters: - name: "envoy.filters.listener.tls_inspector" + typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.listener.tls_inspector.v3.TlsInspector filter_chains: - filter_chain_match: server_names: ["example.com", "www.example.com"] diff --git a/docs/root/intro/arch_overview/advanced/attributes.rst b/docs/root/intro/arch_overview/advanced/attributes.rst index aabbf41ce3685..024da72875205 100644 --- a/docs/root/intro/arch_overview/advanced/attributes.rst +++ b/docs/root/intro/arch_overview/advanced/attributes.rst @@ -119,7 +119,7 @@ RBAC): connection.dns_san_peer_certificate, string, The first DNS entry in the SAN field of the peer certificate in the downstream TLS connection connection.uri_san_local_certificate, string, The first URI entry in the SAN field of the local certificate in the downstream TLS connection connection.uri_san_peer_certificate, string, The first URI entry in the SAN field of the peer certificate in the downstream TLS connection - connection.sha256_peer_certificate_digest, SHA256 digest of the peer certificate in the downstream TLS connection if present + connection.sha256_peer_certificate_digest, string, SHA256 digest of the peer certificate in the downstream TLS connection if present connection.transport_failure_reason, string, The transport failure reason e.g. certificate validation failed The following additional attributes are available upon the downstream connection termination: @@ -148,7 +148,7 @@ The following attributes are available once the upstream connection is establish upstream.dns_san_peer_certificate, string, The first DNS entry in the SAN field of the peer certificate in the upstream TLS connection upstream.uri_san_local_certificate, string, The first URI entry in the SAN field of the local certificate in the upstream TLS connection upstream.uri_san_peer_certificate, string, The first URI entry in the SAN field of the peer certificate in the upstream TLS connection - upstream.sha256_peer_certificate_digest, SHA256 digest of the peer certificate in the upstream TLS connection if present + upstream.sha256_peer_certificate_digest, string, SHA256 digest of the peer certificate in the upstream TLS connection if present upstream.local_address, string, The local address of the upstream connection upstream.transport_failure_reason, string, The upstream transport failure reason e.g. certificate validation failed diff --git a/docs/root/start/sandboxes/lua-cluster-specifier.rst b/docs/root/start/sandboxes/lua-cluster-specifier.rst index a7e4c852c849e..f927333ad7554 100644 --- a/docs/root/start/sandboxes/lua-cluster-specifier.rst +++ b/docs/root/start/sandboxes/lua-cluster-specifier.rst @@ -1,6 +1,6 @@ .. _install_sandboxes_lua_cluster_specifier: -Lua Cluster Specifier +Lua cluster specifier ===================== .. sidebar:: Requirements @@ -17,13 +17,15 @@ The example Envoy proxy configuration includes a Lua cluster specifier plugin th - ``envoy_on_route(route_handle)`` -:ref:`See here ` for an overview of Envoy's Lua cluster specifier -and documentation regarding the function. +.. tip:: + + See the :ref:`Lua cluster configuration documentation ` for an overview and + documentation regarding the function. Step 1: Build the sandbox ************************* -Change to the ``examples/lua-cluster-specifier`` directory. +Change to the ``examples/lua-cluster-specifier`` directory, and bring up the composition. .. code-block:: console @@ -35,27 +37,23 @@ Change to the ``examples/lua-cluster-specifier`` directory. Name Command State Ports -------------------------------------------------------------------------------------------- - lua-cluster-specifier-proxy-1 /docker-entrypoint.sh /usr ... Up 10000/tcp, 0.0.0.0:8000->8000/tcp - lua-cluster-specifier-web_service-1 /bin/echo-server Up 0.0.0.0:8080->8080/tcp + lua-cluster-specifier-proxy-1 /docker-entrypoint.sh /usr ... Up 10000/tcp, 0.0.0.0:10000->10000/tcp Step 2: Send a request to the normal service ******************************************** The output from the ``curl`` command below should return 200, since the lua code select the normal service. -Terminal 1 - .. code-block:: console - $ curl -i localhost:8000/anything 2>&1 |grep 200 + $ curl -i localhost:10000/anything 2>&1 |grep 200 HTTP/1.1 200 OK Step 3: Send a request to the fake service ****************************************** -The output from the ``curl`` command below should return 503, since the lua code select the fake service. - -Terminal 1 +If you specify the request header ``header_key:fake``, curl will return a ``503`` response, as +the Lua code will select the fake service. .. code-block:: console diff --git a/envoy/common/BUILD b/envoy/common/BUILD index f32828da2aa8f..e1ee7d1f36759 100644 --- a/envoy/common/BUILD +++ b/envoy/common/BUILD @@ -121,9 +121,19 @@ envoy_cc_library( hdrs = ["backoff_strategy.h"], ) +envoy_cc_library( + name = "execution_context", + hdrs = ["execution_context.h"], + deps = [":pure_lib"], +) + envoy_cc_library( name = "scope_tracker_interface", hdrs = ["scope_tracker.h"], + deps = [ + ":execution_context", + ":pure_lib", + ], ) envoy_cc_library( diff --git a/envoy/common/execution_context.h b/envoy/common/execution_context.h new file mode 100644 index 0000000000000..fb227a05af415 --- /dev/null +++ b/envoy/common/execution_context.h @@ -0,0 +1,68 @@ +#pragma once + +#include + +#include "envoy/common/pure.h" + +#include "source/common/common/non_copyable.h" + +namespace Envoy { + +class ScopedExecutionContext; + +// ExecutionContext can be inherited by subclasses to represent arbitrary information associated +// with the execution of a piece of code. activate/deactivate are called when the said execution +// starts/ends. For an example usage, please see +// https://github.com/envoyproxy/envoy/issues/32012. +class ExecutionContext : NonCopyable { +public: + ExecutionContext() = default; + virtual ~ExecutionContext() = default; + +protected: + // Called when the current thread starts to run code on behalf of the owner of this object. + // protected because it should only be called by ScopedExecutionContext. + virtual void activate() PURE; + // Called when the current thread stops running code on behalf of the owner of this object. + // protected because it should only be called by ScopedExecutionContext. + virtual void deactivate() PURE; + + friend class ScopedExecutionContext; +}; + +// ScopedExecutionContext is a stack-only RAII object to call ExecutionContext::activate on +// construction and ExecutionContext::deactivate on destruction. +// +// ScopedExecutionContext is intened to be used in a simple c++ scope: +// { +// ExecutionContext context; +// // context.activate() called here. +// ScopedExecutionContext scoped_execution_context(&context); +// // context.deactivate() called when scoped_execution_context destructs. +// } +class ScopedExecutionContext : NonCopyable { +public: + ScopedExecutionContext() : ScopedExecutionContext(nullptr) {} + ScopedExecutionContext(ExecutionContext* context) : context_(context) { + if (context_ != nullptr) { + context_->activate(); + } + } + + ~ScopedExecutionContext() { + if (context_ != nullptr) { + context_->deactivate(); + } + } + + // This object is stack-only, it is part of ScopeTrackerScopeState which is + // also stack-only. + void* operator new(std::size_t) = delete; + + bool isNull() const { return context_ == nullptr; } + +private: + ExecutionContext* context_; +}; + +} // namespace Envoy diff --git a/envoy/common/platform.h b/envoy/common/platform.h index a877e91083d13..42075f881f80d 100644 --- a/envoy/common/platform.h +++ b/envoy/common/platform.h @@ -329,3 +329,9 @@ struct mmsghdr { // On non-Linux platforms use 128 which is libevent listener default #define ENVOY_TCP_BACKLOG_SIZE 128 #endif + +#if defined(__linux__) +#define ENVOY_PLATFORM_ENABLE_SEND_RST 1 +#else +#define ENVOY_PLATFORM_ENABLE_SEND_RST 0 +#endif diff --git a/envoy/common/scope_tracker.h b/envoy/common/scope_tracker.h index 4c9d8fbc42197..f96425541513b 100644 --- a/envoy/common/scope_tracker.h +++ b/envoy/common/scope_tracker.h @@ -2,6 +2,7 @@ #include +#include "envoy/common/execution_context.h" #include "envoy/common/pure.h" namespace Envoy { @@ -18,6 +19,11 @@ class ScopeTrackedObject { public: virtual ~ScopeTrackedObject() = default; + /** + * If the tracked object has a ExecutionContext, returns it. Returns nullptr otherwise. + */ + virtual ExecutionContext* executionContext() const { return nullptr; } + /** * Dump debug state of the object in question to the provided ostream. * diff --git a/envoy/http/query_params.h b/envoy/http/query_params.h index 03cac1771d198..b41530d67c8c3 100644 --- a/envoy/http/query_params.h +++ b/envoy/http/query_params.h @@ -4,10 +4,11 @@ #include #include +#include "envoy/http/header_map.h" + #include "absl/container/btree_map.h" #include "absl/strings/string_view.h" #include "absl/types/optional.h" -#include "header_map.h" namespace Envoy { namespace Http { diff --git a/envoy/server/filter_config.h b/envoy/server/filter_config.h index aaffe9edd00bf..b06fe858402f0 100644 --- a/envoy/server/filter_config.h +++ b/envoy/server/filter_config.h @@ -117,8 +117,9 @@ class ProtocolOptionsFactory : public Config::TypedFactory { * @param config supplies the protobuf configuration for the filter * @param validation_visitor message validation visitor instance. * @return Upstream::ProtocolOptionsConfigConstSharedPtr the protocol options + * or an error message. */ - virtual Upstream::ProtocolOptionsConfigConstSharedPtr + virtual absl::StatusOr createProtocolOptionsConfig(const Protobuf::Message& config, ProtocolOptionsFactoryContext& factory_context) { UNREFERENCED_PARAMETER(config); diff --git a/envoy/stream_info/stream_info.h b/envoy/stream_info/stream_info.h index 4091b6eeddc56..3b791bcebf4fc 100644 --- a/envoy/stream_info/stream_info.h +++ b/envoy/stream_info/stream_info.h @@ -36,67 +36,99 @@ using ClusterInfoConstSharedPtr = std::shared_ptr; namespace StreamInfo { -enum ResponseFlag { +enum CoreResponseFlag : uint16_t { // Local server healthcheck failed. - FailedLocalHealthCheck = 0x1, + FailedLocalHealthCheck, // No healthy upstream. - NoHealthyUpstream = 0x2, + NoHealthyUpstream, // Request timeout on upstream. - UpstreamRequestTimeout = 0x4, + UpstreamRequestTimeout, // Local codec level reset was sent on the stream. - LocalReset = 0x8, + LocalReset, // Remote codec level reset was received on the stream. - UpstreamRemoteReset = 0x10, + UpstreamRemoteReset, // Local reset by a connection pool due to an initial connection failure. - UpstreamConnectionFailure = 0x20, + UpstreamConnectionFailure, // If the stream was locally reset due to connection termination. - UpstreamConnectionTermination = 0x40, + UpstreamConnectionTermination, // The stream was reset because of a resource overflow. - UpstreamOverflow = 0x80, + UpstreamOverflow, // No route found for a given request. - NoRouteFound = 0x100, + NoRouteFound, // Request was delayed before proxying. - DelayInjected = 0x200, + DelayInjected, // Abort with error code was injected. - FaultInjected = 0x400, + FaultInjected, // Request was ratelimited locally by rate limit filter. - RateLimited = 0x800, + RateLimited, // Request was unauthorized by external authorization service. - UnauthorizedExternalService = 0x1000, + UnauthorizedExternalService, // Unable to call Ratelimit service. - RateLimitServiceError = 0x2000, + RateLimitServiceError, // If the stream was reset due to a downstream connection termination. - DownstreamConnectionTermination = 0x4000, + DownstreamConnectionTermination, // Exceeded upstream retry limit. - UpstreamRetryLimitExceeded = 0x8000, + UpstreamRetryLimitExceeded, // Request hit the stream idle timeout, triggering a 408. - StreamIdleTimeout = 0x10000, + StreamIdleTimeout, // Request specified x-envoy-* header values that failed strict header checks. - InvalidEnvoyRequestHeaders = 0x20000, + InvalidEnvoyRequestHeaders, // Downstream request had an HTTP protocol error - DownstreamProtocolError = 0x40000, + DownstreamProtocolError, // Upstream request reached to user defined max stream duration. - UpstreamMaxStreamDurationReached = 0x80000, + UpstreamMaxStreamDurationReached, // True if the response was served from an Envoy cache filter. - ResponseFromCacheFilter = 0x100000, + ResponseFromCacheFilter, // Filter config was not received within the permitted warming deadline. - NoFilterConfigFound = 0x200000, + NoFilterConfigFound, // Request or connection exceeded the downstream connection duration. - DurationTimeout = 0x400000, + DurationTimeout, // Upstream response had an HTTP protocol error - UpstreamProtocolError = 0x800000, + UpstreamProtocolError, // No cluster found for a given request. - NoClusterFound = 0x1000000, + NoClusterFound, // Overload Manager terminated the stream. - OverloadManager = 0x2000000, + OverloadManager, // DNS resolution failed. - DnsResolutionFailed = 0x4000000, + DnsResolutionFailed, // Drop certain percentage of overloaded traffic. - DropOverLoad = 0x8000000, + DropOverLoad, // ATTENTION: MAKE SURE THIS REMAINS EQUAL TO THE LAST FLAG. LastFlag = DropOverLoad, }; +class ResponseFlagUtils; + +class ResponseFlag { +public: + constexpr ResponseFlag() = default; + + /** + * Construct a response flag from the core response flag enum. The integer + * value of the enum is used as the raw integer value of the flag. + * @param flag the core response flag enum. + */ + constexpr ResponseFlag(CoreResponseFlag flag) : value_(flag) {} + + /** + * Get the raw integer value of the flag. + * @return uint16_t the raw integer value. + */ + uint16_t value() const { return value_; } + + bool operator==(const ResponseFlag& other) const { return value_ == other.value_; } + +private: + friend class ResponseFlagUtils; + + // This private constructor is used to create extended response flags from + // uint16_t values. This can only be used by ResponseFlagUtils to ensure + // only validated values are used. + ResponseFlag(uint16_t value) : value_(value) {} + + uint16_t value_{}; +}; + /** * Constants for the response code details field of StreamInfo for details sent * by core (non-extension) code. @@ -617,13 +649,6 @@ class StreamInfo { virtual void setConnectionTerminationDetails(absl::string_view connection_termination_details) PURE; - /** - * @param response_flags the response_flags to intersect with. - * @return true if the intersection of the response_flags argument and the currently set response - * flags is non-empty. - */ - virtual bool intersectResponseFlags(uint64_t response_flags) const PURE; - /** * @return std::string& the name of the route. The name is get from the route() and it is * empty if there is no route. @@ -766,9 +791,15 @@ class StreamInfo { virtual bool hasAnyResponseFlag() const PURE; /** - * @return response flags encoded as an integer. + * @return all response flags that are set. + */ + virtual absl::Span responseFlags() const PURE; + + /** + * @return response flags encoded as an integer. Every bit of the integer is used to represent a + * flag. Only flags that are declared in the enum CoreResponseFlag type are supported. */ - virtual uint64_t responseFlags() const PURE; + virtual uint64_t legacyResponseFlags() const PURE; /** * @return whether the request is a health check request or not. diff --git a/envoy/upstream/upstream.h b/envoy/upstream/upstream.h index 3a7c5f27a2562..220fb23148412 100644 --- a/envoy/upstream/upstream.h +++ b/envoy/upstream/upstream.h @@ -149,7 +149,9 @@ class Host : virtual public HostDescription { /* is not meant to be routed to. */ \ m(EXCLUDED_VIA_IMMEDIATE_HC_FAIL, 0x80) \ /* The host failed active HC due to timeout. */ \ - m(ACTIVE_HC_TIMEOUT, 0x100) + m(ACTIVE_HC_TIMEOUT, 0x100) \ + /* The host is currently marked as draining by EDS */ \ + m(EDS_STATUS_DRAINING, 0x200) // clang-format on #define DECLARE_ENUM(name, value) name = value, @@ -594,6 +596,7 @@ class PrioritySet { * @param locality_weights supplies a map from locality to associated weight. * @param hosts_added supplies the hosts added since the last update. * @param hosts_removed supplies the hosts removed since the last update. + * @param seed a random number to initialize the locality load-balancing algorithm. * @param weighted_priority_health if present, overwrites the current weighted_priority_health. * @param overprovisioning_factor if present, overwrites the current overprovisioning_factor. * @param cross_priority_host_map read only cross-priority host map which is created in the main @@ -602,7 +605,7 @@ class PrioritySet { virtual void updateHosts(uint32_t priority, UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, const HostVector& hosts_removed, - absl::optional weighted_priority_health, + uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor, HostMapConstSharedPtr cross_priority_host_map = nullptr) PURE; @@ -626,7 +629,7 @@ class PrioritySet { virtual void updateHosts(uint32_t priority, UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, const HostVector& hosts_removed, - absl::optional weighted_priority_health, + uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor) PURE; }; @@ -1273,6 +1276,14 @@ class ClusterInfo : public Http::FilterChainFactory { */ virtual Http::ClientHeaderValidatorPtr makeHeaderValidator(Http::Protocol protocol) const PURE; + /** + * @return absl::optional + * an optional value of the configuration for happy eyeballs for this cluster. + */ + virtual const absl::optional< + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig> + happyEyeballsConfig() const PURE; + protected: /** * Invoked by extensionProtocolOptionsTyped. diff --git a/examples/ext_authz/Dockerfile-opa b/examples/ext_authz/Dockerfile-opa index 53ddab6b56f54..5afaffa73be2b 100644 --- a/examples/ext_authz/Dockerfile-opa +++ b/examples/ext_authz/Dockerfile-opa @@ -1 +1 @@ -FROM openpolicyagent/opa:0.60.0-istio@sha256:242a2dbe29b668b524daae8446fb00518ab95a46215bbc17d8b80b2d28370841 +FROM openpolicyagent/opa:0.61.0-istio@sha256:5ee86eb43bbe8a80e24d4d218a7fd568e5e5c1a782f20aa03a5643cad307034f diff --git a/examples/ext_authz/auth/grpc-service/go.mod b/examples/ext_authz/auth/grpc-service/go.mod index 72ee6d16d88fc..02aef65f59668 100644 --- a/examples/ext_authz/auth/grpc-service/go.mod +++ b/examples/ext_authz/auth/grpc-service/go.mod @@ -5,6 +5,6 @@ go 1.14 require ( github.com/envoyproxy/go-control-plane v0.12.0 github.com/golang/protobuf v1.5.3 - google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97 - google.golang.org/grpc v1.60.1 + google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17 + google.golang.org/grpc v1.61.0 ) diff --git a/examples/ext_authz/auth/grpc-service/go.sum b/examples/ext_authz/auth/grpc-service/go.sum index 25019aec0e7c2..52de68a071178 100644 --- a/examples/ext_authz/auth/grpc-service/go.sum +++ b/examples/ext_authz/auth/grpc-service/go.sum @@ -41,16 +41,24 @@ cloud.google.com/go v0.110.4/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5x cloud.google.com/go v0.110.6/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5xsI= cloud.google.com/go v0.110.7/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5xsI= cloud.google.com/go v0.110.8/go.mod h1:Iz8AkXJf1qmxC3Oxoep8R1T36w8B92yU29PcBhHO5fk= +cloud.google.com/go v0.110.9/go.mod h1:rpxevX/0Lqvlbc88b7Sc1SPNdyK1riNBTUU6JXhYNpM= +cloud.google.com/go v0.110.10/go.mod h1:v1OoFqYxiBkUrruItNM3eT4lLByNjxmJSV/xDKJNnic= cloud.google.com/go/accessapproval v1.4.0/go.mod h1:zybIuC3KpDOvotz59lFe5qxRZx6C75OtwbisN56xYB4= cloud.google.com/go/accessapproval v1.5.0/go.mod h1:HFy3tuiGvMdcd/u+Cu5b9NkO1pEICJ46IR82PoUdplw= cloud.google.com/go/accessapproval v1.6.0/go.mod h1:R0EiYnwV5fsRFiKZkPHr6mwyk2wxUJ30nL4j2pcFY2E= cloud.google.com/go/accessapproval v1.7.1/go.mod h1:JYczztsHRMK7NTXb6Xw+dwbs/WnOJxbo/2mTI+Kgg68= +cloud.google.com/go/accessapproval v1.7.2/go.mod h1:/gShiq9/kK/h8T/eEn1BTzalDvk0mZxJlhfw0p+Xuc0= +cloud.google.com/go/accessapproval v1.7.3/go.mod h1:4l8+pwIxGTNqSf4T3ds8nLO94NQf0W/KnMNuQ9PbnP8= +cloud.google.com/go/accessapproval v1.7.4/go.mod h1:/aTEh45LzplQgFYdQdwPMR9YdX0UlhBmvB84uAmQKUc= cloud.google.com/go/accesscontextmanager v1.3.0/go.mod h1:TgCBehyr5gNMz7ZaH9xubp+CE8dkrszb4oK9CWyvD4o= cloud.google.com/go/accesscontextmanager v1.4.0/go.mod h1:/Kjh7BBu/Gh83sv+K60vN9QE5NJcd80sU33vIe2IFPE= cloud.google.com/go/accesscontextmanager v1.6.0/go.mod h1:8XCvZWfYw3K/ji0iVnp+6pu7huxoQTLmxAbVjbloTtM= cloud.google.com/go/accesscontextmanager v1.7.0/go.mod h1:CEGLewx8dwa33aDAZQujl7Dx+uYhS0eay198wB/VumQ= cloud.google.com/go/accesscontextmanager v1.8.0/go.mod h1:uI+AI/r1oyWK99NN8cQ3UK76AMelMzgZCvJfsi2c+ps= cloud.google.com/go/accesscontextmanager v1.8.1/go.mod h1:JFJHfvuaTC+++1iL1coPiG1eu5D24db2wXCDWDjIrxo= +cloud.google.com/go/accesscontextmanager v1.8.2/go.mod h1:E6/SCRM30elQJ2PKtFMs2YhfJpZSNcJyejhuzoId4Zk= +cloud.google.com/go/accesscontextmanager v1.8.3/go.mod h1:4i/JkF2JiFbhLnnpnfoTX5vRXfhf9ukhU1ANOTALTOQ= +cloud.google.com/go/accesscontextmanager v1.8.4/go.mod h1:ParU+WbMpD34s5JFEnGAnPBYAgUHozaTmDJU7aCU9+M= cloud.google.com/go/aiplatform v1.22.0/go.mod h1:ig5Nct50bZlzV6NvKaTwmplLLddFx0YReh9WfTO5jKw= cloud.google.com/go/aiplatform v1.24.0/go.mod h1:67UUvRBKG6GTayHKV8DBv2RtR1t93YRu5B1P3x99mYY= cloud.google.com/go/aiplatform v1.27.0/go.mod h1:Bvxqtl40l0WImSb04d0hXFU7gDOiq9jQmorivIiWcKg= @@ -60,6 +68,10 @@ cloud.google.com/go/aiplatform v1.37.0/go.mod h1:IU2Cv29Lv9oCn/9LkFiiuKfwrRTq+QQ cloud.google.com/go/aiplatform v1.45.0/go.mod h1:Iu2Q7sC7QGhXUeOhAj/oCK9a+ULz1O4AotZiqjQ8MYA= cloud.google.com/go/aiplatform v1.48.0/go.mod h1:Iu2Q7sC7QGhXUeOhAj/oCK9a+ULz1O4AotZiqjQ8MYA= cloud.google.com/go/aiplatform v1.50.0/go.mod h1:IRc2b8XAMTa9ZmfJV1BCCQbieWWvDnP1A8znyz5N7y4= +cloud.google.com/go/aiplatform v1.51.0/go.mod h1:IRc2b8XAMTa9ZmfJV1BCCQbieWWvDnP1A8znyz5N7y4= +cloud.google.com/go/aiplatform v1.51.1/go.mod h1:kY3nIMAVQOK2XDqDPHaOuD9e+FdMA6OOpfBjsvaFSOo= +cloud.google.com/go/aiplatform v1.51.2/go.mod h1:hCqVYB3mY45w99TmetEoe8eCQEwZEp9WHxeZdcv9phw= +cloud.google.com/go/aiplatform v1.52.0/go.mod h1:pwZMGvqe0JRkI1GWSZCtnAfrR4K1bv65IHILGA//VEU= cloud.google.com/go/analytics v0.11.0/go.mod h1:DjEWCu41bVbYcKyvlws9Er60YE4a//bK6mnhWvQeFNI= cloud.google.com/go/analytics v0.12.0/go.mod h1:gkfj9h6XRf9+TS4bmuhPEShsh3hH8PAZzm/41OOhQd4= cloud.google.com/go/analytics v0.17.0/go.mod h1:WXFa3WSym4IZ+JiKmavYdJwGG/CvpqiqczmL59bTD9M= @@ -67,18 +79,30 @@ cloud.google.com/go/analytics v0.18.0/go.mod h1:ZkeHGQlcIPkw0R/GW+boWHhCOR43xz9R cloud.google.com/go/analytics v0.19.0/go.mod h1:k8liqf5/HCnOUkbawNtrWWc+UAzyDlW89doe8TtoDsE= cloud.google.com/go/analytics v0.21.2/go.mod h1:U8dcUtmDmjrmUTnnnRnI4m6zKn/yaA5N9RlEkYFHpQo= cloud.google.com/go/analytics v0.21.3/go.mod h1:U8dcUtmDmjrmUTnnnRnI4m6zKn/yaA5N9RlEkYFHpQo= +cloud.google.com/go/analytics v0.21.4/go.mod h1:zZgNCxLCy8b2rKKVfC1YkC2vTrpfZmeRCySM3aUbskA= +cloud.google.com/go/analytics v0.21.5/go.mod h1:BQtOBHWTlJ96axpPPnw5CvGJ6i3Ve/qX2fTxR8qWyr8= +cloud.google.com/go/analytics v0.21.6/go.mod h1:eiROFQKosh4hMaNhF85Oc9WO97Cpa7RggD40e/RBy8w= cloud.google.com/go/apigateway v1.3.0/go.mod h1:89Z8Bhpmxu6AmUxuVRg/ECRGReEdiP3vQtk4Z1J9rJk= cloud.google.com/go/apigateway v1.4.0/go.mod h1:pHVY9MKGaH9PQ3pJ4YLzoj6U5FUDeDFBllIz7WmzJoc= cloud.google.com/go/apigateway v1.5.0/go.mod h1:GpnZR3Q4rR7LVu5951qfXPJCHquZt02jf7xQx7kpqN8= cloud.google.com/go/apigateway v1.6.1/go.mod h1:ufAS3wpbRjqfZrzpvLC2oh0MFlpRJm2E/ts25yyqmXA= +cloud.google.com/go/apigateway v1.6.2/go.mod h1:CwMC90nnZElorCW63P2pAYm25AtQrHfuOkbRSHj0bT8= +cloud.google.com/go/apigateway v1.6.3/go.mod h1:k68PXWpEs6BVDTtnLQAyG606Q3mz8pshItwPXjgv44Y= +cloud.google.com/go/apigateway v1.6.4/go.mod h1:0EpJlVGH5HwAN4VF4Iec8TAzGN1aQgbxAWGJsnPCGGY= cloud.google.com/go/apigeeconnect v1.3.0/go.mod h1:G/AwXFAKo0gIXkPTVfZDd2qA1TxBXJ3MgMRBQkIi9jc= cloud.google.com/go/apigeeconnect v1.4.0/go.mod h1:kV4NwOKqjvt2JYR0AoIWo2QGfoRtn/pkS3QlHp0Ni04= cloud.google.com/go/apigeeconnect v1.5.0/go.mod h1:KFaCqvBRU6idyhSNyn3vlHXc8VMDJdRmwDF6JyFRqZ8= cloud.google.com/go/apigeeconnect v1.6.1/go.mod h1:C4awq7x0JpLtrlQCr8AzVIzAaYgngRqWf9S5Uhg+wWs= +cloud.google.com/go/apigeeconnect v1.6.2/go.mod h1:s6O0CgXT9RgAxlq3DLXvG8riw8PYYbU/v25jqP3Dy18= +cloud.google.com/go/apigeeconnect v1.6.3/go.mod h1:peG0HFQ0si2bN15M6QSjEW/W7Gy3NYkWGz7pFz13cbo= +cloud.google.com/go/apigeeconnect v1.6.4/go.mod h1:CapQCWZ8TCjnU0d7PobxhpOdVz/OVJ2Hr/Zcuu1xFx0= cloud.google.com/go/apigeeregistry v0.4.0/go.mod h1:EUG4PGcsZvxOXAdyEghIdXwAEi/4MEaoqLMLDMIwKXY= cloud.google.com/go/apigeeregistry v0.5.0/go.mod h1:YR5+s0BVNZfVOUkMa5pAR2xGd0A473vA5M7j247o1wM= cloud.google.com/go/apigeeregistry v0.6.0/go.mod h1:BFNzW7yQVLZ3yj0TKcwzb8n25CFBri51GVGOEUcgQsc= cloud.google.com/go/apigeeregistry v0.7.1/go.mod h1:1XgyjZye4Mqtw7T9TsY4NW10U7BojBvG4RMD+vRDrIw= +cloud.google.com/go/apigeeregistry v0.7.2/go.mod h1:9CA2B2+TGsPKtfi3F7/1ncCCsL62NXBRfM6iPoGSM+8= +cloud.google.com/go/apigeeregistry v0.8.1/go.mod h1:MW4ig1N4JZQsXmBSwH4rwpgDonocz7FPBSw6XPGHmYw= +cloud.google.com/go/apigeeregistry v0.8.2/go.mod h1:h4v11TDGdeXJDJvImtgK2AFVvMIgGWjSb0HRnBSjcX8= cloud.google.com/go/apikeys v0.4.0/go.mod h1:XATS/yqZbaBK0HOssf+ALHp8jAlNHUgyfprvNcBIszU= cloud.google.com/go/apikeys v0.5.0/go.mod h1:5aQfwY4D+ewMMWScd3hm2en3hCj+BROlyrt3ytS7KLI= cloud.google.com/go/apikeys v0.6.0/go.mod h1:kbpXu5upyiAlGkKrJgQl8A0rKNNJ7dQ377pdroRSSi8= @@ -88,11 +112,17 @@ cloud.google.com/go/appengine v1.6.0/go.mod h1:hg6i0J/BD2cKmDJbaFSYHFyZkgBEfQrDg cloud.google.com/go/appengine v1.7.0/go.mod h1:eZqpbHFCqRGa2aCdope7eC0SWLV1j0neb/QnMJVWx6A= cloud.google.com/go/appengine v1.7.1/go.mod h1:IHLToyb/3fKutRysUlFO0BPt5j7RiQ45nrzEJmKTo6E= cloud.google.com/go/appengine v1.8.1/go.mod h1:6NJXGLVhZCN9aQ/AEDvmfzKEfoYBlfB80/BHiKVputY= +cloud.google.com/go/appengine v1.8.2/go.mod h1:WMeJV9oZ51pvclqFN2PqHoGnys7rK0rz6s3Mp6yMvDo= +cloud.google.com/go/appengine v1.8.3/go.mod h1:2oUPZ1LVZ5EXi+AF1ihNAF+S8JrzQ3till5m9VQkrsk= +cloud.google.com/go/appengine v1.8.4/go.mod h1:TZ24v+wXBujtkK77CXCpjZbnuTvsFNT41MUaZ28D6vg= cloud.google.com/go/area120 v0.5.0/go.mod h1:DE/n4mp+iqVyvxHN41Vf1CR602GiHQjFPusMFW6bGR4= cloud.google.com/go/area120 v0.6.0/go.mod h1:39yFJqWVgm0UZqWTOdqkLhjoC7uFfgXRC8g/ZegeAh0= cloud.google.com/go/area120 v0.7.0/go.mod h1:a3+8EUD1SX5RUcCs3MY5YasiO1z6yLiNLRiFrykbynY= cloud.google.com/go/area120 v0.7.1/go.mod h1:j84i4E1RboTWjKtZVWXPqvK5VHQFJRF2c1Nm69pWm9k= cloud.google.com/go/area120 v0.8.1/go.mod h1:BVfZpGpB7KFVNxPiQBuHkX6Ed0rS51xIgmGyjrAfzsg= +cloud.google.com/go/area120 v0.8.2/go.mod h1:a5qfo+x77SRLXnCynFWPUZhnZGeSgvQ+Y0v1kSItkh4= +cloud.google.com/go/area120 v0.8.3/go.mod h1:5zj6pMzVTH+SVHljdSKC35sriR/CVvQZzG/Icdyriw0= +cloud.google.com/go/area120 v0.8.4/go.mod h1:jfawXjxf29wyBXr48+W+GyX/f8fflxp642D/bb9v68M= cloud.google.com/go/artifactregistry v1.6.0/go.mod h1:IYt0oBPSAGYj/kprzsBjZ/4LnG/zOcHyFHjWPCi6SAQ= cloud.google.com/go/artifactregistry v1.7.0/go.mod h1:mqTOFOnGZx8EtSqK/ZWcsm/4U8B77rbcLP6ruDU2Ixk= cloud.google.com/go/artifactregistry v1.8.0/go.mod h1:w3GQXkJX8hiKN0v+at4b0qotwijQbYUqF2GWkZzAhC0= @@ -102,6 +132,10 @@ cloud.google.com/go/artifactregistry v1.11.2/go.mod h1:nLZns771ZGAwVLzTX/7Al6R9e cloud.google.com/go/artifactregistry v1.12.0/go.mod h1:o6P3MIvtzTOnmvGagO9v/rOjjA0HmhJ+/6KAXrmYDCI= cloud.google.com/go/artifactregistry v1.13.0/go.mod h1:uy/LNfoOIivepGhooAUpL1i30Hgee3Cu0l4VTWHUC08= cloud.google.com/go/artifactregistry v1.14.1/go.mod h1:nxVdG19jTaSTu7yA7+VbWL346r3rIdkZ142BSQqhn5E= +cloud.google.com/go/artifactregistry v1.14.2/go.mod h1:Xk+QbsKEb0ElmyeMfdHAey41B+qBq3q5R5f5xD4XT3U= +cloud.google.com/go/artifactregistry v1.14.3/go.mod h1:A2/E9GXnsyXl7GUvQ/2CjHA+mVRoWAXC0brg2os+kNI= +cloud.google.com/go/artifactregistry v1.14.4/go.mod h1:SJJcZTMv6ce0LDMUnihCN7WSrI+kBSFV0KIKo8S8aYU= +cloud.google.com/go/artifactregistry v1.14.6/go.mod h1:np9LSFotNWHcjnOgh8UVK0RFPCTUGbO0ve3384xyHfE= cloud.google.com/go/asset v1.5.0/go.mod h1:5mfs8UvcM5wHhqtSv8J1CtxxaQq3AdBxxQi2jGW/K4o= cloud.google.com/go/asset v1.7.0/go.mod h1:YbENsRK4+xTiL+Ofoj5Ckf+O17kJtgp3Y3nn4uzZz5s= cloud.google.com/go/asset v1.8.0/go.mod h1:mUNGKhiqIdbr8X7KNayoYvyc4HbbFO9URsjbytpUaW0= @@ -111,6 +145,10 @@ cloud.google.com/go/asset v1.11.1/go.mod h1:fSwLhbRvC9p9CXQHJ3BgFeQNM4c9x10lqlrd cloud.google.com/go/asset v1.12.0/go.mod h1:h9/sFOa4eDIyKmH6QMpm4eUK3pDojWnUhTgJlk762Hg= cloud.google.com/go/asset v1.13.0/go.mod h1:WQAMyYek/b7NBpYq/K4KJWcRqzoalEsxz/t/dTk4THw= cloud.google.com/go/asset v1.14.1/go.mod h1:4bEJ3dnHCqWCDbWJ/6Vn7GVI9LerSi7Rfdi03hd+WTQ= +cloud.google.com/go/asset v1.15.0/go.mod h1:tpKafV6mEut3+vN9ScGvCHXHj7FALFVta+okxFECHcg= +cloud.google.com/go/asset v1.15.1/go.mod h1:yX/amTvFWRpp5rcFq6XbCxzKT8RJUam1UoboE179jU4= +cloud.google.com/go/asset v1.15.2/go.mod h1:B6H5tclkXvXz7PD22qCA2TDxSVQfasa3iDlM89O2NXs= +cloud.google.com/go/asset v1.15.3/go.mod h1:yYLfUD4wL4X589A9tYrv4rFrba0QlDeag0CMcM5ggXU= cloud.google.com/go/assuredworkloads v1.5.0/go.mod h1:n8HOZ6pff6re5KYfBXcFvSViQjDwxFkAkmUFffJRbbY= cloud.google.com/go/assuredworkloads v1.6.0/go.mod h1:yo2YOk37Yc89Rsd5QMVECvjaMKymF9OP+QXWlKXUkXw= cloud.google.com/go/assuredworkloads v1.7.0/go.mod h1:z/736/oNmtGAyU47reJgGN+KVoYoxeLBoj4XkKYscNI= @@ -118,28 +156,44 @@ cloud.google.com/go/assuredworkloads v1.8.0/go.mod h1:AsX2cqyNCOvEQC8RMPnoc0yEar cloud.google.com/go/assuredworkloads v1.9.0/go.mod h1:kFuI1P78bplYtT77Tb1hi0FMxM0vVpRC7VVoJC3ZoT0= cloud.google.com/go/assuredworkloads v1.10.0/go.mod h1:kwdUQuXcedVdsIaKgKTp9t0UJkE5+PAVNhdQm4ZVq2E= cloud.google.com/go/assuredworkloads v1.11.1/go.mod h1:+F04I52Pgn5nmPG36CWFtxmav6+7Q+c5QyJoL18Lry0= +cloud.google.com/go/assuredworkloads v1.11.2/go.mod h1:O1dfr+oZJMlE6mw0Bp0P1KZSlj5SghMBvTpZqIcUAW4= +cloud.google.com/go/assuredworkloads v1.11.3/go.mod h1:vEjfTKYyRUaIeA0bsGJceFV2JKpVRgyG2op3jfa59Zs= +cloud.google.com/go/assuredworkloads v1.11.4/go.mod h1:4pwwGNwy1RP0m+y12ef3Q/8PaiWrIDQ6nD2E8kvWI9U= cloud.google.com/go/automl v1.5.0/go.mod h1:34EjfoFGMZ5sgJ9EoLsRtdPSNZLcfflJR39VbVNS2M0= cloud.google.com/go/automl v1.6.0/go.mod h1:ugf8a6Fx+zP0D59WLhqgTDsQI9w07o64uf/Is3Nh5p8= cloud.google.com/go/automl v1.7.0/go.mod h1:RL9MYCCsJEOmt0Wf3z9uzG0a7adTT1fe+aObgSpkCt8= cloud.google.com/go/automl v1.8.0/go.mod h1:xWx7G/aPEe/NP+qzYXktoBSDfjO+vnKMGgsApGJJquM= cloud.google.com/go/automl v1.12.0/go.mod h1:tWDcHDp86aMIuHmyvjuKeeHEGq76lD7ZqfGLN6B0NuU= cloud.google.com/go/automl v1.13.1/go.mod h1:1aowgAHWYZU27MybSCFiukPO7xnyawv7pt3zK4bheQE= +cloud.google.com/go/automl v1.13.2/go.mod h1:gNY/fUmDEN40sP8amAX3MaXkxcqPIn7F1UIIPZpy4Mg= +cloud.google.com/go/automl v1.13.3/go.mod h1:Y8KwvyAZFOsMAPqUCfNu1AyclbC6ivCUF/MTwORymyY= +cloud.google.com/go/automl v1.13.4/go.mod h1:ULqwX/OLZ4hBVfKQaMtxMSTlPx0GqGbWN8uA/1EqCP8= cloud.google.com/go/baremetalsolution v0.3.0/go.mod h1:XOrocE+pvK1xFfleEnShBlNAXf+j5blPPxrhjKgnIFc= cloud.google.com/go/baremetalsolution v0.4.0/go.mod h1:BymplhAadOO/eBa7KewQ0Ppg4A4Wplbn+PsFKRLo0uI= cloud.google.com/go/baremetalsolution v0.5.0/go.mod h1:dXGxEkmR9BMwxhzBhV0AioD0ULBmuLZI8CdwalUxuss= cloud.google.com/go/baremetalsolution v1.1.1/go.mod h1:D1AV6xwOksJMV4OSlWHtWuFNZZYujJknMAP4Qa27QIA= cloud.google.com/go/baremetalsolution v1.2.0/go.mod h1:68wi9AwPYkEWIUT4SvSGS9UJwKzNpshjHsH4lzk8iOw= +cloud.google.com/go/baremetalsolution v1.2.1/go.mod h1:3qKpKIw12RPXStwQXcbhfxVj1dqQGEvcmA+SX/mUR88= +cloud.google.com/go/baremetalsolution v1.2.2/go.mod h1:O5V6Uu1vzVelYahKfwEWRMaS3AbCkeYHy3145s1FkhM= +cloud.google.com/go/baremetalsolution v1.2.3/go.mod h1:/UAQ5xG3faDdy180rCUv47e0jvpp3BFxT+Cl0PFjw5g= cloud.google.com/go/batch v0.3.0/go.mod h1:TR18ZoAekj1GuirsUsR1ZTKN3FC/4UDnScjT8NXImFE= cloud.google.com/go/batch v0.4.0/go.mod h1:WZkHnP43R/QCGQsZ+0JyG4i79ranE2u8xvjq/9+STPE= cloud.google.com/go/batch v0.7.0/go.mod h1:vLZN95s6teRUqRQ4s3RLDsH8PvboqBK+rn1oevL159g= cloud.google.com/go/batch v1.3.1/go.mod h1:VguXeQKXIYaeeIYbuozUmBR13AfL4SJP7IltNPS+A4A= cloud.google.com/go/batch v1.4.1/go.mod h1:KdBmDD61K0ovcxoRHGrN6GmOBWeAOyCgKD0Mugx4Fkk= +cloud.google.com/go/batch v1.5.0/go.mod h1:KdBmDD61K0ovcxoRHGrN6GmOBWeAOyCgKD0Mugx4Fkk= +cloud.google.com/go/batch v1.5.1/go.mod h1:RpBuIYLkQu8+CWDk3dFD/t/jOCGuUpkpX+Y0n1Xccs8= +cloud.google.com/go/batch v1.6.1/go.mod h1:urdpD13zPe6YOK+6iZs/8/x2VBRofvblLpx0t57vM98= +cloud.google.com/go/batch v1.6.3/go.mod h1:J64gD4vsNSA2O5TtDB5AAux3nJ9iV8U3ilg3JDBYejU= cloud.google.com/go/beyondcorp v0.2.0/go.mod h1:TB7Bd+EEtcw9PCPQhCJtJGjk/7TC6ckmnSFS+xwTfm4= cloud.google.com/go/beyondcorp v0.3.0/go.mod h1:E5U5lcrcXMsCuoDNyGrpyTm/hn7ne941Jz2vmksAxW8= cloud.google.com/go/beyondcorp v0.4.0/go.mod h1:3ApA0mbhHx6YImmuubf5pyW8srKnCEPON32/5hj+RmM= cloud.google.com/go/beyondcorp v0.5.0/go.mod h1:uFqj9X+dSfrheVp7ssLTaRHd2EHqSL4QZmH4e8WXGGU= cloud.google.com/go/beyondcorp v0.6.1/go.mod h1:YhxDWw946SCbmcWo3fAhw3V4XZMSpQ/VYfcKGAEU8/4= cloud.google.com/go/beyondcorp v1.0.0/go.mod h1:YhxDWw946SCbmcWo3fAhw3V4XZMSpQ/VYfcKGAEU8/4= +cloud.google.com/go/beyondcorp v1.0.1/go.mod h1:zl/rWWAFVeV+kx+X2Javly7o1EIQThU4WlkynffL/lk= +cloud.google.com/go/beyondcorp v1.0.2/go.mod h1:m8cpG7caD+5su+1eZr+TSvF6r21NdLJk4f9u4SP2Ntc= +cloud.google.com/go/beyondcorp v1.0.3/go.mod h1:HcBvnEd7eYr+HGDd5ZbuVmBYX019C6CEXBonXbCVwJo= cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o= cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE= cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= @@ -156,6 +210,8 @@ cloud.google.com/go/bigquery v1.50.0/go.mod h1:YrleYEh2pSEbgTBZYMJ5SuSr0ML3ypjRB cloud.google.com/go/bigquery v1.52.0/go.mod h1:3b/iXjRQGU4nKa87cXeg6/gogLjO8C6PmuM8i5Bi/u4= cloud.google.com/go/bigquery v1.53.0/go.mod h1:3b/iXjRQGU4nKa87cXeg6/gogLjO8C6PmuM8i5Bi/u4= cloud.google.com/go/bigquery v1.55.0/go.mod h1:9Y5I3PN9kQWuid6183JFhOGOW3GcirA5LpsKCUn+2ec= +cloud.google.com/go/bigquery v1.56.0/go.mod h1:KDcsploXTEY7XT3fDQzMUZlpQLHzE4itubHrnmhUrZA= +cloud.google.com/go/bigquery v1.57.1/go.mod h1:iYzC0tGVWt1jqSzBHqCr3lrRn0u13E8e+AqowBsDgug= cloud.google.com/go/billing v1.4.0/go.mod h1:g9IdKBEFlItS8bTtlrZdVLWSSdSyFUZKXNS02zKMOZY= cloud.google.com/go/billing v1.5.0/go.mod h1:mztb1tBc3QekhjSgmpf/CV4LzWXLzCArwpLmP2Gm88s= cloud.google.com/go/billing v1.6.0/go.mod h1:WoXzguj+BeHXPbKfNWkqVtDdzORazmCjraY+vrxcyvI= @@ -164,6 +220,10 @@ cloud.google.com/go/billing v1.12.0/go.mod h1:yKrZio/eu+okO/2McZEbch17O5CB5NpZhh cloud.google.com/go/billing v1.13.0/go.mod h1:7kB2W9Xf98hP9Sr12KfECgfGclsH3CQR0R08tnRlRbc= cloud.google.com/go/billing v1.16.0/go.mod h1:y8vx09JSSJG02k5QxbycNRrN7FGZB6F3CAcgum7jvGA= cloud.google.com/go/billing v1.17.0/go.mod h1:Z9+vZXEq+HwH7bhJkyI4OQcR6TSbeMrjlpEjO2vzY64= +cloud.google.com/go/billing v1.17.1/go.mod h1:Z9+vZXEq+HwH7bhJkyI4OQcR6TSbeMrjlpEjO2vzY64= +cloud.google.com/go/billing v1.17.2/go.mod h1:u/AdV/3wr3xoRBk5xvUzYMS1IawOAPwQMuHgHMdljDg= +cloud.google.com/go/billing v1.17.3/go.mod h1:z83AkoZ7mZwBGT3yTnt6rSGI1OOsHSIi6a5M3mJ8NaU= +cloud.google.com/go/billing v1.17.4/go.mod h1:5DOYQStCxquGprqfuid/7haD7th74kyMBHkjO/OvDtk= cloud.google.com/go/binaryauthorization v1.1.0/go.mod h1:xwnoWu3Y84jbuHa0zd526MJYmtnVXn0syOjaJgy4+dM= cloud.google.com/go/binaryauthorization v1.2.0/go.mod h1:86WKkJHtRcv5ViNABtYMhhNWRrD1Vpi//uKEy7aYEfI= cloud.google.com/go/binaryauthorization v1.3.0/go.mod h1:lRZbKgjDIIQvzYQS1p99A7/U1JqvqeZg0wiI5tp6tg0= @@ -171,16 +231,25 @@ cloud.google.com/go/binaryauthorization v1.4.0/go.mod h1:tsSPQrBd77VLplV70GUhBf/ cloud.google.com/go/binaryauthorization v1.5.0/go.mod h1:OSe4OU1nN/VswXKRBmciKpo9LulY41gch5c68htf3/Q= cloud.google.com/go/binaryauthorization v1.6.1/go.mod h1:TKt4pa8xhowwffiBmbrbcxijJRZED4zrqnwZ1lKH51U= cloud.google.com/go/binaryauthorization v1.7.0/go.mod h1:Zn+S6QqTMn6odcMU1zDZCJxPjU2tZPV1oDl45lWY154= +cloud.google.com/go/binaryauthorization v1.7.1/go.mod h1:GTAyfRWYgcbsP3NJogpV3yeunbUIjx2T9xVeYovtURE= +cloud.google.com/go/binaryauthorization v1.7.2/go.mod h1:kFK5fQtxEp97m92ziy+hbu+uKocka1qRRL8MVJIgjv0= +cloud.google.com/go/binaryauthorization v1.7.3/go.mod h1:VQ/nUGRKhrStlGr+8GMS8f6/vznYLkdK5vaKfdCIpvU= cloud.google.com/go/certificatemanager v1.3.0/go.mod h1:n6twGDvcUBFu9uBgt4eYvvf3sQ6My8jADcOVwHmzadg= cloud.google.com/go/certificatemanager v1.4.0/go.mod h1:vowpercVFyqs8ABSmrdV+GiFf2H/ch3KyudYQEMM590= cloud.google.com/go/certificatemanager v1.6.0/go.mod h1:3Hh64rCKjRAX8dXgRAyOcY5vQ/fE1sh8o+Mdd6KPgY8= cloud.google.com/go/certificatemanager v1.7.1/go.mod h1:iW8J3nG6SaRYImIa+wXQ0g8IgoofDFRp5UMzaNk1UqI= +cloud.google.com/go/certificatemanager v1.7.2/go.mod h1:15SYTDQMd00kdoW0+XY5d9e+JbOPjp24AvF48D8BbcQ= +cloud.google.com/go/certificatemanager v1.7.3/go.mod h1:T/sZYuC30PTag0TLo28VedIRIj1KPGcOQzjWAptHa00= +cloud.google.com/go/certificatemanager v1.7.4/go.mod h1:FHAylPe/6IIKuaRmHbjbdLhGhVQ+CWHSD5Jq0k4+cCE= cloud.google.com/go/channel v1.8.0/go.mod h1:W5SwCXDJsq/rg3tn3oG0LOxpAo6IMxNa09ngphpSlnk= cloud.google.com/go/channel v1.9.0/go.mod h1:jcu05W0my9Vx4mt3/rEHpfxc9eKi9XwsdDL8yBMbKUk= cloud.google.com/go/channel v1.11.0/go.mod h1:IdtI0uWGqhEeatSB62VOoJ8FSUhJ9/+iGkJVqp74CGE= cloud.google.com/go/channel v1.12.0/go.mod h1:VkxCGKASi4Cq7TbXxlaBezonAYpp1GCnKMY6tnMQnLU= cloud.google.com/go/channel v1.16.0/go.mod h1:eN/q1PFSl5gyu0dYdmxNXscY/4Fi7ABmeHCJNf/oHmc= cloud.google.com/go/channel v1.17.0/go.mod h1:RpbhJsGi/lXWAUM1eF4IbQGbsfVlg2o8Iiy2/YLfVT0= +cloud.google.com/go/channel v1.17.1/go.mod h1:xqfzcOZAcP4b/hUDH0GkGg1Sd5to6di1HOJn/pi5uBQ= +cloud.google.com/go/channel v1.17.2/go.mod h1:aT2LhnftnyfQceFql5I/mP8mIbiiJS4lWqgXA815zMk= +cloud.google.com/go/channel v1.17.3/go.mod h1:QcEBuZLGGrUMm7kNj9IbU1ZfmJq2apotsV83hbxX7eE= cloud.google.com/go/cloudbuild v1.3.0/go.mod h1:WequR4ULxlqvMsjDEEEFnOG5ZSRSgWOywXYDb1vPE6U= cloud.google.com/go/cloudbuild v1.4.0/go.mod h1:5Qwa40LHiOXmz3386FrjrYM93rM/hdRr7b53sySrTqA= cloud.google.com/go/cloudbuild v1.6.0/go.mod h1:UIbc/w9QCbH12xX+ezUsgblrWv+Cv4Tw83GiSMHOn9M= @@ -189,11 +258,17 @@ cloud.google.com/go/cloudbuild v1.9.0/go.mod h1:qK1d7s4QlO0VwfYn5YuClDGg2hfmLZEb cloud.google.com/go/cloudbuild v1.10.1/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= cloud.google.com/go/cloudbuild v1.13.0/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= cloud.google.com/go/cloudbuild v1.14.0/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= +cloud.google.com/go/cloudbuild v1.14.1/go.mod h1:K7wGc/3zfvmYWOWwYTgF/d/UVJhS4pu+HAy7PL7mCsU= +cloud.google.com/go/cloudbuild v1.14.2/go.mod h1:Bn6RO0mBYk8Vlrt+8NLrru7WXlQ9/RDWz2uo5KG1/sg= +cloud.google.com/go/cloudbuild v1.14.3/go.mod h1:eIXYWmRt3UtggLnFGx4JvXcMj4kShhVzGndL1LwleEM= cloud.google.com/go/clouddms v1.3.0/go.mod h1:oK6XsCDdW4Ib3jCCBugx+gVjevp2TMXFtgxvPSee3OM= cloud.google.com/go/clouddms v1.4.0/go.mod h1:Eh7sUGCC+aKry14O1NRljhjyrr0NFC0G2cjwX0cByRk= cloud.google.com/go/clouddms v1.5.0/go.mod h1:QSxQnhikCLUw13iAbffF2CZxAER3xDGNHjsTAkQJcQA= cloud.google.com/go/clouddms v1.6.1/go.mod h1:Ygo1vL52Ov4TBZQquhz5fiw2CQ58gvu+PlS6PVXCpZI= cloud.google.com/go/clouddms v1.7.0/go.mod h1:MW1dC6SOtI/tPNCciTsXtsGNEM0i0OccykPvv3hiYeM= +cloud.google.com/go/clouddms v1.7.1/go.mod h1:o4SR8U95+P7gZ/TX+YbJxehOCsM+fe6/brlrFquiszk= +cloud.google.com/go/clouddms v1.7.2/go.mod h1:Rk32TmWmHo64XqDvW7jgkFQet1tUKNVzs7oajtJT3jU= +cloud.google.com/go/clouddms v1.7.3/go.mod h1:fkN2HQQNUYInAU3NQ3vRLkV2iWs8lIdmBKOx4nrL6Hc= cloud.google.com/go/cloudtasks v1.5.0/go.mod h1:fD92REy1x5woxkKEkLdvavGnPJGEn8Uic9nWuLzqCpY= cloud.google.com/go/cloudtasks v1.6.0/go.mod h1:C6Io+sxuke9/KNRkbQpihnW93SWDU3uXt92nu85HkYI= cloud.google.com/go/cloudtasks v1.7.0/go.mod h1:ImsfdYWwlWNJbdgPIIGJWC+gemEGTBK/SunNQQNCAb4= @@ -202,6 +277,9 @@ cloud.google.com/go/cloudtasks v1.9.0/go.mod h1:w+EyLsVkLWHcOaqNEyvcKAsWp9p29dL6 cloud.google.com/go/cloudtasks v1.10.0/go.mod h1:NDSoTLkZ3+vExFEWu2UJV1arUyzVDAiZtdWcsUyNwBs= cloud.google.com/go/cloudtasks v1.11.1/go.mod h1:a9udmnou9KO2iulGscKR0qBYjreuX8oHwpmFsKspEvM= cloud.google.com/go/cloudtasks v1.12.1/go.mod h1:a9udmnou9KO2iulGscKR0qBYjreuX8oHwpmFsKspEvM= +cloud.google.com/go/cloudtasks v1.12.2/go.mod h1:A7nYkjNlW2gUoROg1kvJrQGhJP/38UaWwsnuBDOBVUk= +cloud.google.com/go/cloudtasks v1.12.3/go.mod h1:GPVXhIOSGEaR+3xT4Fp72ScI+HjHffSS4B8+BaBB5Ys= +cloud.google.com/go/cloudtasks v1.12.4/go.mod h1:BEPu0Gtt2dU6FxZHNqqNdGqIG86qyWKBPGnsb7udGY0= cloud.google.com/go/compute v0.1.0/go.mod h1:GAesmwr110a34z04OlxYkATPBEfVhkymfTBXtfbBFow= cloud.google.com/go/compute v1.3.0/go.mod h1:cCZiE1NHEtai4wiufUhW8I8S1JKkAnhnQJWM7YD99wM= cloud.google.com/go/compute v1.5.0/go.mod h1:9SMHyhJlzhlkJqrPAc839t2BZFTSk6Jdj6mkzQJeu0M= @@ -221,6 +299,9 @@ cloud.google.com/go/compute v1.19.3/go.mod h1:qxvISKp/gYnXkSAD1ppcSOveRAmzxicEv/ cloud.google.com/go/compute v1.20.1/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= cloud.google.com/go/compute v1.21.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= cloud.google.com/go/compute v1.23.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= +cloud.google.com/go/compute v1.23.1/go.mod h1:CqB3xpmPKKt3OJpW2ndFIXnA9A4xAy/F3Xp1ixncW78= +cloud.google.com/go/compute v1.23.2/go.mod h1:JJ0atRC0J/oWYiiVBmsSsrRnh92DhZPG4hFDcR04Rns= +cloud.google.com/go/compute v1.23.3/go.mod h1:VCgBUoMnIVIR0CscqQiPJLAG25E3ZRZMzcFZeQ+h8CI= cloud.google.com/go/compute/metadata v0.1.0/go.mod h1:Z1VN+bulIf6bt4P/C37K4DyZYZEXYonfTBHHFPO/4UU= cloud.google.com/go/compute/metadata v0.2.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/compute/metadata v0.2.1/go.mod h1:jgHgmJd2RKBGzXqF5LR2EZMGxBkeanZ9wwa75XHJgOM= @@ -230,6 +311,10 @@ cloud.google.com/go/contactcenterinsights v1.4.0/go.mod h1:L2YzkGbPsv+vMQMCADxJo cloud.google.com/go/contactcenterinsights v1.6.0/go.mod h1:IIDlT6CLcDoyv79kDv8iWxMSTZhLxSCofVV5W6YFM/w= cloud.google.com/go/contactcenterinsights v1.9.1/go.mod h1:bsg/R7zGLYMVxFFzfh9ooLTruLRCG9fnzhH9KznHhbM= cloud.google.com/go/contactcenterinsights v1.10.0/go.mod h1:bsg/R7zGLYMVxFFzfh9ooLTruLRCG9fnzhH9KznHhbM= +cloud.google.com/go/contactcenterinsights v1.11.0/go.mod h1:hutBdImE4XNZ1NV4vbPJKSFOnQruhC5Lj9bZqWMTKiU= +cloud.google.com/go/contactcenterinsights v1.11.1/go.mod h1:FeNP3Kg8iteKM80lMwSk3zZZKVxr+PGnAId6soKuXwE= +cloud.google.com/go/contactcenterinsights v1.11.2/go.mod h1:A9PIR5ov5cRcd28KlDbmmXE8Aay+Gccer2h4wzkYFso= +cloud.google.com/go/contactcenterinsights v1.11.3/go.mod h1:HHX5wrz5LHVAwfI2smIotQG9x8Qd6gYilaHcLLLmNis= cloud.google.com/go/container v1.6.0/go.mod h1:Xazp7GjJSeUYo688S+6J5V+n/t+G5sKBTFkKNudGRxg= cloud.google.com/go/container v1.7.0/go.mod h1:Dp5AHtmothHGX3DwwIHPgq45Y8KmNsgN3amoYfxVkLo= cloud.google.com/go/container v1.13.1/go.mod h1:6wgbMPeQRw9rSnKBCAJXnds3Pzj03C4JHamr8asWKy4= @@ -238,12 +323,18 @@ cloud.google.com/go/container v1.15.0/go.mod h1:ft+9S0WGjAyjDggg5S06DXj+fHJICWg8 cloud.google.com/go/container v1.22.1/go.mod h1:lTNExE2R7f+DLbAN+rJiKTisauFCaoDq6NURZ83eVH4= cloud.google.com/go/container v1.24.0/go.mod h1:lTNExE2R7f+DLbAN+rJiKTisauFCaoDq6NURZ83eVH4= cloud.google.com/go/container v1.26.0/go.mod h1:YJCmRet6+6jnYYRS000T6k0D0xUXQgBSaJ7VwI8FBj4= +cloud.google.com/go/container v1.26.1/go.mod h1:5smONjPRUxeEpDG7bMKWfDL4sauswqEtnBK1/KKpR04= +cloud.google.com/go/container v1.26.2/go.mod h1:YlO84xCt5xupVbLaMY4s3XNE79MUJ+49VmkInr6HvF4= +cloud.google.com/go/container v1.27.1/go.mod h1:b1A1gJeTBXVLQ6GGw9/9M4FG94BEGsqJ5+t4d/3N7O4= cloud.google.com/go/containeranalysis v0.5.1/go.mod h1:1D92jd8gRR/c0fGMlymRgxWD3Qw9C1ff6/T7mLgVL8I= cloud.google.com/go/containeranalysis v0.6.0/go.mod h1:HEJoiEIu+lEXM+k7+qLCci0h33lX3ZqoYFdmPcoO7s4= cloud.google.com/go/containeranalysis v0.7.0/go.mod h1:9aUL+/vZ55P2CXfuZjS4UjQ9AgXoSw8Ts6lemfmxBxI= cloud.google.com/go/containeranalysis v0.9.0/go.mod h1:orbOANbwk5Ejoom+s+DUCTTJ7IBdBQJDcSylAx/on9s= cloud.google.com/go/containeranalysis v0.10.1/go.mod h1:Ya2jiILITMY68ZLPaogjmOMNkwsDrWBSTyBubGXO7j0= cloud.google.com/go/containeranalysis v0.11.0/go.mod h1:4n2e99ZwpGxpNcz+YsFT1dfOHPQFGcAC8FN2M2/ne/U= +cloud.google.com/go/containeranalysis v0.11.1/go.mod h1:rYlUOM7nem1OJMKwE1SadufX0JP3wnXj844EtZAwWLY= +cloud.google.com/go/containeranalysis v0.11.2/go.mod h1:xibioGBC1MD2j4reTyV1xY1/MvKaz+fyM9ENWhmIeP8= +cloud.google.com/go/containeranalysis v0.11.3/go.mod h1:kMeST7yWFQMGjiG9K7Eov+fPNQcGhb8mXj/UcTiWw9U= cloud.google.com/go/datacatalog v1.3.0/go.mod h1:g9svFY6tuR+j+hrTw3J2dNcmI0dzmSiyOzm8kpLq0a0= cloud.google.com/go/datacatalog v1.5.0/go.mod h1:M7GPLNQeLfWqeIm3iuiruhPzkt65+Bx8dAKvScX8jvs= cloud.google.com/go/datacatalog v1.6.0/go.mod h1:+aEyF8JKg+uXcIdAmmaMUmZ3q1b/lKLtXCmXdnc0lbc= @@ -256,24 +347,40 @@ cloud.google.com/go/datacatalog v1.14.0/go.mod h1:h0PrGtlihoutNMp/uvwhawLQ9+c63K cloud.google.com/go/datacatalog v1.14.1/go.mod h1:d2CevwTG4yedZilwe+v3E3ZBDRMobQfSG/a6cCCN5R4= cloud.google.com/go/datacatalog v1.16.0/go.mod h1:d2CevwTG4yedZilwe+v3E3ZBDRMobQfSG/a6cCCN5R4= cloud.google.com/go/datacatalog v1.17.1/go.mod h1:nCSYFHgtxh2MiEktWIz71s/X+7ds/UT9kp0PC7waCzE= +cloud.google.com/go/datacatalog v1.18.0/go.mod h1:nCSYFHgtxh2MiEktWIz71s/X+7ds/UT9kp0PC7waCzE= +cloud.google.com/go/datacatalog v1.18.1/go.mod h1:TzAWaz+ON1tkNr4MOcak8EBHX7wIRX/gZKM+yTVsv+A= +cloud.google.com/go/datacatalog v1.18.2/go.mod h1:SPVgWW2WEMuWHA+fHodYjmxPiMqcOiWfhc9OD5msigk= +cloud.google.com/go/datacatalog v1.18.3/go.mod h1:5FR6ZIF8RZrtml0VUao22FxhdjkoG+a0866rEnObryM= cloud.google.com/go/dataflow v0.6.0/go.mod h1:9QwV89cGoxjjSR9/r7eFDqqjtvbKxAK2BaYU6PVk9UM= cloud.google.com/go/dataflow v0.7.0/go.mod h1:PX526vb4ijFMesO1o202EaUmouZKBpjHsTlCtB4parQ= cloud.google.com/go/dataflow v0.8.0/go.mod h1:Rcf5YgTKPtQyYz8bLYhFoIV/vP39eL7fWNcSOyFfLJE= cloud.google.com/go/dataflow v0.9.1/go.mod h1:Wp7s32QjYuQDWqJPFFlnBKhkAtiFpMTdg00qGbnIHVw= +cloud.google.com/go/dataflow v0.9.2/go.mod h1:vBfdBZ/ejlTaYIGB3zB4T08UshH70vbtZeMD+urnUSo= +cloud.google.com/go/dataflow v0.9.3/go.mod h1:HI4kMVjcHGTs3jTHW/kv3501YW+eloiJSLxkJa/vqFE= +cloud.google.com/go/dataflow v0.9.4/go.mod h1:4G8vAkHYCSzU8b/kmsoR2lWyHJD85oMJPHMtan40K8w= cloud.google.com/go/dataform v0.3.0/go.mod h1:cj8uNliRlHpa6L3yVhDOBrUXH+BPAO1+KFMQQNSThKo= cloud.google.com/go/dataform v0.4.0/go.mod h1:fwV6Y4Ty2yIFL89huYlEkwUPtS7YZinZbzzj5S9FzCE= cloud.google.com/go/dataform v0.5.0/go.mod h1:GFUYRe8IBa2hcomWplodVmUx/iTL0FrsauObOM3Ipr0= cloud.google.com/go/dataform v0.6.0/go.mod h1:QPflImQy33e29VuapFdf19oPbE4aYTJxr31OAPV+ulA= cloud.google.com/go/dataform v0.7.0/go.mod h1:7NulqnVozfHvWUBpMDfKMUESr+85aJsC/2O0o3jWPDE= cloud.google.com/go/dataform v0.8.1/go.mod h1:3BhPSiw8xmppbgzeBbmDvmSWlwouuJkXsXsb8UBih9M= +cloud.google.com/go/dataform v0.8.2/go.mod h1:X9RIqDs6NbGPLR80tnYoPNiO1w0wenKTb8PxxlhTMKM= +cloud.google.com/go/dataform v0.8.3/go.mod h1:8nI/tvv5Fso0drO3pEjtowz58lodx8MVkdV2q0aPlqg= +cloud.google.com/go/dataform v0.9.1/go.mod h1:pWTg+zGQ7i16pyn0bS1ruqIE91SdL2FDMvEYu/8oQxs= cloud.google.com/go/datafusion v1.4.0/go.mod h1:1Zb6VN+W6ALo85cXnM1IKiPw+yQMKMhB9TsTSRDo/38= cloud.google.com/go/datafusion v1.5.0/go.mod h1:Kz+l1FGHB0J+4XF2fud96WMmRiq/wj8N9u007vyXZ2w= cloud.google.com/go/datafusion v1.6.0/go.mod h1:WBsMF8F1RhSXvVM8rCV3AeyWVxcC2xY6vith3iw3S+8= cloud.google.com/go/datafusion v1.7.1/go.mod h1:KpoTBbFmoToDExJUso/fcCiguGDk7MEzOWXUsJo0wsI= +cloud.google.com/go/datafusion v1.7.2/go.mod h1:62K2NEC6DRlpNmI43WHMWf9Vg/YvN6QVi8EVwifElI0= +cloud.google.com/go/datafusion v1.7.3/go.mod h1:eoLt1uFXKGBq48jy9LZ+Is8EAVLnmn50lNncLzwYokE= +cloud.google.com/go/datafusion v1.7.4/go.mod h1:BBs78WTOLYkT4GVZIXQCZT3GFpkpDN4aBY4NDX/jVlM= cloud.google.com/go/datalabeling v0.5.0/go.mod h1:TGcJ0G2NzcsXSE/97yWjIZO0bXj0KbVlINXMG9ud42I= cloud.google.com/go/datalabeling v0.6.0/go.mod h1:WqdISuk/+WIGeMkpw/1q7bK/tFEZxsrFJOJdY2bXvTQ= cloud.google.com/go/datalabeling v0.7.0/go.mod h1:WPQb1y08RJbmpM3ww0CSUAGweL0SxByuW2E+FU+wXcM= cloud.google.com/go/datalabeling v0.8.1/go.mod h1:XS62LBSVPbYR54GfYQsPXZjTW8UxCK2fkDciSrpRFdY= +cloud.google.com/go/datalabeling v0.8.2/go.mod h1:cyDvGHuJWu9U/cLDA7d8sb9a0tWLEletStu2sTmg3BE= +cloud.google.com/go/datalabeling v0.8.3/go.mod h1:tvPhpGyS/V7lqjmb3V0TaDdGvhzgR1JoW7G2bpi2UTI= +cloud.google.com/go/datalabeling v0.8.4/go.mod h1:Z1z3E6LHtffBGrNUkKwbwbDxTiXEApLzIgmymj8A3S8= cloud.google.com/go/dataplex v1.3.0/go.mod h1:hQuRtDg+fCiFgC8j0zV222HvzFQdRd+SVX8gdmFcZzA= cloud.google.com/go/dataplex v1.4.0/go.mod h1:X51GfLXEMVJ6UN47ESVqvlsRplbLhcsAt0kZCCKsU0A= cloud.google.com/go/dataplex v1.5.2/go.mod h1:cVMgQHsmfRoI5KFYq4JtIBEUbYwc3c7tXmIDhRmNNVQ= @@ -281,15 +388,24 @@ cloud.google.com/go/dataplex v1.6.0/go.mod h1:bMsomC/aEJOSpHXdFKFGQ1b0TDPIeL28nJ cloud.google.com/go/dataplex v1.8.1/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= cloud.google.com/go/dataplex v1.9.0/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= cloud.google.com/go/dataplex v1.9.1/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= +cloud.google.com/go/dataplex v1.10.1/go.mod h1:1MzmBv8FvjYfc7vDdxhnLFNskikkB+3vl475/XdCDhs= +cloud.google.com/go/dataplex v1.10.2/go.mod h1:xdC8URdTrCrZMW6keY779ZT1cTOfV8KEPNsw+LTRT1Y= +cloud.google.com/go/dataplex v1.11.1/go.mod h1:mHJYQQ2VEJHsyoC0OdNyy988DvEbPhqFs5OOLffLX0c= cloud.google.com/go/dataproc v1.7.0/go.mod h1:CKAlMjII9H90RXaMpSxQ8EU6dQx6iAYNPcYPOkSbi8s= cloud.google.com/go/dataproc v1.8.0/go.mod h1:5OW+zNAH0pMpw14JVrPONsxMQYMBqJuzORhIBfBn9uI= cloud.google.com/go/dataproc v1.12.0/go.mod h1:zrF3aX0uV3ikkMz6z4uBbIKyhRITnxvr4i3IjKsKrw4= cloud.google.com/go/dataproc/v2 v2.0.1/go.mod h1:7Ez3KRHdFGcfY7GcevBbvozX+zyWGcwLJvvAMwCaoZ4= cloud.google.com/go/dataproc/v2 v2.2.0/go.mod h1:lZR7AQtwZPvmINx5J87DSOOpTfof9LVZju6/Qo4lmcY= +cloud.google.com/go/dataproc/v2 v2.2.1/go.mod h1:QdAJLaBjh+l4PVlVZcmrmhGccosY/omC1qwfQ61Zv/o= +cloud.google.com/go/dataproc/v2 v2.2.2/go.mod h1:aocQywVmQVF4i8CL740rNI/ZRpsaaC1Wh2++BJ7HEJ4= +cloud.google.com/go/dataproc/v2 v2.2.3/go.mod h1:G5R6GBc9r36SXv/RtZIVfB8SipI+xVn0bX5SxUzVYbY= cloud.google.com/go/dataqna v0.5.0/go.mod h1:90Hyk596ft3zUQ8NkFfvICSIfHFh1Bc7C4cK3vbhkeo= cloud.google.com/go/dataqna v0.6.0/go.mod h1:1lqNpM7rqNLVgWBJyk5NF6Uen2PHym0jtVJonplVsDA= cloud.google.com/go/dataqna v0.7.0/go.mod h1:Lx9OcIIeqCrw1a6KdO3/5KMP1wAmTc0slZWwP12Qq3c= cloud.google.com/go/dataqna v0.8.1/go.mod h1:zxZM0Bl6liMePWsHA8RMGAfmTG34vJMapbHAxQ5+WA8= +cloud.google.com/go/dataqna v0.8.2/go.mod h1:KNEqgx8TTmUipnQsScOoDpq/VlXVptUqVMZnt30WAPs= +cloud.google.com/go/dataqna v0.8.3/go.mod h1:wXNBW2uvc9e7Gl5k8adyAMnLush1KVV6lZUhB+rqNu4= +cloud.google.com/go/dataqna v0.8.4/go.mod h1:mySRKjKg5Lz784P6sCov3p1QD+RZQONRMRjzGNcFd0c= cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE= cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= cloud.google.com/go/datastore v1.10.0/go.mod h1:PC5UzAmDEkAmkfaknstTYbNpgE49HAgW2J1gcgUfmdM= @@ -298,6 +414,7 @@ cloud.google.com/go/datastore v1.12.0/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1 cloud.google.com/go/datastore v1.12.1/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1EoLgSp6/N70= cloud.google.com/go/datastore v1.13.0/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1EoLgSp6/N70= cloud.google.com/go/datastore v1.14.0/go.mod h1:GAeStMBIt9bPS7jMJA85kgkpsMkvseWWXiaHya9Jes8= +cloud.google.com/go/datastore v1.15.0/go.mod h1:GAeStMBIt9bPS7jMJA85kgkpsMkvseWWXiaHya9Jes8= cloud.google.com/go/datastream v1.2.0/go.mod h1:i/uTP8/fZwgATHS/XFu0TcNUhuA0twZxxQ3EyCUQMwo= cloud.google.com/go/datastream v1.3.0/go.mod h1:cqlOX8xlyYF/uxhiKn6Hbv6WjwPPuI9W2M9SAXwaLLQ= cloud.google.com/go/datastream v1.4.0/go.mod h1:h9dpzScPhDTs5noEMQVWP8Wx8AFBRyS0s8KWPx/9r0g= @@ -306,12 +423,18 @@ cloud.google.com/go/datastream v1.6.0/go.mod h1:6LQSuswqLa7S4rPAOZFVjHIG3wJIjZcZ cloud.google.com/go/datastream v1.7.0/go.mod h1:uxVRMm2elUSPuh65IbZpzJNMbuzkcvu5CjMqVIUHrww= cloud.google.com/go/datastream v1.9.1/go.mod h1:hqnmr8kdUBmrnk65k5wNRoHSCYksvpdZIcZIEl8h43Q= cloud.google.com/go/datastream v1.10.0/go.mod h1:hqnmr8kdUBmrnk65k5wNRoHSCYksvpdZIcZIEl8h43Q= +cloud.google.com/go/datastream v1.10.1/go.mod h1:7ngSYwnw95YFyTd5tOGBxHlOZiL+OtpjheqU7t2/s/c= +cloud.google.com/go/datastream v1.10.2/go.mod h1:W42TFgKAs/om6x/CdXX5E4oiAsKlH+e8MTGy81zdYt0= +cloud.google.com/go/datastream v1.10.3/go.mod h1:YR0USzgjhqA/Id0Ycu1VvZe8hEWwrkjuXrGbzeDOSEA= cloud.google.com/go/deploy v1.4.0/go.mod h1:5Xghikd4VrmMLNaF6FiRFDlHb59VM59YoDQnOUdsH/c= cloud.google.com/go/deploy v1.5.0/go.mod h1:ffgdD0B89tToyW/U/D2eL0jN2+IEV/3EMuXHA0l4r+s= cloud.google.com/go/deploy v1.6.0/go.mod h1:f9PTHehG/DjCom3QH0cntOVRm93uGBDt2vKzAPwpXQI= cloud.google.com/go/deploy v1.8.0/go.mod h1:z3myEJnA/2wnB4sgjqdMfgxCA0EqC3RBTNcVPs93mtQ= cloud.google.com/go/deploy v1.11.0/go.mod h1:tKuSUV5pXbn67KiubiUNUejqLs4f5cxxiCNCeyl0F2g= cloud.google.com/go/deploy v1.13.0/go.mod h1:tKuSUV5pXbn67KiubiUNUejqLs4f5cxxiCNCeyl0F2g= +cloud.google.com/go/deploy v1.13.1/go.mod h1:8jeadyLkH9qu9xgO3hVWw8jVr29N1mnW42gRJT8GY6g= +cloud.google.com/go/deploy v1.14.1/go.mod h1:N8S0b+aIHSEeSr5ORVoC0+/mOPUysVt8ae4QkZYolAw= +cloud.google.com/go/deploy v1.14.2/go.mod h1:e5XOUI5D+YGldyLNZ21wbp9S8otJbBE4i88PtO9x/2g= cloud.google.com/go/dialogflow v1.15.0/go.mod h1:HbHDWs33WOGJgn6rfzBW1Kv807BE3O1+xGbn59zZWI4= cloud.google.com/go/dialogflow v1.16.1/go.mod h1:po6LlzGfK+smoSmTBnbkIZY2w8ffjz/RcGSS+sh1el0= cloud.google.com/go/dialogflow v1.17.0/go.mod h1:YNP09C/kXA1aZdBgC/VtXX74G/TKn7XVCcVumTflA+8= @@ -323,10 +446,17 @@ cloud.google.com/go/dialogflow v1.32.0/go.mod h1:jG9TRJl8CKrDhMEcvfcfFkkpp8ZhgPz cloud.google.com/go/dialogflow v1.38.0/go.mod h1:L7jnH+JL2mtmdChzAIcXQHXMvQkE3U4hTaNltEuxXn4= cloud.google.com/go/dialogflow v1.40.0/go.mod h1:L7jnH+JL2mtmdChzAIcXQHXMvQkE3U4hTaNltEuxXn4= cloud.google.com/go/dialogflow v1.43.0/go.mod h1:pDUJdi4elL0MFmt1REMvFkdsUTYSHq+rTCS8wg0S3+M= +cloud.google.com/go/dialogflow v1.44.0/go.mod h1:pDUJdi4elL0MFmt1REMvFkdsUTYSHq+rTCS8wg0S3+M= +cloud.google.com/go/dialogflow v1.44.1/go.mod h1:n/h+/N2ouKOO+rbe/ZnI186xImpqvCVj2DdsWS/0EAk= +cloud.google.com/go/dialogflow v1.44.2/go.mod h1:QzFYndeJhpVPElnFkUXxdlptx0wPnBWLCBT9BvtC3/c= +cloud.google.com/go/dialogflow v1.44.3/go.mod h1:mHly4vU7cPXVweuB5R0zsYKPMzy240aQdAu06SqBbAQ= cloud.google.com/go/dlp v1.6.0/go.mod h1:9eyB2xIhpU0sVwUixfBubDoRwP+GjeUoxxeueZmqvmM= cloud.google.com/go/dlp v1.7.0/go.mod h1:68ak9vCiMBjbasxeVD17hVPxDEck+ExiHavX8kiHG+Q= cloud.google.com/go/dlp v1.9.0/go.mod h1:qdgmqgTyReTz5/YNSSuueR8pl7hO0o9bQ39ZhtgkWp4= cloud.google.com/go/dlp v1.10.1/go.mod h1:IM8BWz1iJd8njcNcG0+Kyd9OPnqnRNkDV8j42VT5KOI= +cloud.google.com/go/dlp v1.10.2/go.mod h1:ZbdKIhcnyhILgccwVDzkwqybthh7+MplGC3kZVZsIOQ= +cloud.google.com/go/dlp v1.10.3/go.mod h1:iUaTc/ln8I+QT6Ai5vmuwfw8fqTk2kaz0FvCwhLCom0= +cloud.google.com/go/dlp v1.11.1/go.mod h1:/PA2EnioBeXTL/0hInwgj0rfsQb3lpE3R8XUJxqUNKI= cloud.google.com/go/documentai v1.7.0/go.mod h1:lJvftZB5NRiFSX4moiye1SMxHx0Bc3x1+p9e/RfXYiU= cloud.google.com/go/documentai v1.8.0/go.mod h1:xGHNEB7CtsnySCNrCFdCyyMz44RhFEEX2Q7UD0c5IhU= cloud.google.com/go/documentai v1.9.0/go.mod h1:FS5485S8R00U10GhgBC0aNGrJxBP8ZVpEeJ7PQDZd6k= @@ -336,35 +466,55 @@ cloud.google.com/go/documentai v1.18.0/go.mod h1:F6CK6iUH8J81FehpskRmhLq/3VlwQvb cloud.google.com/go/documentai v1.20.0/go.mod h1:yJkInoMcK0qNAEdRnqY/D5asy73tnPe88I1YTZT+a8E= cloud.google.com/go/documentai v1.22.0/go.mod h1:yJkInoMcK0qNAEdRnqY/D5asy73tnPe88I1YTZT+a8E= cloud.google.com/go/documentai v1.22.1/go.mod h1:LKs22aDHbJv7ufXuPypzRO7rG3ALLJxzdCXDPutw4Qc= +cloud.google.com/go/documentai v1.23.0/go.mod h1:LKs22aDHbJv7ufXuPypzRO7rG3ALLJxzdCXDPutw4Qc= +cloud.google.com/go/documentai v1.23.2/go.mod h1:Q/wcRT+qnuXOpjAkvOV4A+IeQl04q2/ReT7SSbytLSo= +cloud.google.com/go/documentai v1.23.4/go.mod h1:4MYAaEMnADPN1LPN5xboDR5QVB6AgsaxgFdJhitlE2Y= +cloud.google.com/go/documentai v1.23.5/go.mod h1:ghzBsyVTiVdkfKaUCum/9bGBEyBjDO4GfooEcYKhN+g= cloud.google.com/go/domains v0.6.0/go.mod h1:T9Rz3GasrpYk6mEGHh4rymIhjlnIuB4ofT1wTxDeT4Y= cloud.google.com/go/domains v0.7.0/go.mod h1:PtZeqS1xjnXuRPKE/88Iru/LdfoRyEHYA9nFQf4UKpg= cloud.google.com/go/domains v0.8.0/go.mod h1:M9i3MMDzGFXsydri9/vW+EWz9sWb4I6WyHqdlAk0idE= cloud.google.com/go/domains v0.9.1/go.mod h1:aOp1c0MbejQQ2Pjf1iJvnVyT+z6R6s8pX66KaCSDYfE= +cloud.google.com/go/domains v0.9.2/go.mod h1:3YvXGYzZG1Temjbk7EyGCuGGiXHJwVNmwIf+E/cUp5I= +cloud.google.com/go/domains v0.9.3/go.mod h1:29k66YNDLDY9LCFKpGFeh6Nj9r62ZKm5EsUJxAl84KU= +cloud.google.com/go/domains v0.9.4/go.mod h1:27jmJGShuXYdUNjyDG0SodTfT5RwLi7xmH334Gvi3fY= cloud.google.com/go/edgecontainer v0.1.0/go.mod h1:WgkZ9tp10bFxqO8BLPqv2LlfmQF1X8lZqwW4r1BTajk= cloud.google.com/go/edgecontainer v0.2.0/go.mod h1:RTmLijy+lGpQ7BXuTDa4C4ssxyXT34NIuHIgKuP4s5w= cloud.google.com/go/edgecontainer v0.3.0/go.mod h1:FLDpP4nykgwwIfcLt6zInhprzw0lEi2P1fjO6Ie0qbc= cloud.google.com/go/edgecontainer v1.0.0/go.mod h1:cttArqZpBB2q58W/upSG++ooo6EsblxDIolxa3jSjbY= cloud.google.com/go/edgecontainer v1.1.1/go.mod h1:O5bYcS//7MELQZs3+7mabRqoWQhXCzenBu0R8bz2rwk= +cloud.google.com/go/edgecontainer v1.1.2/go.mod h1:wQRjIzqxEs9e9wrtle4hQPSR1Y51kqN75dgF7UllZZ4= +cloud.google.com/go/edgecontainer v1.1.3/go.mod h1:Ll2DtIABzEfaxaVSbwj3QHFaOOovlDFiWVDu349jSsA= +cloud.google.com/go/edgecontainer v1.1.4/go.mod h1:AvFdVuZuVGdgaE5YvlL1faAoa1ndRR/5XhXZvPBHbsE= cloud.google.com/go/errorreporting v0.3.0/go.mod h1:xsP2yaAp+OAW4OIm60An2bbLpqIhKXdWR/tawvl7QzU= cloud.google.com/go/essentialcontacts v1.3.0/go.mod h1:r+OnHa5jfj90qIfZDO/VztSFqbQan7HV75p8sA+mdGI= cloud.google.com/go/essentialcontacts v1.4.0/go.mod h1:8tRldvHYsmnBCHdFpvU+GL75oWiBKl80BiqlFh9tp+8= cloud.google.com/go/essentialcontacts v1.5.0/go.mod h1:ay29Z4zODTuwliK7SnX8E86aUF2CTzdNtvv42niCX0M= cloud.google.com/go/essentialcontacts v1.6.2/go.mod h1:T2tB6tX+TRak7i88Fb2N9Ok3PvY3UNbUsMag9/BARh4= +cloud.google.com/go/essentialcontacts v1.6.3/go.mod h1:yiPCD7f2TkP82oJEFXFTou8Jl8L6LBRPeBEkTaO0Ggo= +cloud.google.com/go/essentialcontacts v1.6.4/go.mod h1:iju5Vy3d9tJUg0PYMd1nHhjV7xoCXaOAVabrwLaPBEM= +cloud.google.com/go/essentialcontacts v1.6.5/go.mod h1:jjYbPzw0x+yglXC890l6ECJWdYeZ5dlYACTFL0U/VuM= cloud.google.com/go/eventarc v1.7.0/go.mod h1:6ctpF3zTnaQCxUjHUdcfgcA1A2T309+omHZth7gDfmc= cloud.google.com/go/eventarc v1.8.0/go.mod h1:imbzxkyAU4ubfsaKYdQg04WS1NvncblHEup4kvF+4gw= cloud.google.com/go/eventarc v1.10.0/go.mod h1:u3R35tmZ9HvswGRBnF48IlYgYeBcPUCjkr4BTdem2Kw= cloud.google.com/go/eventarc v1.11.0/go.mod h1:PyUjsUKPWoRBCHeOxZd/lbOOjahV41icXyUY5kSTvVY= cloud.google.com/go/eventarc v1.12.1/go.mod h1:mAFCW6lukH5+IZjkvrEss+jmt2kOdYlN8aMx3sRJiAI= cloud.google.com/go/eventarc v1.13.0/go.mod h1:mAFCW6lukH5+IZjkvrEss+jmt2kOdYlN8aMx3sRJiAI= +cloud.google.com/go/eventarc v1.13.1/go.mod h1:EqBxmGHFrruIara4FUQ3RHlgfCn7yo1HYsu2Hpt/C3Y= +cloud.google.com/go/eventarc v1.13.2/go.mod h1:X9A80ShVu19fb4e5sc/OLV7mpFUKZMwfJFeeWhcIObM= +cloud.google.com/go/eventarc v1.13.3/go.mod h1:RWH10IAZIRcj1s/vClXkBgMHwh59ts7hSWcqD3kaclg= cloud.google.com/go/filestore v1.3.0/go.mod h1:+qbvHGvXU1HaKX2nD0WEPo92TP/8AQuCVEBXNY9z0+w= cloud.google.com/go/filestore v1.4.0/go.mod h1:PaG5oDfo9r224f8OYXURtAsY+Fbyq/bLYoINEK8XQAI= cloud.google.com/go/filestore v1.5.0/go.mod h1:FqBXDWBp4YLHqRnVGveOkHDf8svj9r5+mUDLupOWEDs= cloud.google.com/go/filestore v1.6.0/go.mod h1:di5unNuss/qfZTw2U9nhFqo8/ZDSc466dre85Kydllg= cloud.google.com/go/filestore v1.7.1/go.mod h1:y10jsorq40JJnjR/lQ8AfFbbcGlw3g+Dp8oN7i7FjV4= +cloud.google.com/go/filestore v1.7.2/go.mod h1:TYOlyJs25f/omgj+vY7/tIG/E7BX369triSPzE4LdgE= +cloud.google.com/go/filestore v1.7.3/go.mod h1:Qp8WaEERR3cSkxToxFPHh/b8AACkSut+4qlCjAmKTV0= +cloud.google.com/go/filestore v1.7.4/go.mod h1:S5JCxIbFjeBhWMTfIYH2Jx24J6BqjwpkkPl+nBA5DlI= cloud.google.com/go/firestore v1.9.0/go.mod h1:HMkjKHNTtRyZNiMzu7YAsLr9K3X2udY2AMwDaMEQiiE= cloud.google.com/go/firestore v1.11.0/go.mod h1:b38dKhgzlmNNGTNZZwe7ZRFEuRab1Hay3/DBsIGKKy4= cloud.google.com/go/firestore v1.12.0/go.mod h1:b38dKhgzlmNNGTNZZwe7ZRFEuRab1Hay3/DBsIGKKy4= cloud.google.com/go/firestore v1.13.0/go.mod h1:QojqqOh8IntInDUSTAh0c8ZsPYAr68Ma8c5DWOy8xb8= +cloud.google.com/go/firestore v1.14.0/go.mod h1:96MVaHLsEhbvkBEdZgfN+AS/GIkco1LRpH9Xp9YZfzQ= cloud.google.com/go/functions v1.6.0/go.mod h1:3H1UA3qiIPRWD7PeZKLvHZ9SaQhR26XIJcC0A5GbvAk= cloud.google.com/go/functions v1.7.0/go.mod h1:+d+QBcWM+RsrgZfV9xo6KfA1GlzJfxcfZcRPEhDDfzg= cloud.google.com/go/functions v1.8.0/go.mod h1:RTZ4/HsQjIqIYP9a9YPbU+QFoQsAlYgrwOXJWHn1POY= @@ -373,6 +523,9 @@ cloud.google.com/go/functions v1.10.0/go.mod h1:0D3hEOe3DbEvCXtYOZHQZmD+SzYsi1Yb cloud.google.com/go/functions v1.12.0/go.mod h1:AXWGrF3e2C/5ehvwYo/GH6O5s09tOPksiKhz+hH8WkA= cloud.google.com/go/functions v1.13.0/go.mod h1:EU4O007sQm6Ef/PwRsI8N2umygGqPBS/IZQKBQBcJ3c= cloud.google.com/go/functions v1.15.1/go.mod h1:P5yNWUTkyU+LvW/S9O6V+V423VZooALQlqoXdoPz5AE= +cloud.google.com/go/functions v1.15.2/go.mod h1:CHAjtcR6OU4XF2HuiVeriEdELNcnvRZSk1Q8RMqy4lE= +cloud.google.com/go/functions v1.15.3/go.mod h1:r/AMHwBheapkkySEhiZYLDBwVJCdlRwsm4ieJu35/Ug= +cloud.google.com/go/functions v1.15.4/go.mod h1:CAsTc3VlRMVvx+XqXxKqVevguqJpnVip4DdonFsX28I= cloud.google.com/go/gaming v1.5.0/go.mod h1:ol7rGcxP/qHTRQE/RO4bxkXq+Fix0j6D4LFPzYTIrDM= cloud.google.com/go/gaming v1.6.0/go.mod h1:YMU1GEvA39Qt3zWGyAVA9bpYz/yAhTvaQ1t2sK4KPUA= cloud.google.com/go/gaming v1.7.0/go.mod h1:LrB8U7MHdGgFG851iHAfqUdLcKBdQ55hzXy9xBJz0+w= @@ -384,26 +537,41 @@ cloud.google.com/go/gkebackup v0.3.0/go.mod h1:n/E671i1aOQvUxT541aTkCwExO/bTer2H cloud.google.com/go/gkebackup v0.4.0/go.mod h1:byAyBGUwYGEEww7xsbnUTBHIYcOPy/PgUWUtOeRm9Vg= cloud.google.com/go/gkebackup v1.3.0/go.mod h1:vUDOu++N0U5qs4IhG1pcOnD1Mac79xWy6GoBFlWCWBU= cloud.google.com/go/gkebackup v1.3.1/go.mod h1:vUDOu++N0U5qs4IhG1pcOnD1Mac79xWy6GoBFlWCWBU= +cloud.google.com/go/gkebackup v1.3.2/go.mod h1:OMZbXzEJloyXMC7gqdSB+EOEQ1AKcpGYvO3s1ec5ixk= +cloud.google.com/go/gkebackup v1.3.3/go.mod h1:eMk7/wVV5P22KBakhQnJxWSVftL1p4VBFLpv0kIft7I= +cloud.google.com/go/gkebackup v1.3.4/go.mod h1:gLVlbM8h/nHIs09ns1qx3q3eaXcGSELgNu1DWXYz1HI= cloud.google.com/go/gkeconnect v0.5.0/go.mod h1:c5lsNAg5EwAy7fkqX/+goqFsU1Da/jQFqArp+wGNr/o= cloud.google.com/go/gkeconnect v0.6.0/go.mod h1:Mln67KyU/sHJEBY8kFZ0xTeyPtzbq9StAVvEULYK16A= cloud.google.com/go/gkeconnect v0.7.0/go.mod h1:SNfmVqPkaEi3bF/B3CNZOAYPYdg7sU+obZ+QTky2Myw= cloud.google.com/go/gkeconnect v0.8.1/go.mod h1:KWiK1g9sDLZqhxB2xEuPV8V9NYzrqTUmQR9shJHpOZw= +cloud.google.com/go/gkeconnect v0.8.2/go.mod h1:6nAVhwchBJYgQCXD2pHBFQNiJNyAd/wyxljpaa6ZPrY= +cloud.google.com/go/gkeconnect v0.8.3/go.mod h1:i9GDTrfzBSUZGCe98qSu1B8YB8qfapT57PenIb820Jo= +cloud.google.com/go/gkeconnect v0.8.4/go.mod h1:84hZz4UMlDCKl8ifVW8layK4WHlMAFeq8vbzjU0yJkw= cloud.google.com/go/gkehub v0.9.0/go.mod h1:WYHN6WG8w9bXU0hqNxt8rm5uxnk8IH+lPY9J2TV7BK0= cloud.google.com/go/gkehub v0.10.0/go.mod h1:UIPwxI0DsrpsVoWpLB0stwKCP+WFVG9+y977wO+hBH0= cloud.google.com/go/gkehub v0.11.0/go.mod h1:JOWHlmN+GHyIbuWQPl47/C2RFhnFKH38jH9Ascu3n0E= cloud.google.com/go/gkehub v0.12.0/go.mod h1:djiIwwzTTBrF5NaXCGv3mf7klpEMcST17VBTVVDcuaw= cloud.google.com/go/gkehub v0.14.1/go.mod h1:VEXKIJZ2avzrbd7u+zeMtW00Y8ddk/4V9511C9CQGTY= +cloud.google.com/go/gkehub v0.14.2/go.mod h1:iyjYH23XzAxSdhrbmfoQdePnlMj2EWcvnR+tHdBQsCY= +cloud.google.com/go/gkehub v0.14.3/go.mod h1:jAl6WafkHHW18qgq7kqcrXYzN08hXeK/Va3utN8VKg8= +cloud.google.com/go/gkehub v0.14.4/go.mod h1:Xispfu2MqnnFt8rV/2/3o73SK1snL8s9dYJ9G2oQMfc= cloud.google.com/go/gkemulticloud v0.3.0/go.mod h1:7orzy7O0S+5kq95e4Hpn7RysVA7dPs8W/GgfUtsPbrA= cloud.google.com/go/gkemulticloud v0.4.0/go.mod h1:E9gxVBnseLWCk24ch+P9+B2CoDFJZTyIgLKSalC7tuI= cloud.google.com/go/gkemulticloud v0.5.0/go.mod h1:W0JDkiyi3Tqh0TJr//y19wyb1yf8llHVto2Htf2Ja3Y= cloud.google.com/go/gkemulticloud v0.6.1/go.mod h1:kbZ3HKyTsiwqKX7Yw56+wUGwwNZViRnxWK2DVknXWfw= cloud.google.com/go/gkemulticloud v1.0.0/go.mod h1:kbZ3HKyTsiwqKX7Yw56+wUGwwNZViRnxWK2DVknXWfw= +cloud.google.com/go/gkemulticloud v1.0.1/go.mod h1:AcrGoin6VLKT/fwZEYuqvVominLriQBCKmbjtnbMjG8= +cloud.google.com/go/gkemulticloud v1.0.2/go.mod h1:+ee5VXxKb3H1l4LZAcgWB/rvI16VTNTrInWxDjAGsGo= +cloud.google.com/go/gkemulticloud v1.0.3/go.mod h1:7NpJBN94U6DY1xHIbsDqB2+TFZUfjLUKLjUX8NGLor0= cloud.google.com/go/grafeas v0.2.0/go.mod h1:KhxgtF2hb0P191HlY5besjYm6MqTSTj3LSI+M+ByZHc= cloud.google.com/go/grafeas v0.3.0/go.mod h1:P7hgN24EyONOTMyeJH6DxG4zD7fwiYa5Q6GUgyFSOU8= cloud.google.com/go/gsuiteaddons v1.3.0/go.mod h1:EUNK/J1lZEZO8yPtykKxLXI6JSVN2rg9bN8SXOa0bgM= cloud.google.com/go/gsuiteaddons v1.4.0/go.mod h1:rZK5I8hht7u7HxFQcFei0+AtfS9uSushomRlg+3ua1o= cloud.google.com/go/gsuiteaddons v1.5.0/go.mod h1:TFCClYLd64Eaa12sFVmUyG62tk4mdIsI7pAnSXRkcFo= cloud.google.com/go/gsuiteaddons v1.6.1/go.mod h1:CodrdOqRZcLp5WOwejHWYBjZvfY0kOphkAKpF/3qdZY= +cloud.google.com/go/gsuiteaddons v1.6.2/go.mod h1:K65m9XSgs8hTF3X9nNTPi8IQueljSdYo9F+Mi+s4MyU= +cloud.google.com/go/gsuiteaddons v1.6.3/go.mod h1:sCFJkZoMrLZT3JTb8uJqgKPNshH2tfXeCwTFRebTq48= +cloud.google.com/go/gsuiteaddons v1.6.4/go.mod h1:rxtstw7Fx22uLOXBpsvb9DUbC+fiXs7rF4U29KHM/pE= cloud.google.com/go/iam v0.1.0/go.mod h1:vcUNEa0pEm0qRVpmWepWaFMIAI8/hjB9mO8rNCJtF6c= cloud.google.com/go/iam v0.3.0/go.mod h1:XzJPvDayI+9zsASAFO68Hk07u3z+f+JrT2xXNdp4bnY= cloud.google.com/go/iam v0.5.0/go.mod h1:wPU9Vt0P4UmCux7mqtRu6jcpPAb74cP1fh50J3QpkUc= @@ -417,6 +585,9 @@ cloud.google.com/go/iam v1.0.1/go.mod h1:yR3tmSL8BcZB4bxByRv2jkSIahVmCtfKZwLYGBa cloud.google.com/go/iam v1.1.0/go.mod h1:nxdHjaKfCr7fNYx/HJMM8LgiMugmveWlkatear5gVyk= cloud.google.com/go/iam v1.1.1/go.mod h1:A5avdyVL2tCppe4unb0951eI9jreack+RJ0/d+KUZOU= cloud.google.com/go/iam v1.1.2/go.mod h1:A5avdyVL2tCppe4unb0951eI9jreack+RJ0/d+KUZOU= +cloud.google.com/go/iam v1.1.3/go.mod h1:3khUlaBXfPKKe7huYgEpDn6FtgRyMEqbkvBxrQyY5SE= +cloud.google.com/go/iam v1.1.4/go.mod h1:l/rg8l1AaA+VFMho/HYx2Vv6xinPSLMF8qfhRPIZ0L8= +cloud.google.com/go/iam v1.1.5/go.mod h1:rB6P/Ic3mykPbFio+vo7403drjlgvoWfYpJhMXEbzv8= cloud.google.com/go/iap v1.4.0/go.mod h1:RGFwRJdihTINIe4wZ2iCP0zF/qu18ZwyKxrhMhygBEc= cloud.google.com/go/iap v1.5.0/go.mod h1:UH/CGgKd4KyohZL5Pt0jSKE4m3FR51qg6FKQ/z/Ix9A= cloud.google.com/go/iap v1.6.0/go.mod h1:NSuvI9C/j7UdjGjIde7t7HBz+QTwBcapPE07+sSRcLk= @@ -424,15 +595,24 @@ cloud.google.com/go/iap v1.7.0/go.mod h1:beqQx56T9O1G1yNPph+spKpNibDlYIiIixiqsQX cloud.google.com/go/iap v1.7.1/go.mod h1:WapEwPc7ZxGt2jFGB/C/bm+hP0Y6NXzOYGjpPnmMS74= cloud.google.com/go/iap v1.8.1/go.mod h1:sJCbeqg3mvWLqjZNsI6dfAtbbV1DL2Rl7e1mTyXYREQ= cloud.google.com/go/iap v1.9.0/go.mod h1:01OFxd1R+NFrg78S+hoPV5PxEzv22HXaNqUUlmNHFuY= +cloud.google.com/go/iap v1.9.1/go.mod h1:SIAkY7cGMLohLSdBR25BuIxO+I4fXJiL06IBL7cy/5Q= +cloud.google.com/go/iap v1.9.2/go.mod h1:GwDTOs047PPSnwRD0Us5FKf4WDRcVvHg1q9WVkKBhdI= +cloud.google.com/go/iap v1.9.3/go.mod h1:DTdutSZBqkkOm2HEOTBzhZxh2mwwxshfD/h3yofAiCw= cloud.google.com/go/ids v1.1.0/go.mod h1:WIuwCaYVOzHIj2OhN9HAwvW+DBdmUAdcWlFxRl+KubM= cloud.google.com/go/ids v1.2.0/go.mod h1:5WXvp4n25S0rA/mQWAg1YEEBBq6/s+7ml1RDCW1IrcY= cloud.google.com/go/ids v1.3.0/go.mod h1:JBdTYwANikFKaDP6LtW5JAi4gubs57SVNQjemdt6xV4= cloud.google.com/go/ids v1.4.1/go.mod h1:np41ed8YMU8zOgv53MMMoCntLTn2lF+SUzlM+O3u/jw= +cloud.google.com/go/ids v1.4.2/go.mod h1:3vw8DX6YddRu9BncxuzMyWn0g8+ooUjI2gslJ7FH3vk= +cloud.google.com/go/ids v1.4.3/go.mod h1:9CXPqI3GedjmkjbMWCUhMZ2P2N7TUMzAkVXYEH2orYU= +cloud.google.com/go/ids v1.4.4/go.mod h1:z+WUc2eEl6S/1aZWzwtVNWoSZslgzPxAboS0lZX0HjI= cloud.google.com/go/iot v1.3.0/go.mod h1:r7RGh2B61+B8oz0AGE+J72AhA0G7tdXItODWsaA2oLs= cloud.google.com/go/iot v1.4.0/go.mod h1:dIDxPOn0UvNDUMD8Ger7FIaTuvMkj+aGk94RPP0iV+g= cloud.google.com/go/iot v1.5.0/go.mod h1:mpz5259PDl3XJthEmh9+ap0affn/MqNSP4My77Qql9o= cloud.google.com/go/iot v1.6.0/go.mod h1:IqdAsmE2cTYYNO1Fvjfzo9po179rAtJeVGUvkLN3rLE= cloud.google.com/go/iot v1.7.1/go.mod h1:46Mgw7ev1k9KqK1ao0ayW9h0lI+3hxeanz+L1zmbbbk= +cloud.google.com/go/iot v1.7.2/go.mod h1:q+0P5zr1wRFpw7/MOgDXrG/HVA+l+cSwdObffkrpnSg= +cloud.google.com/go/iot v1.7.3/go.mod h1:t8itFchkol4VgNbHnIq9lXoOOtHNR3uAACQMYbN9N4I= +cloud.google.com/go/iot v1.7.4/go.mod h1:3TWqDVvsddYBG++nHSZmluoCAVGr1hAcabbWZNKEZLk= cloud.google.com/go/kms v1.4.0/go.mod h1:fajBHndQ+6ubNw6Ss2sSd+SWvjL26RNo/dr7uxsnnOA= cloud.google.com/go/kms v1.5.0/go.mod h1:QJS2YY0eJGBg3mnDfuaCyLauWwBJiHRboYxJ++1xJNg= cloud.google.com/go/kms v1.6.0/go.mod h1:Jjy850yySiasBUDi6KFUwUv2n1+o7QZFyuUJg6OgjA0= @@ -444,6 +624,9 @@ cloud.google.com/go/kms v1.11.0/go.mod h1:hwdiYC0xjnWsKQQCQQmIQnS9asjYVSK6jtXm+z cloud.google.com/go/kms v1.12.1/go.mod h1:c9J991h5DTl+kg7gi3MYomh12YEENGrf48ee/N/2CDM= cloud.google.com/go/kms v1.15.0/go.mod h1:c9J991h5DTl+kg7gi3MYomh12YEENGrf48ee/N/2CDM= cloud.google.com/go/kms v1.15.2/go.mod h1:3hopT4+7ooWRCjc2DxgnpESFxhIraaI2IpAVUEhbT/w= +cloud.google.com/go/kms v1.15.3/go.mod h1:AJdXqHxS2GlPyduM99s9iGqi2nwbviBbhV/hdmt4iOQ= +cloud.google.com/go/kms v1.15.4/go.mod h1:L3Sdj6QTHK8dfwK5D1JLsAyELsNMnd3tAIwGS4ltKpc= +cloud.google.com/go/kms v1.15.5/go.mod h1:cU2H5jnp6G2TDpUGZyqTCoy1n16fbubHZjmVXSMtwDI= cloud.google.com/go/language v1.4.0/go.mod h1:F9dRpNFQmJbkaop6g0JhSBXCNlO90e1KWx5iDdxbWic= cloud.google.com/go/language v1.6.0/go.mod h1:6dJ8t3B+lUYfStgls25GusK04NLh3eDLQnWM3mdEbhI= cloud.google.com/go/language v1.7.0/go.mod h1:DJ6dYN/W+SQOjF8e1hLQXMF21AkH2w9wiPzPCJa2MIE= @@ -451,10 +634,16 @@ cloud.google.com/go/language v1.8.0/go.mod h1:qYPVHf7SPoNNiCL2Dr0FfEFNil1qi3pQEy cloud.google.com/go/language v1.9.0/go.mod h1:Ns15WooPM5Ad/5no/0n81yUetis74g3zrbeJBE+ptUY= cloud.google.com/go/language v1.10.1/go.mod h1:CPp94nsdVNiQEt1CNjF5WkTcisLiHPyIbMhvR8H2AW0= cloud.google.com/go/language v1.11.0/go.mod h1:uDx+pFDdAKTY8ehpWbiXyQdz8tDSYLJbQcXsCkjYyvQ= +cloud.google.com/go/language v1.11.1/go.mod h1:Xyid9MG9WOX3utvDbpX7j3tXDmmDooMyMDqgUVpH17U= +cloud.google.com/go/language v1.12.1/go.mod h1:zQhalE2QlQIxbKIZt54IASBzmZpN/aDASea5zl1l+J4= +cloud.google.com/go/language v1.12.2/go.mod h1:9idWapzr/JKXBBQ4lWqVX/hcadxB194ry20m/bTrhWc= cloud.google.com/go/lifesciences v0.5.0/go.mod h1:3oIKy8ycWGPUyZDR/8RNnTOYevhaMLqh5vLUXs9zvT8= cloud.google.com/go/lifesciences v0.6.0/go.mod h1:ddj6tSX/7BOnhxCSd3ZcETvtNr8NZ6t/iPhY2Tyfu08= cloud.google.com/go/lifesciences v0.8.0/go.mod h1:lFxiEOMqII6XggGbOnKiyZ7IBwoIqA84ClvoezaA/bo= cloud.google.com/go/lifesciences v0.9.1/go.mod h1:hACAOd1fFbCGLr/+weUKRAJas82Y4vrL3O5326N//Wc= +cloud.google.com/go/lifesciences v0.9.2/go.mod h1:QHEOO4tDzcSAzeJg7s2qwnLM2ji8IRpQl4p6m5Z9yTA= +cloud.google.com/go/lifesciences v0.9.3/go.mod h1:gNGBOJV80IWZdkd+xz4GQj4mbqaz737SCLHn2aRhQKM= +cloud.google.com/go/lifesciences v0.9.4/go.mod h1:bhm64duKhMi7s9jR9WYJYvjAFJwRqNj+Nia7hF0Z7JA= cloud.google.com/go/logging v1.6.1/go.mod h1:5ZO0mHHbvm8gEmeEUHrmDlTDSu5imF6MUP9OfilNXBw= cloud.google.com/go/logging v1.7.0/go.mod h1:3xjP2CjkM3ZkO73aj4ASA5wRPGGCRrPIAeNqVNkzY8M= cloud.google.com/go/logging v1.8.1/go.mod h1:TJjR+SimHwuC8MZ9cjByQulAMgni+RkXeI3wwctHJEI= @@ -464,25 +653,40 @@ cloud.google.com/go/longrunning v0.4.1/go.mod h1:4iWDqhBZ70CvZ6BfETbvam3T8FMvLK+ cloud.google.com/go/longrunning v0.4.2/go.mod h1:OHrnaYyLUV6oqwh0xiS7e5sLQhP1m0QU9R+WhGDMgIQ= cloud.google.com/go/longrunning v0.5.0/go.mod h1:0JNuqRShmscVAhIACGtskSAWtqtOoPkwP0YF1oVEchc= cloud.google.com/go/longrunning v0.5.1/go.mod h1:spvimkwdz6SPWKEt/XBij79E9fiTkHSQl/fRUUQJYJc= +cloud.google.com/go/longrunning v0.5.2/go.mod h1:nqo6DQbNV2pXhGDbDMoN2bWz68MjZUzqv2YttZiveCs= +cloud.google.com/go/longrunning v0.5.3/go.mod h1:y/0ga59EYu58J6SHmmQOvekvND2qODbu8ywBBW7EK7Y= +cloud.google.com/go/longrunning v0.5.4/go.mod h1:zqNVncI0BOP8ST6XQD1+VcvuShMmq7+xFSzOL++V0dI= cloud.google.com/go/managedidentities v1.3.0/go.mod h1:UzlW3cBOiPrzucO5qWkNkh0w33KFtBJU281hacNvsdE= cloud.google.com/go/managedidentities v1.4.0/go.mod h1:NWSBYbEMgqmbZsLIyKvxrYbtqOsxY1ZrGM+9RgDqInM= cloud.google.com/go/managedidentities v1.5.0/go.mod h1:+dWcZ0JlUmpuxpIDfyP5pP5y0bLdRwOS4Lp7gMni/LA= cloud.google.com/go/managedidentities v1.6.1/go.mod h1:h/irGhTN2SkZ64F43tfGPMbHnypMbu4RB3yl8YcuEak= +cloud.google.com/go/managedidentities v1.6.2/go.mod h1:5c2VG66eCa0WIq6IylRk3TBW83l161zkFvCj28X7jn8= +cloud.google.com/go/managedidentities v1.6.3/go.mod h1:tewiat9WLyFN0Fi7q1fDD5+0N4VUoL0SCX0OTCthZq4= +cloud.google.com/go/managedidentities v1.6.4/go.mod h1:WgyaECfHmF00t/1Uk8Oun3CQ2PGUtjc3e9Alh79wyiM= cloud.google.com/go/maps v0.1.0/go.mod h1:BQM97WGyfw9FWEmQMpZ5T6cpovXXSd1cGmFma94eubI= cloud.google.com/go/maps v0.6.0/go.mod h1:o6DAMMfb+aINHz/p/jbcY+mYeXBoZoxTfdSQ8VAJaCw= cloud.google.com/go/maps v0.7.0/go.mod h1:3GnvVl3cqeSvgMcpRlQidXsPYuDGQ8naBis7MVzpXsY= cloud.google.com/go/maps v1.3.0/go.mod h1:6mWTUv+WhnOwAgjVsSW2QPPECmW+s3PcRyOa9vgG/5s= cloud.google.com/go/maps v1.4.0/go.mod h1:6mWTUv+WhnOwAgjVsSW2QPPECmW+s3PcRyOa9vgG/5s= +cloud.google.com/go/maps v1.4.1/go.mod h1:BxSa0BnW1g2U2gNdbq5zikLlHUuHW0GFWh7sgML2kIY= +cloud.google.com/go/maps v1.5.1/go.mod h1:NPMZw1LJwQZYCfz4y+EIw+SI+24A4bpdFJqdKVr0lt4= +cloud.google.com/go/maps v1.6.1/go.mod h1:4+buOHhYXFBp58Zj/K+Lc1rCmJssxxF4pJ5CJnhdz18= cloud.google.com/go/mediatranslation v0.5.0/go.mod h1:jGPUhGTybqsPQn91pNXw0xVHfuJ3leR1wj37oU3y1f4= cloud.google.com/go/mediatranslation v0.6.0/go.mod h1:hHdBCTYNigsBxshbznuIMFNe5QXEowAuNmmC7h8pu5w= cloud.google.com/go/mediatranslation v0.7.0/go.mod h1:LCnB/gZr90ONOIQLgSXagp8XUW1ODs2UmUMvcgMfI2I= cloud.google.com/go/mediatranslation v0.8.1/go.mod h1:L/7hBdEYbYHQJhX2sldtTO5SZZ1C1vkapubj0T2aGig= +cloud.google.com/go/mediatranslation v0.8.2/go.mod h1:c9pUaDRLkgHRx3irYE5ZC8tfXGrMYwNZdmDqKMSfFp8= +cloud.google.com/go/mediatranslation v0.8.3/go.mod h1:F9OnXTy336rteOEywtY7FOqCk+J43o2RF638hkOQl4Y= +cloud.google.com/go/mediatranslation v0.8.4/go.mod h1:9WstgtNVAdN53m6TQa5GjIjLqKQPXe74hwSCxUP6nj4= cloud.google.com/go/memcache v1.4.0/go.mod h1:rTOfiGZtJX1AaFUrOgsMHX5kAzaTQ8azHiuDoTPzNsE= cloud.google.com/go/memcache v1.5.0/go.mod h1:dk3fCK7dVo0cUU2c36jKb4VqKPS22BTkf81Xq617aWM= cloud.google.com/go/memcache v1.6.0/go.mod h1:XS5xB0eQZdHtTuTF9Hf8eJkKtR3pVRCcvJwtm68T3rA= cloud.google.com/go/memcache v1.7.0/go.mod h1:ywMKfjWhNtkQTxrWxCkCFkoPjLHPW6A7WOTVI8xy3LY= cloud.google.com/go/memcache v1.9.0/go.mod h1:8oEyzXCu+zo9RzlEaEjHl4KkgjlNDaXbCQeQWlzNFJM= cloud.google.com/go/memcache v1.10.1/go.mod h1:47YRQIarv4I3QS5+hoETgKO40InqzLP6kpNLvyXuyaA= +cloud.google.com/go/memcache v1.10.2/go.mod h1:f9ZzJHLBrmd4BkguIAa/l/Vle6uTHzHokdnzSWOdQ6A= +cloud.google.com/go/memcache v1.10.3/go.mod h1:6z89A41MT2DVAW0P4iIRdu5cmRTsbsFn4cyiIx8gbwo= +cloud.google.com/go/memcache v1.10.4/go.mod h1:v/d8PuC8d1gD6Yn5+I3INzLR01IDn0N4Ym56RgikSI0= cloud.google.com/go/metastore v1.5.0/go.mod h1:2ZNrDcQwghfdtCwJ33nM0+GrBGlVuh8rakL3vdPY3XY= cloud.google.com/go/metastore v1.6.0/go.mod h1:6cyQTls8CWXzk45G55x57DVQ9gWg7RiH65+YgPsNh9s= cloud.google.com/go/metastore v1.7.0/go.mod h1:s45D0B4IlsINu87/AsWiEVYbLaIMeUSoxlKKDqBGFS8= @@ -490,12 +694,19 @@ cloud.google.com/go/metastore v1.8.0/go.mod h1:zHiMc4ZUpBiM7twCIFQmJ9JMEkDSyZS9U cloud.google.com/go/metastore v1.10.0/go.mod h1:fPEnH3g4JJAk+gMRnrAnoqyv2lpUCqJPWOodSaf45Eo= cloud.google.com/go/metastore v1.11.1/go.mod h1:uZuSo80U3Wd4zi6C22ZZliOUJ3XeM/MlYi/z5OAOWRA= cloud.google.com/go/metastore v1.12.0/go.mod h1:uZuSo80U3Wd4zi6C22ZZliOUJ3XeM/MlYi/z5OAOWRA= +cloud.google.com/go/metastore v1.13.0/go.mod h1:URDhpG6XLeh5K+Glq0NOt74OfrPKTwS62gEPZzb5SOk= +cloud.google.com/go/metastore v1.13.1/go.mod h1:IbF62JLxuZmhItCppcIfzBBfUFq0DIB9HPDoLgWrVOU= +cloud.google.com/go/metastore v1.13.2/go.mod h1:KS59dD+unBji/kFebVp8XU/quNSyo8b6N6tPGspKszA= +cloud.google.com/go/metastore v1.13.3/go.mod h1:K+wdjXdtkdk7AQg4+sXS8bRrQa9gcOr+foOMF2tqINE= cloud.google.com/go/monitoring v1.7.0/go.mod h1:HpYse6kkGo//7p6sT0wsIC6IBDET0RhIsnmlA53dvEk= cloud.google.com/go/monitoring v1.8.0/go.mod h1:E7PtoMJ1kQXWxPjB6mv2fhC5/15jInuulFdYYtlcvT4= cloud.google.com/go/monitoring v1.12.0/go.mod h1:yx8Jj2fZNEkL/GYZyTLS4ZtZEZN8WtDEiEqG4kLK50w= cloud.google.com/go/monitoring v1.13.0/go.mod h1:k2yMBAB1H9JT/QETjNkgdCGD9bPF712XiLTVr+cBrpw= cloud.google.com/go/monitoring v1.15.1/go.mod h1:lADlSAlFdbqQuwwpaImhsJXu1QSdd3ojypXrFSMr2rM= cloud.google.com/go/monitoring v1.16.0/go.mod h1:Ptp15HgAyM1fNICAojDMoNc/wUmn67mLHQfyqbw+poY= +cloud.google.com/go/monitoring v1.16.1/go.mod h1:6HsxddR+3y9j+o/cMJH6q/KJ/CBTvM/38L/1m7bTRJ4= +cloud.google.com/go/monitoring v1.16.2/go.mod h1:B44KGwi4ZCF8Rk/5n+FWeispDXoKSk9oss2QNlXJBgc= +cloud.google.com/go/monitoring v1.16.3/go.mod h1:KwSsX5+8PnXv5NJnICZzW2R8pWTis8ypC4zmdRD63Tw= cloud.google.com/go/networkconnectivity v1.4.0/go.mod h1:nOl7YL8odKyAOtzNX73/M5/mGZgqqMeryi6UPZTk/rA= cloud.google.com/go/networkconnectivity v1.5.0/go.mod h1:3GzqJx7uhtlM3kln0+x5wyFvuVH1pIBJjhCpjzSt75o= cloud.google.com/go/networkconnectivity v1.6.0/go.mod h1:OJOoEXW+0LAxHh89nXd64uGG+FbQoeH8DtxCHVOMlaM= @@ -504,16 +715,26 @@ cloud.google.com/go/networkconnectivity v1.10.0/go.mod h1:UP4O4sWXJG13AqrTdQCD9T cloud.google.com/go/networkconnectivity v1.11.0/go.mod h1:iWmDD4QF16VCDLXUqvyspJjIEtBR/4zq5hwnY2X3scM= cloud.google.com/go/networkconnectivity v1.12.1/go.mod h1:PelxSWYM7Sh9/guf8CFhi6vIqf19Ir/sbfZRUwXh92E= cloud.google.com/go/networkconnectivity v1.13.0/go.mod h1:SAnGPes88pl7QRLUen2HmcBSE9AowVAcdug8c0RSBFk= +cloud.google.com/go/networkconnectivity v1.14.0/go.mod h1:SAnGPes88pl7QRLUen2HmcBSE9AowVAcdug8c0RSBFk= +cloud.google.com/go/networkconnectivity v1.14.1/go.mod h1:LyGPXR742uQcDxZ/wv4EI0Vu5N6NKJ77ZYVnDe69Zug= +cloud.google.com/go/networkconnectivity v1.14.2/go.mod h1:5UFlwIisZylSkGG1AdwK/WZUaoz12PKu6wODwIbFzJo= +cloud.google.com/go/networkconnectivity v1.14.3/go.mod h1:4aoeFdrJpYEXNvrnfyD5kIzs8YtHg945Og4koAjHQek= cloud.google.com/go/networkmanagement v1.4.0/go.mod h1:Q9mdLLRn60AsOrPc8rs8iNV6OHXaGcDdsIQe1ohekq8= cloud.google.com/go/networkmanagement v1.5.0/go.mod h1:ZnOeZ/evzUdUsnvRt792H0uYEnHQEMaz+REhhzJRcf4= cloud.google.com/go/networkmanagement v1.6.0/go.mod h1:5pKPqyXjB/sgtvB5xqOemumoQNB7y95Q7S+4rjSOPYY= cloud.google.com/go/networkmanagement v1.8.0/go.mod h1:Ho/BUGmtyEqrttTgWEe7m+8vDdK74ibQc+Be0q7Fof0= cloud.google.com/go/networkmanagement v1.9.0/go.mod h1:UTUaEU9YwbCAhhz3jEOHr+2/K/MrBk2XxOLS89LQzFw= +cloud.google.com/go/networkmanagement v1.9.1/go.mod h1:CCSYgrQQvW73EJawO2QamemYcOb57LvrDdDU51F0mcI= +cloud.google.com/go/networkmanagement v1.9.2/go.mod h1:iDGvGzAoYRghhp4j2Cji7sF899GnfGQcQRQwgVOWnDw= +cloud.google.com/go/networkmanagement v1.9.3/go.mod h1:y7WMO1bRLaP5h3Obm4tey+NquUvB93Co1oh4wpL+XcU= cloud.google.com/go/networksecurity v0.5.0/go.mod h1:xS6fOCoqpVC5zx15Z/MqkfDwH4+m/61A3ODiDV1xmiQ= cloud.google.com/go/networksecurity v0.6.0/go.mod h1:Q5fjhTr9WMI5mbpRYEbiexTzROf7ZbDzvzCrNl14nyU= cloud.google.com/go/networksecurity v0.7.0/go.mod h1:mAnzoxx/8TBSyXEeESMy9OOYwo1v+gZ5eMRnsT5bC8k= cloud.google.com/go/networksecurity v0.8.0/go.mod h1:B78DkqsxFG5zRSVuwYFRZ9Xz8IcQ5iECsNrPn74hKHU= cloud.google.com/go/networksecurity v0.9.1/go.mod h1:MCMdxOKQ30wsBI1eI659f9kEp4wuuAueoC9AJKSPWZQ= +cloud.google.com/go/networksecurity v0.9.2/go.mod h1:jG0SeAttWzPMUILEHDUvFYdQTl8L/E/KC8iZDj85lEI= +cloud.google.com/go/networksecurity v0.9.3/go.mod h1:l+C0ynM6P+KV9YjOnx+kk5IZqMSLccdBqW6GUoF4p/0= +cloud.google.com/go/networksecurity v0.9.4/go.mod h1:E9CeMZ2zDsNBkr8axKSYm8XyTqNhiCHf1JO/Vb8mD1w= cloud.google.com/go/notebooks v1.2.0/go.mod h1:9+wtppMfVPUeJ8fIWPOq1UnATHISkGXGqTkxeieQ6UY= cloud.google.com/go/notebooks v1.3.0/go.mod h1:bFR5lj07DtCPC7YAAJ//vHskFBxA5JzYlH68kXVdk34= cloud.google.com/go/notebooks v1.4.0/go.mod h1:4QPMngcwmgb6uw7Po99B2xv5ufVoIQ7nOGDyL4P8AgA= @@ -522,20 +743,32 @@ cloud.google.com/go/notebooks v1.7.0/go.mod h1:PVlaDGfJgj1fl1S3dUwhFMXFgfYGhYQt2 cloud.google.com/go/notebooks v1.8.0/go.mod h1:Lq6dYKOYOWUCTvw5t2q1gp1lAp0zxAxRycayS0iJcqQ= cloud.google.com/go/notebooks v1.9.1/go.mod h1:zqG9/gk05JrzgBt4ghLzEepPHNwE5jgPcHZRKhlC1A8= cloud.google.com/go/notebooks v1.10.0/go.mod h1:SOPYMZnttHxqot0SGSFSkRrwE29eqnKPBJFqgWmiK2k= +cloud.google.com/go/notebooks v1.10.1/go.mod h1:5PdJc2SgAybE76kFQCWrTfJolCOUQXF97e+gteUUA6A= +cloud.google.com/go/notebooks v1.11.1/go.mod h1:V2Zkv8wX9kDCGRJqYoI+bQAaoVeE5kSiz4yYHd2yJwQ= +cloud.google.com/go/notebooks v1.11.2/go.mod h1:z0tlHI/lREXC8BS2mIsUeR3agM1AkgLiS+Isov3SS70= cloud.google.com/go/optimization v1.1.0/go.mod h1:5po+wfvX5AQlPznyVEZjGJTMr4+CAkJf2XSTQOOl9l4= cloud.google.com/go/optimization v1.2.0/go.mod h1:Lr7SOHdRDENsh+WXVmQhQTrzdu9ybg0NecjHidBq6xs= cloud.google.com/go/optimization v1.3.1/go.mod h1:IvUSefKiwd1a5p0RgHDbWCIbDFgKuEdB+fPPuP0IDLI= cloud.google.com/go/optimization v1.4.1/go.mod h1:j64vZQP7h9bO49m2rVaTVoNM0vEBEN5eKPUPbZyXOrk= cloud.google.com/go/optimization v1.5.0/go.mod h1:evo1OvTxeBRBu6ydPlrIRizKY/LJKo/drDMMRKqGEUU= +cloud.google.com/go/optimization v1.5.1/go.mod h1:NC0gnUD5MWVAF7XLdoYVPmYYVth93Q6BUzqAq3ZwtV8= +cloud.google.com/go/optimization v1.6.1/go.mod h1:hH2RYPTTM9e9zOiTaYPTiGPcGdNZVnBSBxjIAJzUkqo= +cloud.google.com/go/optimization v1.6.2/go.mod h1:mWNZ7B9/EyMCcwNl1frUGEuY6CPijSkz88Fz2vwKPOY= cloud.google.com/go/orchestration v1.3.0/go.mod h1:Sj5tq/JpWiB//X/q3Ngwdl5K7B7Y0KZ7bfv0wL6fqVA= cloud.google.com/go/orchestration v1.4.0/go.mod h1:6W5NLFWs2TlniBphAViZEVhrXRSMgUGDfW7vrWKvsBk= cloud.google.com/go/orchestration v1.6.0/go.mod h1:M62Bevp7pkxStDfFfTuCOaXgaaqRAga1yKyoMtEoWPQ= cloud.google.com/go/orchestration v1.8.1/go.mod h1:4sluRF3wgbYVRqz7zJ1/EUNc90TTprliq9477fGobD8= +cloud.google.com/go/orchestration v1.8.2/go.mod h1:T1cP+6WyTmh6LSZzeUhvGf0uZVmJyTx7t8z7Vg87+A0= +cloud.google.com/go/orchestration v1.8.3/go.mod h1:xhgWAYqlbYjlz2ftbFghdyqENYW+JXuhBx9KsjMoGHs= +cloud.google.com/go/orchestration v1.8.4/go.mod h1:d0lywZSVYtIoSZXb0iFjv9SaL13PGyVOKDxqGxEf/qI= cloud.google.com/go/orgpolicy v1.4.0/go.mod h1:xrSLIV4RePWmP9P3tBl8S93lTmlAxjm06NSm2UTmKvE= cloud.google.com/go/orgpolicy v1.5.0/go.mod h1:hZEc5q3wzwXJaKrsx5+Ewg0u1LxJ51nNFlext7Tanwc= cloud.google.com/go/orgpolicy v1.10.0/go.mod h1:w1fo8b7rRqlXlIJbVhOMPrwVljyuW5mqssvBtU18ONc= cloud.google.com/go/orgpolicy v1.11.0/go.mod h1:2RK748+FtVvnfuynxBzdnyu7sygtoZa1za/0ZfpOs1M= cloud.google.com/go/orgpolicy v1.11.1/go.mod h1:8+E3jQcpZJQliP+zaFfayC2Pg5bmhuLK755wKhIIUCE= +cloud.google.com/go/orgpolicy v1.11.2/go.mod h1:biRDpNwfyytYnmCRWZWxrKF22Nkz9eNVj9zyaBdpm1o= +cloud.google.com/go/orgpolicy v1.11.3/go.mod h1:oKAtJ/gkMjum5icv2aujkP4CxROxPXsBbYGCDbPO8MM= +cloud.google.com/go/orgpolicy v1.11.4/go.mod h1:0+aNV/nrfoTQ4Mytv+Aw+stBDBjNf4d8fYRA9herfJI= cloud.google.com/go/osconfig v1.7.0/go.mod h1:oVHeCeZELfJP7XLxcBGTMBvRO+1nQ5tFG9VQTmYS2Fs= cloud.google.com/go/osconfig v1.8.0/go.mod h1:EQqZLu5w5XA7eKizepumcvWx+m8mJUhEwiPqWiZeEdg= cloud.google.com/go/osconfig v1.9.0/go.mod h1:Yx+IeIZJ3bdWmzbQU4fxNl8xsZ4amB+dygAwFPlvnNo= @@ -543,16 +776,26 @@ cloud.google.com/go/osconfig v1.10.0/go.mod h1:uMhCzqC5I8zfD9zDEAfvgVhDS8oIjySWh cloud.google.com/go/osconfig v1.11.0/go.mod h1:aDICxrur2ogRd9zY5ytBLV89KEgT2MKB2L/n6x1ooPw= cloud.google.com/go/osconfig v1.12.0/go.mod h1:8f/PaYzoS3JMVfdfTubkowZYGmAhUCjjwnjqWI7NVBc= cloud.google.com/go/osconfig v1.12.1/go.mod h1:4CjBxND0gswz2gfYRCUoUzCm9zCABp91EeTtWXyz0tE= +cloud.google.com/go/osconfig v1.12.2/go.mod h1:eh9GPaMZpI6mEJEuhEjUJmaxvQ3gav+fFEJon1Y8Iw0= +cloud.google.com/go/osconfig v1.12.3/go.mod h1:L/fPS8LL6bEYUi1au832WtMnPeQNT94Zo3FwwV1/xGM= +cloud.google.com/go/osconfig v1.12.4/go.mod h1:B1qEwJ/jzqSRslvdOCI8Kdnp0gSng0xW4LOnIebQomA= cloud.google.com/go/oslogin v1.4.0/go.mod h1:YdgMXWRaElXz/lDk1Na6Fh5orF7gvmJ0FGLIs9LId4E= cloud.google.com/go/oslogin v1.5.0/go.mod h1:D260Qj11W2qx/HVF29zBg+0fd6YCSjSqLUkY/qEenQU= cloud.google.com/go/oslogin v1.6.0/go.mod h1:zOJ1O3+dTU8WPlGEkFSh7qeHPPSoxrcMbbK1Nm2iX70= cloud.google.com/go/oslogin v1.7.0/go.mod h1:e04SN0xO1UNJ1M5GP0vzVBFicIe4O53FOfcixIqTyXo= cloud.google.com/go/oslogin v1.9.0/go.mod h1:HNavntnH8nzrn8JCTT5fj18FuJLFJc4NaZJtBnQtKFs= cloud.google.com/go/oslogin v1.10.1/go.mod h1:x692z7yAue5nE7CsSnoG0aaMbNoRJRXO4sn73R+ZqAs= +cloud.google.com/go/oslogin v1.11.0/go.mod h1:8GMTJs4X2nOAUVJiPGqIWVcDaF0eniEto3xlOxaboXE= +cloud.google.com/go/oslogin v1.11.1/go.mod h1:OhD2icArCVNUxKqtK0mcSmKL7lgr0LVlQz+v9s1ujTg= +cloud.google.com/go/oslogin v1.12.1/go.mod h1:VfwTeFJGbnakxAY236eN8fsnglLiVXndlbcNomY4iZU= +cloud.google.com/go/oslogin v1.12.2/go.mod h1:CQ3V8Jvw4Qo4WRhNPF0o+HAM4DiLuE27Ul9CX9g2QdY= cloud.google.com/go/phishingprotection v0.5.0/go.mod h1:Y3HZknsK9bc9dMi+oE8Bim0lczMU6hrX0UpADuMefr0= cloud.google.com/go/phishingprotection v0.6.0/go.mod h1:9Y3LBLgy0kDTcYET8ZH3bq/7qni15yVUoAxiFxnlSUA= cloud.google.com/go/phishingprotection v0.7.0/go.mod h1:8qJI4QKHoda/sb/7/YmMQ2omRLSLYSu9bU0EKCNI+Lk= cloud.google.com/go/phishingprotection v0.8.1/go.mod h1:AxonW7GovcA8qdEk13NfHq9hNx5KPtfxXNeUxTDxB6I= +cloud.google.com/go/phishingprotection v0.8.2/go.mod h1:LhJ91uyVHEYKSKcMGhOa14zMMWfbEdxG032oT6ECbC8= +cloud.google.com/go/phishingprotection v0.8.3/go.mod h1:3B01yO7T2Ra/TMojifn8EoGd4G9jts/6cIO0DgDY9J8= +cloud.google.com/go/phishingprotection v0.8.4/go.mod h1:6b3kNPAc2AQ6jZfFHioZKg9MQNybDg4ixFd4RPZZ2nE= cloud.google.com/go/policytroubleshooter v1.3.0/go.mod h1:qy0+VwANja+kKrjlQuOzmlvscn4RNsAc0e15GGqfMxg= cloud.google.com/go/policytroubleshooter v1.4.0/go.mod h1:DZT4BcRw3QoO8ota9xw/LKtPa8lKeCByYeKTIf/vxdE= cloud.google.com/go/policytroubleshooter v1.5.0/go.mod h1:Rz1WfV+1oIpPdN2VvvuboLVRsB1Hclg3CKQ53j9l8vw= @@ -560,11 +803,17 @@ cloud.google.com/go/policytroubleshooter v1.6.0/go.mod h1:zYqaPTsmfvpjm5ULxAyD/l cloud.google.com/go/policytroubleshooter v1.7.1/go.mod h1:0NaT5v3Ag1M7U5r0GfDCpUFkWd9YqpubBWsQlhanRv0= cloud.google.com/go/policytroubleshooter v1.8.0/go.mod h1:tmn5Ir5EToWe384EuboTcVQT7nTag2+DuH3uHmKd1HU= cloud.google.com/go/policytroubleshooter v1.9.0/go.mod h1:+E2Lga7TycpeSTj2FsH4oXxTnrbHJGRlKhVZBLGgU64= +cloud.google.com/go/policytroubleshooter v1.9.1/go.mod h1:MYI8i0bCrL8cW+VHN1PoiBTyNZTstCg2WUw2eVC4c4U= +cloud.google.com/go/policytroubleshooter v1.10.1/go.mod h1:5C0rhT3TDZVxAu8813bwmTvd57Phbl8mr9F4ipOsxEs= +cloud.google.com/go/policytroubleshooter v1.10.2/go.mod h1:m4uF3f6LseVEnMV6nknlN2vYGRb+75ylQwJdnOXfnv0= cloud.google.com/go/privatecatalog v0.5.0/go.mod h1:XgosMUvvPyxDjAVNDYxJ7wBW8//hLDDYmnsNcMGq1K0= cloud.google.com/go/privatecatalog v0.6.0/go.mod h1:i/fbkZR0hLN29eEWiiwue8Pb+GforiEIBnV9yrRUOKI= cloud.google.com/go/privatecatalog v0.7.0/go.mod h1:2s5ssIFO69F5csTXcwBP7NPFTZvps26xGzvQ2PQaBYg= cloud.google.com/go/privatecatalog v0.8.0/go.mod h1:nQ6pfaegeDAq/Q5lrfCQzQLhubPiZhSaNhIgfJlnIXs= cloud.google.com/go/privatecatalog v0.9.1/go.mod h1:0XlDXW2unJXdf9zFz968Hp35gl/bhF4twwpXZAW50JA= +cloud.google.com/go/privatecatalog v0.9.2/go.mod h1:RMA4ATa8IXfzvjrhhK8J6H4wwcztab+oZph3c6WmtFc= +cloud.google.com/go/privatecatalog v0.9.3/go.mod h1:K5pn2GrVmOPjXz3T26mzwXLcKivfIJ9R5N79AFCF9UE= +cloud.google.com/go/privatecatalog v0.9.4/go.mod h1:SOjm93f+5hp/U3PqMZAHTtBtluqLygrDrVO8X8tYtG0= cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= @@ -588,10 +837,17 @@ cloud.google.com/go/recaptchaenterprise/v2 v2.5.0/go.mod h1:O8LzcHXN3rz0j+LBC91j cloud.google.com/go/recaptchaenterprise/v2 v2.6.0/go.mod h1:RPauz9jeLtB3JVzg6nCbe12qNoaa8pXc4d/YukAmcnA= cloud.google.com/go/recaptchaenterprise/v2 v2.7.0/go.mod h1:19wVj/fs5RtYtynAPJdDTb69oW0vNHYDBTbB4NvMD9c= cloud.google.com/go/recaptchaenterprise/v2 v2.7.2/go.mod h1:kR0KjsJS7Jt1YSyWFkseQ756D45kaYNTlDPPaRAvDBU= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.0/go.mod h1:QuE8EdU9dEnesG8/kG3XuJyNsjEqMlMzg3v3scCJ46c= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.1/go.mod h1:JZYZJOeZjgSSTGP4uz7NlQ4/d1w5hGmksVgM0lbEij0= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.2/go.mod h1:kpaDBOpkwD4G0GVMzG1W6Doy1tFFC97XAV3xy+Rd/pw= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.3/go.mod h1:Dak54rw6lC2gBY8FBznpOCAR58wKf+R+ZSJRoeJok4w= cloud.google.com/go/recommendationengine v0.5.0/go.mod h1:E5756pJcVFeVgaQv3WNpImkFP8a+RptV6dDLGPILjvg= cloud.google.com/go/recommendationengine v0.6.0/go.mod h1:08mq2umu9oIqc7tDy8sx+MNJdLG0fUi3vaSVbztHgJ4= cloud.google.com/go/recommendationengine v0.7.0/go.mod h1:1reUcE3GIu6MeBz/h5xZJqNLuuVjNg1lmWMPyjatzac= cloud.google.com/go/recommendationengine v0.8.1/go.mod h1:MrZihWwtFYWDzE6Hz5nKcNz3gLizXVIDI/o3G1DLcrE= +cloud.google.com/go/recommendationengine v0.8.2/go.mod h1:QIybYHPK58qir9CV2ix/re/M//Ty10OxjnnhWdaKS1Y= +cloud.google.com/go/recommendationengine v0.8.3/go.mod h1:m3b0RZV02BnODE9FeSvGv1qibFo8g0OnmB/RMwYy4V8= +cloud.google.com/go/recommendationengine v0.8.4/go.mod h1:GEteCf1PATl5v5ZsQ60sTClUE0phbWmo3rQ1Js8louU= cloud.google.com/go/recommender v1.5.0/go.mod h1:jdoeiBIVrJe9gQjwd759ecLJbxCDED4A6p+mqoqDvTg= cloud.google.com/go/recommender v1.6.0/go.mod h1:+yETpm25mcoiECKh9DEScGzIRyDKpZ0cEhWGo+8bo+c= cloud.google.com/go/recommender v1.7.0/go.mod h1:XLHs/W+T8olwlGOgfQenXBTbIseGclClff6lhFVe9Bs= @@ -599,33 +855,52 @@ cloud.google.com/go/recommender v1.8.0/go.mod h1:PkjXrTT05BFKwxaUxQmtIlrtj0kph10 cloud.google.com/go/recommender v1.9.0/go.mod h1:PnSsnZY7q+VL1uax2JWkt/UegHssxjUVVCrX52CuEmQ= cloud.google.com/go/recommender v1.10.1/go.mod h1:XFvrE4Suqn5Cq0Lf+mCP6oBHD/yRMA8XxP5sb7Q7gpA= cloud.google.com/go/recommender v1.11.0/go.mod h1:kPiRQhPyTJ9kyXPCG6u/dlPLbYfFlkwHNRwdzPVAoII= +cloud.google.com/go/recommender v1.11.1/go.mod h1:sGwFFAyI57v2Hc5LbIj+lTwXipGu9NW015rkaEM5B18= +cloud.google.com/go/recommender v1.11.2/go.mod h1:AeoJuzOvFR/emIcXdVFkspVXVTYpliRCmKNYDnyBv6Y= +cloud.google.com/go/recommender v1.11.3/go.mod h1:+FJosKKJSId1MBFeJ/TTyoGQZiEelQQIZMKYYD8ruK4= cloud.google.com/go/redis v1.7.0/go.mod h1:V3x5Jq1jzUcg+UNsRvdmsfuFnit1cfe3Z/PGyq/lm4Y= cloud.google.com/go/redis v1.8.0/go.mod h1:Fm2szCDavWzBk2cDKxrkmWBqoCiL1+Ctwq7EyqBCA/A= cloud.google.com/go/redis v1.9.0/go.mod h1:HMYQuajvb2D0LvMgZmLDZW8V5aOC/WxstZHiy4g8OiA= cloud.google.com/go/redis v1.10.0/go.mod h1:ThJf3mMBQtW18JzGgh41/Wld6vnDDc/F/F35UolRZPM= cloud.google.com/go/redis v1.11.0/go.mod h1:/X6eicana+BWcUda5PpwZC48o37SiFVTFSs0fWAJ7uQ= cloud.google.com/go/redis v1.13.1/go.mod h1:VP7DGLpE91M6bcsDdMuyCm2hIpB6Vp2hI090Mfd1tcg= +cloud.google.com/go/redis v1.13.2/go.mod h1:0Hg7pCMXS9uz02q+LoEVl5dNHUkIQv+C/3L76fandSA= +cloud.google.com/go/redis v1.13.3/go.mod h1:vbUpCKUAZSYzFcWKmICnYgRAhTFg9r+djWqFxDYXi4U= +cloud.google.com/go/redis v1.14.1/go.mod h1:MbmBxN8bEnQI4doZPC1BzADU4HGocHBk2de3SbgOkqs= cloud.google.com/go/resourcemanager v1.3.0/go.mod h1:bAtrTjZQFJkiWTPDb1WBjzvc6/kifjj4QBYuKCCoqKA= cloud.google.com/go/resourcemanager v1.4.0/go.mod h1:MwxuzkumyTX7/a3n37gmsT3py7LIXwrShilPh3P1tR0= cloud.google.com/go/resourcemanager v1.5.0/go.mod h1:eQoXNAiAvCf5PXxWxXjhKQoTMaUSNrEfg+6qdf/wots= cloud.google.com/go/resourcemanager v1.6.0/go.mod h1:YcpXGRs8fDzcUl1Xw8uOVmI8JEadvhRIkoXXUNVYcVo= cloud.google.com/go/resourcemanager v1.7.0/go.mod h1:HlD3m6+bwhzj9XCouqmeiGuni95NTrExfhoSrkC/3EI= cloud.google.com/go/resourcemanager v1.9.1/go.mod h1:dVCuosgrh1tINZ/RwBufr8lULmWGOkPS8gL5gqyjdT8= +cloud.google.com/go/resourcemanager v1.9.2/go.mod h1:OujkBg1UZg5lX2yIyMo5Vz9O5hf7XQOSV7WxqxxMtQE= +cloud.google.com/go/resourcemanager v1.9.3/go.mod h1:IqrY+g0ZgLsihcfcmqSe+RKp1hzjXwG904B92AwBz6U= +cloud.google.com/go/resourcemanager v1.9.4/go.mod h1:N1dhP9RFvo3lUfwtfLWVxfUWq8+KUQ+XLlHLH3BoFJ0= cloud.google.com/go/resourcesettings v1.3.0/go.mod h1:lzew8VfESA5DQ8gdlHwMrqZs1S9V87v3oCnKCWoOuQU= cloud.google.com/go/resourcesettings v1.4.0/go.mod h1:ldiH9IJpcrlC3VSuCGvjR5of/ezRrOxFtpJoJo5SmXg= cloud.google.com/go/resourcesettings v1.5.0/go.mod h1:+xJF7QSG6undsQDfsCJyqWXyBwUoJLhetkRMDRnIoXA= cloud.google.com/go/resourcesettings v1.6.1/go.mod h1:M7mk9PIZrC5Fgsu1kZJci6mpgN8o0IUzVx3eJU3y4Jw= +cloud.google.com/go/resourcesettings v1.6.2/go.mod h1:mJIEDd9MobzunWMeniaMp6tzg4I2GvD3TTmPkc8vBXk= +cloud.google.com/go/resourcesettings v1.6.3/go.mod h1:pno5D+7oDYkMWZ5BpPsb4SO0ewg3IXcmmrUZaMJrFic= +cloud.google.com/go/resourcesettings v1.6.4/go.mod h1:pYTTkWdv2lmQcjsthbZLNBP4QW140cs7wqA3DuqErVI= cloud.google.com/go/retail v1.8.0/go.mod h1:QblKS8waDmNUhghY2TI9O3JLlFk8jybHeV4BF19FrE4= cloud.google.com/go/retail v1.9.0/go.mod h1:g6jb6mKuCS1QKnH/dpu7isX253absFl6iE92nHwlBUY= cloud.google.com/go/retail v1.10.0/go.mod h1:2gDk9HsL4HMS4oZwz6daui2/jmKvqShXKQuB2RZ+cCc= cloud.google.com/go/retail v1.11.0/go.mod h1:MBLk1NaWPmh6iVFSz9MeKG/Psyd7TAgm6y/9L2B4x9Y= cloud.google.com/go/retail v1.12.0/go.mod h1:UMkelN/0Z8XvKymXFbD4EhFJlYKRx1FGhQkVPU5kF14= cloud.google.com/go/retail v1.14.1/go.mod h1:y3Wv3Vr2k54dLNIrCzenyKG8g8dhvhncT2NcNjb/6gE= +cloud.google.com/go/retail v1.14.2/go.mod h1:W7rrNRChAEChX336QF7bnMxbsjugcOCPU44i5kbLiL8= +cloud.google.com/go/retail v1.14.3/go.mod h1:Omz2akDHeSlfCq8ArPKiBxlnRpKEBjUH386JYFLUvXo= +cloud.google.com/go/retail v1.14.4/go.mod h1:l/N7cMtY78yRnJqp5JW8emy7MB1nz8E4t2yfOmklYfg= cloud.google.com/go/run v0.2.0/go.mod h1:CNtKsTA1sDcnqqIFR3Pb5Tq0usWxJJvsWOCPldRU3Do= cloud.google.com/go/run v0.3.0/go.mod h1:TuyY1+taHxTjrD0ZFk2iAR+xyOXEA0ztb7U3UNA0zBo= cloud.google.com/go/run v0.8.0/go.mod h1:VniEnuBwqjigv0A7ONfQUaEItaiCRVujlMqerPPiktM= cloud.google.com/go/run v0.9.0/go.mod h1:Wwu+/vvg8Y+JUApMwEDfVfhetv30hCG4ZwDR/IXl2Qg= cloud.google.com/go/run v1.2.0/go.mod h1:36V1IlDzQ0XxbQjUx6IYbw8H3TJnWvhii963WW3B/bo= +cloud.google.com/go/run v1.3.0/go.mod h1:S/osX/4jIPZGg+ssuqh6GNgg7syixKe3YnprwehzHKU= +cloud.google.com/go/run v1.3.1/go.mod h1:cymddtZOzdwLIAsmS6s+Asl4JoXIDm/K1cpZTxV4Q5s= +cloud.google.com/go/run v1.3.2/go.mod h1:SIhmqArbjdU/D9M6JoHaAqnAMKLFtXaVdNeq04NjnVE= +cloud.google.com/go/run v1.3.3/go.mod h1:WSM5pGyJ7cfYyYbONVQBN4buz42zFqwG67Q3ch07iK4= cloud.google.com/go/scheduler v1.4.0/go.mod h1:drcJBmxF3aqZJRhmkHQ9b3uSSpQoltBPGPxGAWROx6s= cloud.google.com/go/scheduler v1.5.0/go.mod h1:ri073ym49NW3AfT6DZi21vLZrG07GXr5p3H1KxN5QlI= cloud.google.com/go/scheduler v1.6.0/go.mod h1:SgeKVM7MIwPn3BqtcBntpLyrIJftQISRrYB5ZtT+KOk= @@ -633,11 +908,17 @@ cloud.google.com/go/scheduler v1.7.0/go.mod h1:jyCiBqWW956uBjjPMMuX09n3x37mtyPJe cloud.google.com/go/scheduler v1.8.0/go.mod h1:TCET+Y5Gp1YgHT8py4nlg2Sew8nUHMqcpousDgXJVQc= cloud.google.com/go/scheduler v1.9.0/go.mod h1:yexg5t+KSmqu+njTIh3b7oYPheFtBWGcbVUYF1GGMIc= cloud.google.com/go/scheduler v1.10.1/go.mod h1:R63Ldltd47Bs4gnhQkmNDse5w8gBRrhObZ54PxgR2Oo= +cloud.google.com/go/scheduler v1.10.2/go.mod h1:O3jX6HRH5eKCA3FutMw375XHZJudNIKVonSCHv7ropY= +cloud.google.com/go/scheduler v1.10.3/go.mod h1:8ANskEM33+sIbpJ+R4xRfw/jzOG+ZFE8WVLy7/yGvbc= +cloud.google.com/go/scheduler v1.10.4/go.mod h1:MTuXcrJC9tqOHhixdbHDFSIuh7xZF2IysiINDuiq6NI= cloud.google.com/go/secretmanager v1.6.0/go.mod h1:awVa/OXF6IiyaU1wQ34inzQNc4ISIDIrId8qE5QGgKA= cloud.google.com/go/secretmanager v1.8.0/go.mod h1:hnVgi/bN5MYHd3Gt0SPuTPPp5ENina1/LxM+2W9U9J4= cloud.google.com/go/secretmanager v1.9.0/go.mod h1:b71qH2l1yHmWQHt9LC80akm86mX8AL6X1MA01dW8ht4= cloud.google.com/go/secretmanager v1.10.0/go.mod h1:MfnrdvKMPNra9aZtQFvBcvRU54hbPD8/HayQdlUgJpU= cloud.google.com/go/secretmanager v1.11.1/go.mod h1:znq9JlXgTNdBeQk9TBW/FnR/W4uChEKGeqQWAJ8SXFw= +cloud.google.com/go/secretmanager v1.11.2/go.mod h1:MQm4t3deoSub7+WNwiC4/tRYgDBHJgJPvswqQVB1Vss= +cloud.google.com/go/secretmanager v1.11.3/go.mod h1:0bA2o6FabmShrEy328i67aV+65XoUFFSmVeLBn/51jI= +cloud.google.com/go/secretmanager v1.11.4/go.mod h1:wreJlbS9Zdq21lMzWmJ0XhWW2ZxgPeahsqeV/vZoJ3w= cloud.google.com/go/security v1.5.0/go.mod h1:lgxGdyOKKjHL4YG3/YwIL2zLqMFCKs0UbQwgyZmfJl4= cloud.google.com/go/security v1.7.0/go.mod h1:mZklORHl6Bg7CNnnjLH//0UlAlaXqiG7Lb9PsPXLfD0= cloud.google.com/go/security v1.8.0/go.mod h1:hAQOwgmaHhztFhiQ41CjDODdWP0+AE1B3sX4OFlq+GU= @@ -646,6 +927,9 @@ cloud.google.com/go/security v1.10.0/go.mod h1:QtOMZByJVlibUT2h9afNDWRZ1G96gVywH cloud.google.com/go/security v1.12.0/go.mod h1:rV6EhrpbNHrrxqlvW0BWAIawFWq3X90SduMJdFwtLB8= cloud.google.com/go/security v1.13.0/go.mod h1:Q1Nvxl1PAgmeW0y3HTt54JYIvUdtcpYKVfIB8AOMZ+0= cloud.google.com/go/security v1.15.1/go.mod h1:MvTnnbsWnehoizHi09zoiZob0iCHVcL4AUBj76h9fXA= +cloud.google.com/go/security v1.15.2/go.mod h1:2GVE/v1oixIRHDaClVbHuPcZwAqFM28mXuAKCfMgYIg= +cloud.google.com/go/security v1.15.3/go.mod h1:gQ/7Q2JYUZZgOzqKtw9McShH+MjNvtDpL40J1cT+vBs= +cloud.google.com/go/security v1.15.4/go.mod h1:oN7C2uIZKhxCLiAAijKUCuHLZbIt/ghYEo8MqwD/Ty4= cloud.google.com/go/securitycenter v1.13.0/go.mod h1:cv5qNAqjY84FCN6Y9z28WlkKXyWsgLO832YiWwkCWcU= cloud.google.com/go/securitycenter v1.14.0/go.mod h1:gZLAhtyKv85n52XYWt6RmeBdydyxfPeTrpToDPw4Auc= cloud.google.com/go/securitycenter v1.15.0/go.mod h1:PeKJ0t8MoFmmXLXWm41JidyzI3PJjd8sXWaVqg43WWk= @@ -653,6 +937,9 @@ cloud.google.com/go/securitycenter v1.16.0/go.mod h1:Q9GMaLQFUD+5ZTabrbujNWLtSLZ cloud.google.com/go/securitycenter v1.18.1/go.mod h1:0/25gAzCM/9OL9vVx4ChPeM/+DlfGQJDwBy/UC8AKK0= cloud.google.com/go/securitycenter v1.19.0/go.mod h1:LVLmSg8ZkkyaNy4u7HCIshAngSQ8EcIRREP3xBnyfag= cloud.google.com/go/securitycenter v1.23.0/go.mod h1:8pwQ4n+Y9WCWM278R8W3nF65QtY172h4S8aXyI9/hsQ= +cloud.google.com/go/securitycenter v1.23.1/go.mod h1:w2HV3Mv/yKhbXKwOCu2i8bCuLtNP1IMHuiYQn4HJq5s= +cloud.google.com/go/securitycenter v1.24.1/go.mod h1:3h9IdjjHhVMXdQnmqzVnM7b0wMn/1O/U20eWVpMpZjI= +cloud.google.com/go/securitycenter v1.24.2/go.mod h1:l1XejOngggzqwr4Fa2Cn+iWZGf+aBLTXtB/vXjy5vXM= cloud.google.com/go/servicecontrol v1.4.0/go.mod h1:o0hUSJ1TXJAmi/7fLJAedOovnujSEvjKCAFNXPQ1RaU= cloud.google.com/go/servicecontrol v1.5.0/go.mod h1:qM0CnXHhyqKVuiZnGKrIurvVImCs8gmqWsDoqe9sU1s= cloud.google.com/go/servicecontrol v1.10.0/go.mod h1:pQvyvSRh7YzUF2efw7H87V92mxU8FnFDawMClGCNuAA= @@ -666,6 +953,9 @@ cloud.google.com/go/servicedirectory v1.8.0/go.mod h1:srXodfhY1GFIPvltunswqXpVxF cloud.google.com/go/servicedirectory v1.9.0/go.mod h1:29je5JjiygNYlmsGz8k6o+OZ8vd4f//bQLtvzkPPT/s= cloud.google.com/go/servicedirectory v1.10.1/go.mod h1:Xv0YVH8s4pVOwfM/1eMTl0XJ6bzIOSLDt8f8eLaGOxQ= cloud.google.com/go/servicedirectory v1.11.0/go.mod h1:Xv0YVH8s4pVOwfM/1eMTl0XJ6bzIOSLDt8f8eLaGOxQ= +cloud.google.com/go/servicedirectory v1.11.1/go.mod h1:tJywXimEWzNzw9FvtNjsQxxJ3/41jseeILgwU/QLrGI= +cloud.google.com/go/servicedirectory v1.11.2/go.mod h1:KD9hCLhncWRV5jJphwIpugKwM5bn1x0GyVVD4NO8mGg= +cloud.google.com/go/servicedirectory v1.11.3/go.mod h1:LV+cHkomRLr67YoQy3Xq2tUXBGOs5z5bPofdq7qtiAw= cloud.google.com/go/servicemanagement v1.4.0/go.mod h1:d8t8MDbezI7Z2R1O/wu8oTggo3BI2GKYbdG4y/SJTco= cloud.google.com/go/servicemanagement v1.5.0/go.mod h1:XGaCRe57kfqu4+lRxaFEAuqmjzF0r+gWHjWqKqBvKFo= cloud.google.com/go/servicemanagement v1.6.0/go.mod h1:aWns7EeeCOtGEX4OvZUWCCJONRZeFKiptqKf1D0l/Jc= @@ -678,11 +968,16 @@ cloud.google.com/go/shell v1.3.0/go.mod h1:VZ9HmRjZBsjLGXusm7K5Q5lzzByZmJHf1d0IW cloud.google.com/go/shell v1.4.0/go.mod h1:HDxPzZf3GkDdhExzD/gs8Grqk+dmYcEjGShZgYa9URw= cloud.google.com/go/shell v1.6.0/go.mod h1:oHO8QACS90luWgxP3N9iZVuEiSF84zNyLytb+qE2f9A= cloud.google.com/go/shell v1.7.1/go.mod h1:u1RaM+huXFaTojTbW4g9P5emOrrmLE69KrxqQahKn4g= +cloud.google.com/go/shell v1.7.2/go.mod h1:KqRPKwBV0UyLickMn0+BY1qIyE98kKyI216sH/TuHmc= +cloud.google.com/go/shell v1.7.3/go.mod h1:cTTEz/JdaBsQAeTQ3B6HHldZudFoYBOqjteev07FbIc= +cloud.google.com/go/shell v1.7.4/go.mod h1:yLeXB8eKLxw0dpEmXQ/FjriYrBijNsONpwnWsdPqlKM= cloud.google.com/go/spanner v1.41.0/go.mod h1:MLYDBJR/dY4Wt7ZaMIQ7rXOTLjYrmxLE/5ve9vFfWos= cloud.google.com/go/spanner v1.44.0/go.mod h1:G8XIgYdOK+Fbcpbs7p2fiprDw4CaZX63whnSMLVBxjk= cloud.google.com/go/spanner v1.45.0/go.mod h1:FIws5LowYz8YAE1J8fOS7DJup8ff7xJeetWEo5REA2M= cloud.google.com/go/spanner v1.47.0/go.mod h1:IXsJwVW2j4UKs0eYDqodab6HgGuA1bViSqW4uH9lfUI= cloud.google.com/go/spanner v1.49.0/go.mod h1:eGj9mQGK8+hkgSVbHNQ06pQ4oS+cyc4tXXd6Dif1KoM= +cloud.google.com/go/spanner v1.50.0/go.mod h1:eGj9mQGK8+hkgSVbHNQ06pQ4oS+cyc4tXXd6Dif1KoM= +cloud.google.com/go/spanner v1.51.0/go.mod h1:c5KNo5LQ1X5tJwma9rSQZsXNBDNvj4/n8BVc3LNahq0= cloud.google.com/go/speech v1.6.0/go.mod h1:79tcr4FHCimOp56lwC01xnt/WPJZc4v3gzyT7FoBkCM= cloud.google.com/go/speech v1.7.0/go.mod h1:KptqL+BAQIhMsj1kOP2la5DSEEerPDuOP/2mmkhHhZQ= cloud.google.com/go/speech v1.8.0/go.mod h1:9bYIl1/tjsAnMgKGHKmBZzXKEkGgtU+MpdDPTE9f7y0= @@ -691,6 +986,9 @@ cloud.google.com/go/speech v1.14.1/go.mod h1:gEosVRPJ9waG7zqqnsHpYTOoAS4KouMRLDF cloud.google.com/go/speech v1.15.0/go.mod h1:y6oH7GhqCaZANH7+Oe0BhgIogsNInLlz542tg3VqeYI= cloud.google.com/go/speech v1.17.1/go.mod h1:8rVNzU43tQvxDaGvqOhpDqgkJTFowBpDvCJ14kGlJYo= cloud.google.com/go/speech v1.19.0/go.mod h1:8rVNzU43tQvxDaGvqOhpDqgkJTFowBpDvCJ14kGlJYo= +cloud.google.com/go/speech v1.19.1/go.mod h1:WcuaWz/3hOlzPFOVo9DUsblMIHwxP589y6ZMtaG+iAA= +cloud.google.com/go/speech v1.19.2/go.mod h1:2OYFfj+Ch5LWjsaSINuCZsre/789zlcCI3SY4oAi2oI= +cloud.google.com/go/speech v1.20.1/go.mod h1:wwolycgONvfz2EDU8rKuHRW3+wc9ILPsAWoikBEWavY= cloud.google.com/go/storage v1.0.0/go.mod h1:IhtSnM/ZTZV8YYJWCY8RULGVqBDmpoyjwiyrjsg+URw= cloud.google.com/go/storage v1.5.0/go.mod h1:tpKbwo567HUNpVclU5sGELwQWBDZ8gh0ZeosJ0Rtdos= cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk= @@ -708,25 +1006,40 @@ cloud.google.com/go/storagetransfer v1.6.0/go.mod h1:y77xm4CQV/ZhFZH75PLEXY0ROiS cloud.google.com/go/storagetransfer v1.7.0/go.mod h1:8Giuj1QNb1kfLAiWM1bN6dHzfdlDAVC9rv9abHot2W4= cloud.google.com/go/storagetransfer v1.8.0/go.mod h1:JpegsHHU1eXg7lMHkvf+KE5XDJ7EQu0GwNJbbVGanEw= cloud.google.com/go/storagetransfer v1.10.0/go.mod h1:DM4sTlSmGiNczmV6iZyceIh2dbs+7z2Ayg6YAiQlYfA= +cloud.google.com/go/storagetransfer v1.10.1/go.mod h1:rS7Sy0BtPviWYTTJVWCSV4QrbBitgPeuK4/FKa4IdLs= +cloud.google.com/go/storagetransfer v1.10.2/go.mod h1:meIhYQup5rg9juQJdyppnA/WLQCOguxtk1pr3/vBWzA= +cloud.google.com/go/storagetransfer v1.10.3/go.mod h1:Up8LY2p6X68SZ+WToswpQbQHnJpOty/ACcMafuey8gc= cloud.google.com/go/talent v1.1.0/go.mod h1:Vl4pt9jiHKvOgF9KoZo6Kob9oV4lwd/ZD5Cto54zDRw= cloud.google.com/go/talent v1.2.0/go.mod h1:MoNF9bhFQbiJ6eFD3uSsg0uBALw4n4gaCaEjBw9zo8g= cloud.google.com/go/talent v1.3.0/go.mod h1:CmcxwJ/PKfRgd1pBjQgU6W3YBwiewmUzQYH5HHmSCmM= cloud.google.com/go/talent v1.4.0/go.mod h1:ezFtAgVuRf8jRsvyE6EwmbTK5LKciD4KVnHuDEFmOOA= cloud.google.com/go/talent v1.5.0/go.mod h1:G+ODMj9bsasAEJkQSzO2uHQWXHHXUomArjWQQYkqK6c= cloud.google.com/go/talent v1.6.2/go.mod h1:CbGvmKCG61mkdjcqTcLOkb2ZN1SrQI8MDyma2l7VD24= +cloud.google.com/go/talent v1.6.3/go.mod h1:xoDO97Qd4AK43rGjJvyBHMskiEf3KulgYzcH6YWOVoo= +cloud.google.com/go/talent v1.6.4/go.mod h1:QsWvi5eKeh6gG2DlBkpMaFYZYrYUnIpo34f6/V5QykY= +cloud.google.com/go/talent v1.6.5/go.mod h1:Mf5cma696HmE+P2BWJ/ZwYqeJXEeU0UqjHFXVLadEDI= cloud.google.com/go/texttospeech v1.4.0/go.mod h1:FX8HQHA6sEpJ7rCMSfXuzBcysDAuWusNNNvN9FELDd8= cloud.google.com/go/texttospeech v1.5.0/go.mod h1:oKPLhR4n4ZdQqWKURdwxMy0uiTS1xU161C8W57Wkea4= cloud.google.com/go/texttospeech v1.6.0/go.mod h1:YmwmFT8pj1aBblQOI3TfKmwibnsfvhIBzPXcW4EBovc= cloud.google.com/go/texttospeech v1.7.1/go.mod h1:m7QfG5IXxeneGqTapXNxv2ItxP/FS0hCZBwXYqucgSk= +cloud.google.com/go/texttospeech v1.7.2/go.mod h1:VYPT6aTOEl3herQjFHYErTlSZJ4vB00Q2ZTmuVgluD4= +cloud.google.com/go/texttospeech v1.7.3/go.mod h1:Av/zpkcgWfXlDLRYob17lqMstGZ3GqlvJXqKMp2u8so= +cloud.google.com/go/texttospeech v1.7.4/go.mod h1:vgv0002WvR4liGuSd5BJbWy4nDn5Ozco0uJymY5+U74= cloud.google.com/go/tpu v1.3.0/go.mod h1:aJIManG0o20tfDQlRIej44FcwGGl/cD0oiRyMKG19IQ= cloud.google.com/go/tpu v1.4.0/go.mod h1:mjZaX8p0VBgllCzF6wcU2ovUXN9TONFLd7iz227X2Xg= cloud.google.com/go/tpu v1.5.0/go.mod h1:8zVo1rYDFuW2l4yZVY0R0fb/v44xLh3llq7RuV61fPM= cloud.google.com/go/tpu v1.6.1/go.mod h1:sOdcHVIgDEEOKuqUoi6Fq53MKHJAtOwtz0GuKsWSH3E= +cloud.google.com/go/tpu v1.6.2/go.mod h1:NXh3NDwt71TsPZdtGWgAG5ThDfGd32X1mJ2cMaRlVgU= +cloud.google.com/go/tpu v1.6.3/go.mod h1:lxiueqfVMlSToZY1151IaZqp89ELPSrk+3HIQ5HRkbY= +cloud.google.com/go/tpu v1.6.4/go.mod h1:NAm9q3Rq2wIlGnOhpYICNI7+bpBebMJbh0yyp3aNw1Y= cloud.google.com/go/trace v1.3.0/go.mod h1:FFUE83d9Ca57C+K8rDl/Ih8LwOzWIV1krKgxg6N0G28= cloud.google.com/go/trace v1.4.0/go.mod h1:UG0v8UBqzusp+z63o7FK74SdFE+AXpCLdFb1rshXG+Y= cloud.google.com/go/trace v1.8.0/go.mod h1:zH7vcsbAhklH8hWFig58HvxcxyQbaIqMarMg9hn5ECA= cloud.google.com/go/trace v1.9.0/go.mod h1:lOQqpE5IaWY0Ixg7/r2SjixMuc6lfTFeO4QGM4dQWOk= cloud.google.com/go/trace v1.10.1/go.mod h1:gbtL94KE5AJLH3y+WVpfWILmqgc6dXcqgNXdOPAQTYk= +cloud.google.com/go/trace v1.10.2/go.mod h1:NPXemMi6MToRFcSxRl2uDnu/qAlAQ3oULUphcHGh1vA= +cloud.google.com/go/trace v1.10.3/go.mod h1:Ke1bgfc73RV3wUFml+uQp7EsDw4dGaETLxB7Iq/r4CY= +cloud.google.com/go/trace v1.10.4/go.mod h1:Nso99EDIK8Mj5/zmB+iGr9dosS/bzWCJ8wGmE6TXNWY= cloud.google.com/go/translate v1.3.0/go.mod h1:gzMUwRjvOqj5i69y/LYLd8RrNQk+hOmIXTi9+nb3Djs= cloud.google.com/go/translate v1.4.0/go.mod h1:06Dn/ppvLD6WvA5Rhdp029IX2Mi3Mn7fpMRLPvXT5Wg= cloud.google.com/go/translate v1.5.0/go.mod h1:29YDSYveqqpA1CQFD7NQuP49xymq17RXNaUDdc0mNu0= @@ -735,6 +1048,9 @@ cloud.google.com/go/translate v1.7.0/go.mod h1:lMGRudH1pu7I3n3PETiOB2507gf3HnfLV cloud.google.com/go/translate v1.8.1/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= cloud.google.com/go/translate v1.8.2/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= cloud.google.com/go/translate v1.9.0/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= +cloud.google.com/go/translate v1.9.1/go.mod h1:TWIgDZknq2+JD4iRcojgeDtqGEp154HN/uL6hMvylS8= +cloud.google.com/go/translate v1.9.2/go.mod h1:E3Tc6rUTsQkVrXW6avbUhKJSr7ZE3j7zNmqzXKHqRrY= +cloud.google.com/go/translate v1.9.3/go.mod h1:Kbq9RggWsbqZ9W5YpM94Q1Xv4dshw/gr/SHfsl5yCZ0= cloud.google.com/go/video v1.8.0/go.mod h1:sTzKFc0bUSByE8Yoh8X0mn8bMymItVGPfTuUBUyRgxk= cloud.google.com/go/video v1.9.0/go.mod h1:0RhNKFRF5v92f8dQt0yhaHrEuH95m068JYOvLZYnJSw= cloud.google.com/go/video v1.12.0/go.mod h1:MLQew95eTuaNDEGriQdcYn0dTwf9oWiA4uYebxM5kdg= @@ -744,12 +1060,18 @@ cloud.google.com/go/video v1.15.0/go.mod h1:SkgaXwT+lIIAKqWAJfktHT/RbgjSuY6DobxE cloud.google.com/go/video v1.17.1/go.mod h1:9qmqPqw/Ib2tLqaeHgtakU+l5TcJxCJbhFXM7UJjVzU= cloud.google.com/go/video v1.19.0/go.mod h1:9qmqPqw/Ib2tLqaeHgtakU+l5TcJxCJbhFXM7UJjVzU= cloud.google.com/go/video v1.20.0/go.mod h1:U3G3FTnsvAGqglq9LxgqzOiBc/Nt8zis8S+850N2DUM= +cloud.google.com/go/video v1.20.1/go.mod h1:3gJS+iDprnj8SY6pe0SwLeC5BUW80NjhwX7INWEuWGU= +cloud.google.com/go/video v1.20.2/go.mod h1:lrixr5JeKNThsgfM9gqtwb6Okuqzfo4VrY2xynaViTA= +cloud.google.com/go/video v1.20.3/go.mod h1:TnH/mNZKVHeNtpamsSPygSR0iHtvrR/cW1/GDjN5+GU= cloud.google.com/go/videointelligence v1.6.0/go.mod h1:w0DIDlVRKtwPCn/C4iwZIJdvC69yInhW0cfi+p546uU= cloud.google.com/go/videointelligence v1.7.0/go.mod h1:k8pI/1wAhjznARtVT9U1llUaFNPh7muw8QyOUpavru4= cloud.google.com/go/videointelligence v1.8.0/go.mod h1:dIcCn4gVDdS7yte/w+koiXn5dWVplOZkE+xwG9FgK+M= cloud.google.com/go/videointelligence v1.9.0/go.mod h1:29lVRMPDYHikk3v8EdPSaL8Ku+eMzDljjuvRs105XoU= cloud.google.com/go/videointelligence v1.10.0/go.mod h1:LHZngX1liVtUhZvi2uNS0VQuOzNi2TkY1OakiuoUOjU= cloud.google.com/go/videointelligence v1.11.1/go.mod h1:76xn/8InyQHarjTWsBR058SmlPCwQjgcvoW0aZykOvo= +cloud.google.com/go/videointelligence v1.11.2/go.mod h1:ocfIGYtIVmIcWk1DsSGOoDiXca4vaZQII1C85qtoplc= +cloud.google.com/go/videointelligence v1.11.3/go.mod h1:tf0NUaGTjU1iS2KEkGWvO5hRHeCkFK3nPo0/cOZhZAo= +cloud.google.com/go/videointelligence v1.11.4/go.mod h1:kPBMAYsTPFiQxMLmmjpcZUMklJp3nC9+ipJJtprccD8= cloud.google.com/go/vision v1.2.0/go.mod h1:SmNwgObm5DpFBme2xpyOyasvBc1aPdjvMk2bBk0tKD0= cloud.google.com/go/vision/v2 v2.2.0/go.mod h1:uCdV4PpN1S0jyCyq8sIM42v2Y6zOLkZs+4R9LrGYwFo= cloud.google.com/go/vision/v2 v2.3.0/go.mod h1:UO61abBx9QRMFkNBbf1D8B1LXdS2cGiiCRx0vSpZoUo= @@ -758,30 +1080,48 @@ cloud.google.com/go/vision/v2 v2.5.0/go.mod h1:MmaezXOOE+IWa+cS7OhRRLK2cNv1ZL98z cloud.google.com/go/vision/v2 v2.6.0/go.mod h1:158Hes0MvOS9Z/bDMSFpjwsUrZ5fPrdwuyyvKSGAGMY= cloud.google.com/go/vision/v2 v2.7.0/go.mod h1:H89VysHy21avemp6xcf9b9JvZHVehWbET0uT/bcuY/0= cloud.google.com/go/vision/v2 v2.7.2/go.mod h1:jKa8oSYBWhYiXarHPvP4USxYANYUEdEsQrloLjrSwJU= +cloud.google.com/go/vision/v2 v2.7.3/go.mod h1:V0IcLCY7W+hpMKXK1JYE0LV5llEqVmj+UJChjvA1WsM= +cloud.google.com/go/vision/v2 v2.7.4/go.mod h1:ynDKnsDN/0RtqkKxQZ2iatv3Dm9O+HfRb5djl7l4Vvw= +cloud.google.com/go/vision/v2 v2.7.5/go.mod h1:GcviprJLFfK9OLf0z8Gm6lQb6ZFUulvpZws+mm6yPLM= cloud.google.com/go/vmmigration v1.2.0/go.mod h1:IRf0o7myyWFSmVR1ItrBSFLFD/rJkfDCUTO4vLlJvsE= cloud.google.com/go/vmmigration v1.3.0/go.mod h1:oGJ6ZgGPQOFdjHuocGcLqX4lc98YQ7Ygq8YQwHh9A7g= cloud.google.com/go/vmmigration v1.5.0/go.mod h1:E4YQ8q7/4W9gobHjQg4JJSgXXSgY21nA5r8swQV+Xxc= cloud.google.com/go/vmmigration v1.6.0/go.mod h1:bopQ/g4z+8qXzichC7GW1w2MjbErL54rk3/C843CjfY= cloud.google.com/go/vmmigration v1.7.1/go.mod h1:WD+5z7a/IpZ5bKK//YmT9E047AD+rjycCAvyMxGJbro= +cloud.google.com/go/vmmigration v1.7.2/go.mod h1:iA2hVj22sm2LLYXGPT1pB63mXHhrH1m/ruux9TwWLd8= +cloud.google.com/go/vmmigration v1.7.3/go.mod h1:ZCQC7cENwmSWlwyTrZcWivchn78YnFniEQYRWQ65tBo= +cloud.google.com/go/vmmigration v1.7.4/go.mod h1:yBXCmiLaB99hEl/G9ZooNx2GyzgsjKnw5fWcINRgD70= cloud.google.com/go/vmwareengine v0.1.0/go.mod h1:RsdNEf/8UDvKllXhMz5J40XxDrNJNN4sagiox+OI208= cloud.google.com/go/vmwareengine v0.2.2/go.mod h1:sKdctNJxb3KLZkE/6Oui94iw/xs9PRNC2wnNLXsHvH8= cloud.google.com/go/vmwareengine v0.3.0/go.mod h1:wvoyMvNWdIzxMYSpH/R7y2h5h3WFkx6d+1TIsP39WGY= cloud.google.com/go/vmwareengine v0.4.1/go.mod h1:Px64x+BvjPZwWuc4HdmVhoygcXqEkGHXoa7uyfTgSI0= cloud.google.com/go/vmwareengine v1.0.0/go.mod h1:Px64x+BvjPZwWuc4HdmVhoygcXqEkGHXoa7uyfTgSI0= +cloud.google.com/go/vmwareengine v1.0.1/go.mod h1:aT3Xsm5sNx0QShk1Jc1B8OddrxAScYLwzVoaiXfdzzk= +cloud.google.com/go/vmwareengine v1.0.2/go.mod h1:xMSNjIk8/itYrz1JA8nV3Ajg4L4n3N+ugP8JKzk3OaA= +cloud.google.com/go/vmwareengine v1.0.3/go.mod h1:QSpdZ1stlbfKtyt6Iu19M6XRxjmXO+vb5a/R6Fvy2y4= cloud.google.com/go/vpcaccess v1.4.0/go.mod h1:aQHVbTWDYUR1EbTApSVvMq1EnT57ppDmQzZ3imqIk4w= cloud.google.com/go/vpcaccess v1.5.0/go.mod h1:drmg4HLk9NkZpGfCmZ3Tz0Bwnm2+DKqViEpeEpOq0m8= cloud.google.com/go/vpcaccess v1.6.0/go.mod h1:wX2ILaNhe7TlVa4vC5xce1bCnqE3AeH27RV31lnmZes= cloud.google.com/go/vpcaccess v1.7.1/go.mod h1:FogoD46/ZU+JUBX9D606X21EnxiszYi2tArQwLY4SXs= +cloud.google.com/go/vpcaccess v1.7.2/go.mod h1:mmg/MnRHv+3e8FJUjeSibVFvQF1cCy2MsFaFqxeY1HU= +cloud.google.com/go/vpcaccess v1.7.3/go.mod h1:YX4skyfW3NC8vI3Fk+EegJnlYFatA+dXK4o236EUCUc= +cloud.google.com/go/vpcaccess v1.7.4/go.mod h1:lA0KTvhtEOb/VOdnH/gwPuOzGgM+CWsmGu6bb4IoMKk= cloud.google.com/go/webrisk v1.4.0/go.mod h1:Hn8X6Zr+ziE2aNd8SliSDWpEnSS1u4R9+xXZmFiHmGE= cloud.google.com/go/webrisk v1.5.0/go.mod h1:iPG6fr52Tv7sGk0H6qUFzmL3HHZev1htXuWDEEsqMTg= cloud.google.com/go/webrisk v1.6.0/go.mod h1:65sW9V9rOosnc9ZY7A7jsy1zoHS5W9IAXv6dGqhMQMc= cloud.google.com/go/webrisk v1.7.0/go.mod h1:mVMHgEYH0r337nmt1JyLthzMr6YxwN1aAIEc2fTcq7A= cloud.google.com/go/webrisk v1.8.0/go.mod h1:oJPDuamzHXgUc+b8SiHRcVInZQuybnvEW72PqTc7sSg= cloud.google.com/go/webrisk v1.9.1/go.mod h1:4GCmXKcOa2BZcZPn6DCEvE7HypmEJcJkr4mtM+sqYPc= +cloud.google.com/go/webrisk v1.9.2/go.mod h1:pY9kfDgAqxUpDBOrG4w8deLfhvJmejKB0qd/5uQIPBc= +cloud.google.com/go/webrisk v1.9.3/go.mod h1:RUYXe9X/wBDXhVilss7EDLW9ZNa06aowPuinUOPCXH8= +cloud.google.com/go/webrisk v1.9.4/go.mod h1:w7m4Ib4C+OseSr2GL66m0zMBywdrVNTDKsdEsfMl7X0= cloud.google.com/go/websecurityscanner v1.3.0/go.mod h1:uImdKm2wyeXQevQJXeh8Uun/Ym1VqworNDlBXQevGMo= cloud.google.com/go/websecurityscanner v1.4.0/go.mod h1:ebit/Fp0a+FWu5j4JOmJEV8S8CzdTkAS77oDsiSqYWQ= cloud.google.com/go/websecurityscanner v1.5.0/go.mod h1:Y6xdCPy81yi0SQnDY1xdNTNpfY1oAgXUlcfN3B3eSng= cloud.google.com/go/websecurityscanner v1.6.1/go.mod h1:Njgaw3rttgRHXzwCB8kgCYqv5/rGpFCsBOvPbYgszpg= +cloud.google.com/go/websecurityscanner v1.6.2/go.mod h1:7YgjuU5tun7Eg2kpKgGnDuEOXWIrh8x8lWrJT4zfmas= +cloud.google.com/go/websecurityscanner v1.6.3/go.mod h1:x9XANObUFR+83Cya3g/B9M/yoHVqzxPnFtgF8yYGAXw= +cloud.google.com/go/websecurityscanner v1.6.4/go.mod h1:mUiyMQ+dGpPPRkHgknIZeCzSHJ45+fY4F52nZFDHm2o= cloud.google.com/go/workflows v1.6.0/go.mod h1:6t9F5h/unJz41YqfBmqSASJSXccBLtD1Vwf+KmJENM0= cloud.google.com/go/workflows v1.7.0/go.mod h1:JhSrZuVZWuiDfKEFxU0/F1PQjmpnpcoISEXH2bcHC3M= cloud.google.com/go/workflows v1.8.0/go.mod h1:ysGhmEajwZxGn1OhGOGKsTXc5PyxOc0vfKf5Af+to4M= @@ -789,6 +1129,9 @@ cloud.google.com/go/workflows v1.9.0/go.mod h1:ZGkj1aFIOd9c8Gerkjjq7OW7I5+l6cSvT cloud.google.com/go/workflows v1.10.0/go.mod h1:fZ8LmRmZQWacon9UCX1r/g/DfAXx5VcPALq2CxzdePw= cloud.google.com/go/workflows v1.11.1/go.mod h1:Z+t10G1wF7h8LgdY/EmRcQY8ptBD/nvofaL6FqlET6g= cloud.google.com/go/workflows v1.12.0/go.mod h1:PYhSk2b6DhZ508tj8HXKaBh+OFe+xdl0dHF/tJdzPQM= +cloud.google.com/go/workflows v1.12.1/go.mod h1:5A95OhD/edtOhQd/O741NSfIMezNTbCwLM1P1tBRGHM= +cloud.google.com/go/workflows v1.12.2/go.mod h1:+OmBIgNqYJPVggnMo9nqmizW0qEXHhmnAzK/CnBqsHc= +cloud.google.com/go/workflows v1.12.3/go.mod h1:fmOUeeqEwPzIU81foMjTRQIdwQHADi/vEr1cx9R1m5g= dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= gioui.org v0.0.0-20210308172011-57750fc8a0a6/go.mod h1:RSH6KIUZ0p2xy5zHDxgAM4zumjgTw83q2ge/PI+yyw8= git.sr.ht/~sbinet/gg v0.3.1/go.mod h1:KGYtlADtqsqANL9ueOFkWymvzUvLMQllU5Ixo+8v3pc= @@ -832,8 +1175,9 @@ github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20230105202645-06c439db220b/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230310173818-32f1caf87195/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230428030218-4003588d1b74/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4 h1:/inchEIKaYC1Akx+H+gqO04wryn5h75LSazbRlnya1k= github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20231109132714-523115ebc101 h1:7To3pQ+pZo0i3dsWEbinPNFs5gPSBOsJtx3wTT94VBY= +github.com/cncf/xds/go v0.0.0-20231109132714-523115ebc101/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -935,8 +1279,11 @@ github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/ github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.7/go.mod h1:n+brtR0CgQNWTVd5ZUFpTBC8YFBDLK/h/bpaJ8/DtOE= github.com/google/go-cmp v0.5.8/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= -github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38= github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/google/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-pkcs11 v0.2.0/go.mod h1:6eQoGcuNJpa7jnd5pMGdkSaQpNDYvPlXWMcjXXThLlY= +github.com/google/go-pkcs11 v0.2.1-0.20230907215043-c6f79328ddf9/go.mod h1:6eQoGcuNJpa7jnd5pMGdkSaQpNDYvPlXWMcjXXThLlY= github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= github.com/google/martian/v3 v3.0.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= github.com/google/martian/v3 v3.1.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= @@ -961,15 +1308,19 @@ github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm4 github.com/google/s2a-go v0.1.0/go.mod h1:OJpEgntRZo8ugHpF9hkoLJbS5dSI20XZeXJ9JVywLlM= github.com/google/s2a-go v0.1.3/go.mod h1:Ej+mSEMGRnqRzjc7VtF+jdBwYG5fuJfiZ8ELkjEwM0A= github.com/google/s2a-go v0.1.4/go.mod h1:Ej+mSEMGRnqRzjc7VtF+jdBwYG5fuJfiZ8ELkjEwM0A= +github.com/google/s2a-go v0.1.7/go.mod h1:50CgR4k1jNlWBu4UfS4AcfhVe1r6pdZPygJ3R8F0Qdw= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.4.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/enterprise-certificate-proxy v0.0.0-20220520183353-fd19c99a87aa/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.1.0/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.2.0/go.mod h1:8C0jb7/mgJe/9KK8Lm7X9ctZC2t60YyIpYEI16jx0Qg= github.com/googleapis/enterprise-certificate-proxy v0.2.1/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= github.com/googleapis/enterprise-certificate-proxy v0.2.3/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= github.com/googleapis/enterprise-certificate-proxy v0.2.4/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= +github.com/googleapis/enterprise-certificate-proxy v0.2.5/go.mod h1:RxW0N9901Cko1VOCW3SXCpWP+mlIEkk2tP7jnHy9a3w= +github.com/googleapis/enterprise-certificate-proxy v0.3.2/go.mod h1:VLSiSSBs/ksPL8kq3OBOQ6WRI2QnaFynd1DCjZ62+V0= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= github.com/googleapis/gax-go/v2 v2.1.0/go.mod h1:Q3nei7sK6ybPYH7twZdmQpAd1MKb7pfu6SK+H1/DsU0= @@ -1101,7 +1452,10 @@ golang.org/x/crypto v0.7.0/go.mod h1:pYwdfH91IfpZVANVyUOhSIPZaFoJGxTFbZhFTx+dXZU golang.org/x/crypto v0.9.0/go.mod h1:yrmDGqONDYtNj3tH8X9dzUun2m2lzPa9ngI6/RUPGR0= golang.org/x/crypto v0.10.0/go.mod h1:o4eNf7Ede1fv+hwOwZsTHl9EsPFO6q6ZvYR8vYfY45I= golang.org/x/crypto v0.11.0/go.mod h1:xgJhtzW8F9jGdVFWZESrid1U1bjeNy4zgy5cRr/CIio= +golang.org/x/crypto v0.12.0/go.mod h1:NF0Gs7EO5K4qLn+Ylc+fih8BSTeIjAP05siRnAh98yw= +golang.org/x/crypto v0.13.0/go.mod h1:y6Z2r+Rw4iayiXXAIxJIDAJ1zMW4yaTpebo8fPOliYc= golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4= +golang.org/x/crypto v0.15.0/go.mod h1:4ChreQoLWfG3xLDer1WdlH5NdlQ3+mwnQq1YTKY+72g= golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20180807140117-3d87b88a115f/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= @@ -1223,9 +1577,11 @@ golang.org/x/net v0.9.0/go.mod h1:d48xBJpPfHeWQsugry2m+kC02ZBRGRgulfHnEXEuWns= golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg= golang.org/x/net v0.11.0/go.mod h1:2L/ixqYpgIVXmeoSA/4Lu7BzTG4KIyPIryS4IsOd1oQ= golang.org/x/net v0.12.0/go.mod h1:zEVYFnQC7m/vmpQFELhcD1EWkZlX69l4oqgmer6hfKA= +golang.org/x/net v0.14.0/go.mod h1:PpSgVXXLK0OxS0F31C1/tv6XNguvCrnXIDrFMspZIUI= golang.org/x/net v0.16.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= -golang.org/x/net v0.17.0 h1:pVaXccu2ozPjCXewfr1S7xza/zcXTity9cCdXQYSjIM= golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= +golang.org/x/net v0.18.0 h1:mIYleuAkSbHh0tCv7RvjL3F6ZVbLjq4+R7zbOn3Kokg= +golang.org/x/net v0.18.0/go.mod h1:/czyP5RqHAH4odGYxBJ1qz0+CE5WZ+2j1YgoEo8F2jQ= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -1257,7 +1613,9 @@ golang.org/x/oauth2 v0.6.0/go.mod h1:ycmewcwgD4Rpr3eZJLSB4Kyyljb3qDh40vJ8STE5HKw golang.org/x/oauth2 v0.7.0/go.mod h1:hPLQkd9LyjfXTiRohC/41GhcFqxisoUQ99sCUOHO9x4= golang.org/x/oauth2 v0.8.0/go.mod h1:yr7u4HXZRm1R1kBWqr/xKNqewf0plRYoB7sla+BCIXE= golang.org/x/oauth2 v0.10.0/go.mod h1:kTpgurOux7LqtuxjuyZa4Gj2gdezIt/jQtGnNFfypQI= +golang.org/x/oauth2 v0.11.0/go.mod h1:LdF7O/8bLR/qWK9DrpXmbHLTouvRHK0SgJl0GmDBchk= golang.org/x/oauth2 v0.13.0/go.mod h1:/JMhi4ZRXAf4HG9LiNmxvk+45+96RUlVThiH8FzNBn0= +golang.org/x/oauth2 v0.14.0/go.mod h1:lAtNWgaWfL4cm7j2OV8TxGi9Qb7ECORx8DktCY74OwM= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -1277,6 +1635,7 @@ golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.2.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= golang.org/x/sync v0.4.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= +golang.org/x/sync v0.5.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/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-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -1358,8 +1717,11 @@ golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.9.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.10.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.13.0 h1:Af8nKPmuFypiUBjVoU9V20FiaFXOcuZI21p0ycVYYGE= +golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.14.0 h1:Vz7Qs629MkJkGyHxUlRHizWJRG2j8fbQKjELVSNhy7Q= +golang.org/x/sys v0.14.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.1.0/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= @@ -1372,7 +1734,10 @@ golang.org/x/term v0.7.0/go.mod h1:P32HKFT3hSsZrRxla30E9HqToFYAQPCMs/zFMBUFqPY= golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo= golang.org/x/term v0.9.0/go.mod h1:M6DEAAIenWoTxdKrOltXcmDY3rSplQUkrvaDU5FcQyo= golang.org/x/term v0.10.0/go.mod h1:lpqdcUyK/oCiQxvxVrppt5ggO2KCZ5QblwqPnfZ6d5o= +golang.org/x/term v0.11.0/go.mod h1:zC9APTIj3jG3FdV/Ons+XE1riIZXG4aZ4GTHiPZJPIU= +golang.org/x/term v0.12.0/go.mod h1:owVbMEjm3cBLCHdkQu9b1opXd4ETQWc3BhuQGKgXgvU= golang.org/x/term v0.13.0/go.mod h1:LTmsnFJwVN6bCy1rVCoS+qHT1HhALEFxKncY3WNNh4U= +golang.org/x/term v0.14.0/go.mod h1:TySc+nGkYR6qt8km8wUhuFRTVSMIX3XPR58y2lC8vww= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/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.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -1391,8 +1756,10 @@ golang.org/x/text v0.8.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.10.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.11.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= -golang.org/x/text v0.13.0 h1:ablQoSUd0tRdKxZewP80B+BaqeKJuVhuRxj/dkrun3k= +golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= +golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ= +golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -1542,6 +1909,8 @@ google.golang.org/api v0.124.0/go.mod h1:xu2HQurE5gi/3t1aFCvhPD781p0a3p11sdunTJ2 google.golang.org/api v0.125.0/go.mod h1:mBwVAtz+87bEN6CbA1GtZPDOqY2R5ONPqJeIlvyo4Aw= google.golang.org/api v0.126.0/go.mod h1:mBwVAtz+87bEN6CbA1GtZPDOqY2R5ONPqJeIlvyo4Aw= google.golang.org/api v0.128.0/go.mod h1:Y611qgqaE92On/7g65MQgxYul3c0rEB894kniWLY750= +google.golang.org/api v0.139.0/go.mod h1:CVagp6Eekz9CjGZ718Z+sloknzkDJE7Vc1Ckj9+viBk= +google.golang.org/api v0.149.0/go.mod h1:Mwn1B7JTXrzXtnvmzQE2BD6bYZQ8DShKZDZbeN9I7qI= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -1693,10 +2062,15 @@ google.golang.org/genproto v0.0.0-20230711160842-782d3b101e98/go.mod h1:S7mY02Oq google.golang.org/genproto v0.0.0-20230726155614-23370e0ffb3e/go.mod h1:0ggbjUrZYpy1q+ANUS30SEoGZ53cdfwtbuG7Ptgy108= google.golang.org/genproto v0.0.0-20230803162519-f966b187b2e5/go.mod h1:oH/ZOT02u4kWEp7oYBGYFFkCdKS/uYR9Z7+0/xuuFp8= google.golang.org/genproto v0.0.0-20230821184602-ccc8af3d0e93/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= +google.golang.org/genproto v0.0.0-20230822172742-b8732ec3820d/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= google.golang.org/genproto v0.0.0-20230913181813-007df8e322eb/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= google.golang.org/genproto v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:CCviP9RmpZ1mxVr8MUjCnSiY09IbAXZxhLE6EhHIdPU= -google.golang.org/genproto v0.0.0-20231002182017-d307bd883b97 h1:SeZZZx0cP0fqUyA+oRzP9k7cSwJlvDFiROO72uwD6i0= google.golang.org/genproto v0.0.0-20231002182017-d307bd883b97/go.mod h1:t1VqOqqvce95G3hIDCT5FeO3YUc6Q4Oe24L/+rNMxRk= +google.golang.org/genproto v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:EMfReVxb80Dq1hhioy0sOsY9jCE46YDgHlJ7fWVUWRE= +google.golang.org/genproto v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:CgAqfJo+Xmu0GwA0411Ht3OU3OntXwsGmrmjI8ioGXI= +google.golang.org/genproto v0.0.0-20231030173426-d783a09b4405/go.mod h1:3WDQMjmJk36UQhjQ89emUzb1mdaHcPeeAh4SCBKznB4= +google.golang.org/genproto v0.0.0-20231106174013-bbf56f31fb17 h1:wpZ8pe2x1Q3f2KyT5f8oP/fa9rHAKgFPr/HZdNuS+PQ= +google.golang.org/genproto v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:J7XzRzVy1+IPwWHZUzoD0IccYZIrXILAQpc+Qy9CMhY= google.golang.org/genproto/googleapis/api v0.0.0-20230525234020-1aefcd67740a/go.mod h1:ts19tUU+Z0ZShN1y3aPyq2+O3d5FUNNgT6FtOzmrNn8= google.golang.org/genproto/googleapis/api v0.0.0-20230525234035-dd9d682886f9/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= google.golang.org/genproto/googleapis/api v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= @@ -1706,10 +2080,17 @@ google.golang.org/genproto/googleapis/api v0.0.0-20230706204954-ccb25ca9f130/go. google.golang.org/genproto/googleapis/api v0.0.0-20230711160842-782d3b101e98/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ= google.golang.org/genproto/googleapis/api v0.0.0-20230726155614-23370e0ffb3e/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ= google.golang.org/genproto/googleapis/api v0.0.0-20230803162519-f966b187b2e5/go.mod h1:5DZzOUPCLYL3mNkQ0ms0F3EuUNZ7py1Bqeq6sxzI7/Q= +google.golang.org/genproto/googleapis/api v0.0.0-20230822172742-b8732ec3820d/go.mod h1:KjSP20unUpOx5kyQUFa7k4OJg0qeJ7DEZflGDu2p6Bk= google.golang.org/genproto/googleapis/api v0.0.0-20230913181813-007df8e322eb/go.mod h1:KjSP20unUpOx5kyQUFa7k4OJg0qeJ7DEZflGDu2p6Bk= google.golang.org/genproto/googleapis/api v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:RdyHbowztCGQySiCvQPgWQWgWhGnouTdCflKoDBt32U= google.golang.org/genproto/googleapis/api v0.0.0-20231002182017-d307bd883b97/go.mod h1:iargEX0SFPm3xcfMI0d1domjg0ZF4Aa0p2awqyxhvF0= +google.golang.org/genproto/googleapis/api v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:SUBoKXbI1Efip18FClrQVGjWcyd0QZd8KkvdP34t7ww= +google.golang.org/genproto/googleapis/api v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:IBQ646DjkDkvUIsVq/cc03FUFQ9wbZu7yE396YcL870= +google.golang.org/genproto/googleapis/api v0.0.0-20231030173426-d783a09b4405/go.mod h1:oT32Z4o8Zv2xPQTg0pbVaPr0MPOH6f14RgXt7zfIpwg= +google.golang.org/genproto/googleapis/api v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:0xJLfVdJqpAPl8tDg1ujOCGzx6LFLttXT5NhllGOXY4= google.golang.org/genproto/googleapis/bytestream v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:ylj+BE99M198VPbBh6A8d9n3w8fChvyLK3wwBOjXBFA= +google.golang.org/genproto/googleapis/bytestream v0.0.0-20230807174057-1744710a1577/go.mod h1:NjCQG/D8JandXxM57PZbAJL1DCNL6EypA0vPPwfsc7c= +google.golang.org/genproto/googleapis/bytestream v0.0.0-20231030173426-d783a09b4405/go.mod h1:GRUCuLdzVqZte8+Dl/D4N25yLzcGqqWaYkeVOwulFqw= google.golang.org/genproto/googleapis/rpc v0.0.0-20230525234015-3fc162c6f38a/go.mod h1:xURIpW9ES5+/GZhnV6beoEtxQrnkRGIfP5VQG2tCBLc= google.golang.org/genproto/googleapis/rpc v0.0.0-20230525234030-28d5490b6b19/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= google.golang.org/genproto/googleapis/rpc v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= @@ -1719,10 +2100,15 @@ google.golang.org/genproto/googleapis/rpc v0.0.0-20230706204954-ccb25ca9f130/go. google.golang.org/genproto/googleapis/rpc v0.0.0-20230711160842-782d3b101e98/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM= google.golang.org/genproto/googleapis/rpc v0.0.0-20230731190214-cbb8c96f2d6d/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM= google.golang.org/genproto/googleapis/rpc v0.0.0-20230803162519-f966b187b2e5/go.mod h1:zBEcrKX2ZOcEkHWxBPAIvYUWOKKMIhYcmNiUIu2ji3I= +google.golang.org/genproto/googleapis/rpc v0.0.0-20230822172742-b8732ec3820d/go.mod h1:+Bk1OCOj40wS2hwAMA+aCW9ypzm63QTBBHp6lQ3p+9M= google.golang.org/genproto/googleapis/rpc v0.0.0-20230920183334-c177e329c48b/go.mod h1:+Bk1OCOj40wS2hwAMA+aCW9ypzm63QTBBHp6lQ3p+9M= google.golang.org/genproto/googleapis/rpc v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:KSqppvjFjtoCI+KGd4PELB0qLNxdJHRGqRI09mB6pQA= -google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97 h1:6GQBEOdGkX6MMTLT9V+TjtIRZCw9VPD5Z+yHY9wMgS0= google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97/go.mod h1:v7nGkzlmW8P3n/bKmWBn2WpBjpOEx8Q6gMueudAmKfY= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:4cYg8o5yUbm77w8ZX00LhMVNl/YVBFJRYWDc0uYWMs0= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:swOH3j0KzcDDgGUWr+SNpyTen5YrXjS3eyPzFYKc6lc= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231030173426-d783a09b4405/go.mod h1:67X1fPuzjcrkymZzZV1vvkFeTn2Rvc6lYF9MYFGCcwE= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17 h1:Jyp0Hsi0bmHXG6k9eATXoYtjd6e2UzZ1SCn/wIupY14= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:oQ5rr10WTTMvP4A36n8JpR1OrO1BEiV4f78CneXZxkA= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= @@ -1768,9 +2154,11 @@ google.golang.org/grpc v1.55.0/go.mod h1:iYEXKGkEBhg1PjZQvoYEVPTDkHo1/bjTnfwTeGO google.golang.org/grpc v1.56.1/go.mod h1:I9bI3vqKfayGqPUAwGdOSu7kt6oIJLixfffKrpXqQ9s= google.golang.org/grpc v1.56.2/go.mod h1:I9bI3vqKfayGqPUAwGdOSu7kt6oIJLixfffKrpXqQ9s= google.golang.org/grpc v1.57.0/go.mod h1:Sd+9RMTACXwmub0zcNY2c4arhtrbBYD1AUHI/dt16Mo= +google.golang.org/grpc v1.58.2/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0= google.golang.org/grpc v1.58.3/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0= -google.golang.org/grpc v1.60.1 h1:26+wFr+cNqSGFcOXcabYC0lUVJVRa2Sb2ortSK7VrEU= -google.golang.org/grpc v1.60.1/go.mod h1:OlCHIeLYqSSsLi6i49B5QGdzaMZK9+M7LXN2FKz4eGM= +google.golang.org/grpc v1.59.0/go.mod h1:aUPDwccQo6OTjy7Hct4AfBPD1GptF4fyUjIkQ9YtF98= +google.golang.org/grpc v1.61.0 h1:TOvOcuXn30kRao+gfcvsebNEa5iZIiLkisYEkf7R7o0= +google.golang.org/grpc v1.61.0/go.mod h1:VUbo7IFqmF1QtCAstipjG0GIoq49KvMe9+h1jFLBNJs= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= diff --git a/examples/golang-http/simple/config.go b/examples/golang-http/simple/config.go index effd79cb87be7..2c635d9f02bb3 100644 --- a/examples/golang-http/simple/config.go +++ b/examples/golang-http/simple/config.go @@ -14,7 +14,7 @@ import ( const Name = "simple" func init() { - http.RegisterHttpFilterConfigFactoryAndParser(Name, ConfigFactory, &parser{}) + http.RegisterHttpFilterFactoryAndConfigParser(Name, filterFactory, &parser{}) } type config struct { @@ -60,17 +60,14 @@ func (p *parser) Merge(parent interface{}, child interface{}) interface{} { return &newConfig } -func ConfigFactory(c interface{}) api.StreamFilterFactory { +func filterFactory(c interface{}, callbacks api.FilterCallbackHandler) api.StreamFilter { conf, ok := c.(*config) if !ok { panic("unexpected config type") } - - return func(callbacks api.FilterCallbackHandler) api.StreamFilter { - return &filter{ - callbacks: callbacks, - config: conf, - } + return &filter{ + callbacks: callbacks, + config: conf, } } diff --git a/examples/grpc-bridge/client/requirements.txt b/examples/grpc-bridge/client/requirements.txt index ffb63c42c8e53..c256b9ee6aef6 100644 --- a/examples/grpc-bridge/client/requirements.txt +++ b/examples/grpc-bridge/client/requirements.txt @@ -100,119 +100,119 @@ charset-normalizer==3.3.0 \ --hash=sha256:f8888e31e3a85943743f8fc15e71536bda1c81d5aa36d014a3c0c44481d7db6e \ --hash=sha256:fc52b79d83a3fe3a360902d3f5d79073a993597d48114c29485e9431092905d8 # via requests -grpcio==1.60.0 \ - --hash=sha256:073f959c6f570797272f4ee9464a9997eaf1e98c27cb680225b82b53390d61e6 \ - --hash=sha256:0fd3b3968ffe7643144580f260f04d39d869fcc2cddb745deef078b09fd2b328 \ - --hash=sha256:1434ca77d6fed4ea312901122dc8da6c4389738bf5788f43efb19a838ac03ead \ - --hash=sha256:1c30bb23a41df95109db130a6cc1b974844300ae2e5d68dd4947aacba5985aa5 \ - --hash=sha256:20e7a4f7ded59097c84059d28230907cd97130fa74f4a8bfd1d8e5ba18c81491 \ - --hash=sha256:2199165a1affb666aa24adf0c97436686d0a61bc5fc113c037701fb7c7fceb96 \ - --hash=sha256:297eef542156d6b15174a1231c2493ea9ea54af8d016b8ca7d5d9cc65cfcc444 \ - --hash=sha256:2aef56e85901c2397bd557c5ba514f84de1f0ae5dd132f5d5fed042858115951 \ - --hash=sha256:30943b9530fe3620e3b195c03130396cd0ee3a0d10a66c1bee715d1819001eaf \ - --hash=sha256:3b36a2c6d4920ba88fa98075fdd58ff94ebeb8acc1215ae07d01a418af4c0253 \ - --hash=sha256:428d699c8553c27e98f4d29fdc0f0edc50e9a8a7590bfd294d2edb0da7be3629 \ - --hash=sha256:43e636dc2ce9ece583b3e2ca41df5c983f4302eabc6d5f9cd04f0562ee8ec1ae \ - --hash=sha256:452ca5b4afed30e7274445dd9b441a35ece656ec1600b77fff8c216fdf07df43 \ - --hash=sha256:467a7d31554892eed2aa6c2d47ded1079fc40ea0b9601d9f79204afa8902274b \ - --hash=sha256:4b44d7e39964e808b071714666a812049765b26b3ea48c4434a3b317bac82f14 \ - --hash=sha256:4c86343cf9ff7b2514dd229bdd88ebba760bd8973dac192ae687ff75e39ebfab \ - --hash=sha256:5208a57eae445ae84a219dfd8b56e04313445d146873117b5fa75f3245bc1390 \ - --hash=sha256:5ff21e000ff2f658430bde5288cb1ac440ff15c0d7d18b5fb222f941b46cb0d2 \ - --hash=sha256:675997222f2e2f22928fbba640824aebd43791116034f62006e19730715166c0 \ - --hash=sha256:676e4a44e740deaba0f4d95ba1d8c5c89a2fcc43d02c39f69450b1fa19d39590 \ - --hash=sha256:6e306b97966369b889985a562ede9d99180def39ad42c8014628dd3cc343f508 \ - --hash=sha256:6fd9584bf1bccdfff1512719316efa77be235469e1e3295dce64538c4773840b \ - --hash=sha256:705a68a973c4c76db5d369ed573fec3367d7d196673fa86614b33d8c8e9ebb08 \ - --hash=sha256:74d7d9fa97809c5b892449b28a65ec2bfa458a4735ddad46074f9f7d9550ad13 \ - --hash=sha256:77c8a317f0fd5a0a2be8ed5cbe5341537d5c00bb79b3bb27ba7c5378ba77dbca \ - --hash=sha256:79a050889eb8d57a93ed21d9585bb63fca881666fc709f5d9f7f9372f5e7fd03 \ - --hash=sha256:7db16dd4ea1b05ada504f08d0dca1cd9b926bed3770f50e715d087c6f00ad748 \ - --hash=sha256:83f2292ae292ed5a47cdcb9821039ca8e88902923198f2193f13959360c01860 \ - --hash=sha256:87c9224acba0ad8bacddf427a1c2772e17ce50b3042a789547af27099c5f751d \ - --hash=sha256:8a97a681e82bc11a42d4372fe57898d270a2707f36c45c6676e49ce0d5c41353 \ - --hash=sha256:9073513ec380434eb8d21970e1ab3161041de121f4018bbed3146839451a6d8e \ - --hash=sha256:90bdd76b3f04bdb21de5398b8a7c629676c81dfac290f5f19883857e9371d28c \ - --hash=sha256:91229d7203f1ef0ab420c9b53fe2ca5c1fbeb34f69b3bc1b5089466237a4a134 \ - --hash=sha256:92f88ca1b956eb8427a11bb8b4a0c0b2b03377235fc5102cb05e533b8693a415 \ - --hash=sha256:95ae3e8e2c1b9bf671817f86f155c5da7d49a2289c5cf27a319458c3e025c320 \ - --hash=sha256:9e30be89a75ee66aec7f9e60086fadb37ff8c0ba49a022887c28c134341f7179 \ - --hash=sha256:a48edde788b99214613e440fce495bbe2b1e142a7f214cce9e0832146c41e324 \ - --hash=sha256:a7152fa6e597c20cb97923407cf0934e14224af42c2b8d915f48bc3ad2d9ac18 \ - --hash=sha256:a9c7b71211f066908e518a2ef7a5e211670761651039f0d6a80d8d40054047df \ - --hash=sha256:b0571a5aef36ba9177e262dc88a9240c866d903a62799e44fd4aae3f9a2ec17e \ - --hash=sha256:b0fb2d4801546598ac5cd18e3ec79c1a9af8b8f2a86283c55a5337c5aeca4b1b \ - --hash=sha256:b10241250cb77657ab315270b064a6c7f1add58af94befa20687e7c8d8603ae6 \ - --hash=sha256:b87efe4a380887425bb15f220079aa8336276398dc33fce38c64d278164f963d \ - --hash=sha256:b98f43fcdb16172dec5f4b49f2fece4b16a99fd284d81c6bbac1b3b69fcbe0ff \ - --hash=sha256:c193109ca4070cdcaa6eff00fdb5a56233dc7610216d58fb81638f89f02e4968 \ - --hash=sha256:c826f93050c73e7769806f92e601e0efdb83ec8d7c76ddf45d514fee54e8e619 \ - --hash=sha256:d020cfa595d1f8f5c6b343530cd3ca16ae5aefdd1e832b777f9f0eb105f5b139 \ - --hash=sha256:d6a478581b1a1a8fdf3318ecb5f4d0cda41cacdffe2b527c23707c9c1b8fdb55 \ - --hash=sha256:de2ad69c9a094bf37c1102b5744c9aec6cf74d2b635558b779085d0263166454 \ - --hash=sha256:e278eafb406f7e1b1b637c2cf51d3ad45883bb5bd1ca56bc05e4fc135dfdaa65 \ - --hash=sha256:e381fe0c2aa6c03b056ad8f52f8efca7be29fb4d9ae2f8873520843b6039612a \ - --hash=sha256:e61e76020e0c332a98290323ecfec721c9544f5b739fab925b6e8cbe1944cf19 \ - --hash=sha256:f897c3b127532e6befdcf961c415c97f320d45614daf84deba0a54e64ea2457b \ - --hash=sha256:fb464479934778d7cc5baf463d959d361954d6533ad34c3a4f1d267e86ee25fd +grpcio==1.60.1 \ + --hash=sha256:0250a7a70b14000fa311de04b169cc7480be6c1a769b190769d347939d3232a8 \ + --hash=sha256:069fe2aeee02dfd2135d562d0663fe70fbb69d5eed6eb3389042a7e963b54de8 \ + --hash=sha256:082081e6a36b6eb5cf0fd9a897fe777dbb3802176ffd08e3ec6567edd85bc104 \ + --hash=sha256:0c5807e9152eff15f1d48f6b9ad3749196f79a4a050469d99eecb679be592acc \ + --hash=sha256:14e8f2c84c0832773fb3958240c69def72357bc11392571f87b2d7b91e0bb092 \ + --hash=sha256:2a6087f234cb570008a6041c8ffd1b7d657b397fdd6d26e83d72283dae3527b1 \ + --hash=sha256:2bb2a2911b028f01c8c64d126f6b632fcd8a9ac975aa1b3855766c94e4107180 \ + --hash=sha256:2f44c32aef186bbba254129cea1df08a20be414144ac3bdf0e84b24e3f3b2e05 \ + --hash=sha256:30e980cd6db1088c144b92fe376747328d5554bc7960ce583ec7b7d81cd47287 \ + --hash=sha256:33aed0a431f5befeffd9d346b0fa44b2c01aa4aeae5ea5b2c03d3e25e0071216 \ + --hash=sha256:33bdea30dcfd4f87b045d404388469eb48a48c33a6195a043d116ed1b9a0196c \ + --hash=sha256:39aa848794b887120b1d35b1b994e445cc028ff602ef267f87c38122c1add50d \ + --hash=sha256:4216e67ad9a4769117433814956031cb300f85edc855252a645a9a724b3b6594 \ + --hash=sha256:49c9b6a510e3ed8df5f6f4f3c34d7fbf2d2cae048ee90a45cd7415abab72912c \ + --hash=sha256:4eec8b8c1c2c9b7125508ff7c89d5701bf933c99d3910e446ed531cd16ad5d87 \ + --hash=sha256:50d56280b482875d1f9128ce596e59031a226a8b84bec88cb2bf76c289f5d0de \ + --hash=sha256:53b69e79d00f78c81eecfb38f4516080dc7f36a198b6b37b928f1c13b3c063e9 \ + --hash=sha256:55ccb7db5a665079d68b5c7c86359ebd5ebf31a19bc1a91c982fd622f1e31ff2 \ + --hash=sha256:5a1ebbae7e2214f51b1f23b57bf98eeed2cf1ba84e4d523c48c36d5b2f8829ff \ + --hash=sha256:61b7199cd2a55e62e45bfb629a35b71fc2c0cb88f686a047f25b1112d3810904 \ + --hash=sha256:660fc6b9c2a9ea3bb2a7e64ba878c98339abaf1811edca904ac85e9e662f1d73 \ + --hash=sha256:6d140bdeb26cad8b93c1455fa00573c05592793c32053d6e0016ce05ba267549 \ + --hash=sha256:6e490fa5f7f5326222cb9f0b78f207a2b218a14edf39602e083d5f617354306f \ + --hash=sha256:6ecf21d20d02d1733e9c820fb5c114c749d888704a7ec824b545c12e78734d1c \ + --hash=sha256:70c83bb530572917be20c21f3b6be92cd86b9aecb44b0c18b1d3b2cc3ae47df0 \ + --hash=sha256:72153a0d2e425f45b884540a61c6639436ddafa1829a42056aa5764b84108b8e \ + --hash=sha256:73e14acd3d4247169955fae8fb103a2b900cfad21d0c35f0dcd0fdd54cd60367 \ + --hash=sha256:76eaaba891083fcbe167aa0f03363311a9f12da975b025d30e94b93ac7a765fc \ + --hash=sha256:79ae0dc785504cb1e1788758c588c711f4e4a0195d70dff53db203c95a0bd303 \ + --hash=sha256:7d142bcd604166417929b071cd396aa13c565749a4c840d6c702727a59d835eb \ + --hash=sha256:8c9554ca8e26241dabe7951aa1fa03a1ba0856688ecd7e7bdbdd286ebc272e4c \ + --hash=sha256:8d488fbdbf04283f0d20742b64968d44825617aa6717b07c006168ed16488804 \ + --hash=sha256:91422ba785a8e7a18725b1dc40fbd88f08a5bb4c7f1b3e8739cab24b04fa8a03 \ + --hash=sha256:9a66f4d2a005bc78e61d805ed95dedfcb35efa84b7bba0403c6d60d13a3de2d6 \ + --hash=sha256:9b106bc52e7f28170e624ba61cc7dc6829566e535a6ec68528f8e1afbed1c41f \ + --hash=sha256:9b54577032d4f235452f77a83169b6527bf4b77d73aeada97d45b2aaf1bf5ce0 \ + --hash=sha256:a09506eb48fa5493c58f946c46754ef22f3ec0df64f2b5149373ff31fb67f3dd \ + --hash=sha256:a212e5dea1a4182e40cd3e4067ee46be9d10418092ce3627475e995cca95de21 \ + --hash=sha256:a731ac5cffc34dac62053e0da90f0c0b8560396a19f69d9703e88240c8f05858 \ + --hash=sha256:af5ef6cfaf0d023c00002ba25d0751e5995fa0e4c9eec6cd263c30352662cbce \ + --hash=sha256:b58b855d0071575ea9c7bc0d84a06d2edfbfccec52e9657864386381a7ce1ae9 \ + --hash=sha256:bc808924470643b82b14fe121923c30ec211d8c693e747eba8a7414bc4351a23 \ + --hash=sha256:c557e94e91a983e5b1e9c60076a8fd79fea1e7e06848eb2e48d0ccfb30f6e073 \ + --hash=sha256:c71be3f86d67d8d1311c6076a4ba3b75ba5703c0b856b4e691c9097f9b1e8bd2 \ + --hash=sha256:c8754c75f55781515a3005063d9a05878b2cfb3cb7e41d5401ad0cf19de14872 \ + --hash=sha256:cb0af13433dbbd1c806e671d81ec75bd324af6ef75171fd7815ca3074fe32bfe \ + --hash=sha256:cba6209c96828711cb7c8fcb45ecef8c8859238baf15119daa1bef0f6c84bfe7 \ + --hash=sha256:cf77f8cf2a651fbd869fbdcb4a1931464189cd210abc4cfad357f1cacc8642a6 \ + --hash=sha256:d7404cebcdb11bb5bd40bf94131faf7e9a7c10a6c60358580fe83913f360f929 \ + --hash=sha256:dd1d3a8d1d2e50ad9b59e10aa7f07c7d1be2b367f3f2d33c5fade96ed5460962 \ + --hash=sha256:e5d97c65ea7e097056f3d1ead77040ebc236feaf7f71489383d20f3b4c28412a \ + --hash=sha256:f1c3dc536b3ee124e8b24feb7533e5c70b9f2ef833e3b2e5513b2897fd46763a \ + --hash=sha256:f2212796593ad1d0235068c79836861f2201fc7137a99aa2fea7beeb3b101177 \ + --hash=sha256:fead980fbc68512dfd4e0c7b1f5754c2a8e5015a04dea454b9cada54a8423525 # via # -r requirements.in # grpcio-tools -grpcio-tools==1.60.0 \ - --hash=sha256:081336d8258f1a56542aa8a7a5dec99a2b38d902e19fbdd744594783301b0210 \ - --hash=sha256:1748893efd05cf4a59a175d7fa1e4fbb652f4d84ccaa2109f7869a2be48ed25e \ - --hash=sha256:17a32b3da4fc0798cdcec0a9c974ac2a1e98298f151517bf9148294a3b1a5742 \ - --hash=sha256:18976684a931ca4bcba65c78afa778683aefaae310f353e198b1823bf09775a0 \ - --hash=sha256:1b93ae8ffd18e9af9a965ebca5fa521e89066267de7abdde20721edc04e42721 \ - --hash=sha256:1fbb9554466d560472f07d906bfc8dcaf52f365c2a407015185993e30372a886 \ - --hash=sha256:24c4ead4a03037beaeb8ef2c90d13d70101e35c9fae057337ed1a9144ef10b53 \ - --hash=sha256:2a8a758701f3ac07ed85f5a4284c6a9ddefcab7913a8e552497f919349e72438 \ - --hash=sha256:2dd01257e4feff986d256fa0bac9f56de59dc735eceeeb83de1c126e2e91f653 \ - --hash=sha256:2e00de389729ca8d8d1a63c2038703078a887ff738dc31be640b7da9c26d0d4f \ - --hash=sha256:2fb4cf74bfe1e707cf10bc9dd38a1ebaa145179453d150febb121c7e9cd749bf \ - --hash=sha256:2fd1671c52f96e79a2302c8b1c1f78b8a561664b8b3d6946f20d8f1cc6b4225a \ - --hash=sha256:321b18f42a70813545e416ddcb8bf20defa407a8114906711c9710a69596ceda \ - --hash=sha256:3456df087ea61a0972a5bc165aed132ed6ddcc63f5749e572f9fff84540bdbad \ - --hash=sha256:4041538f55aad5b3ae7e25ab314d7995d689e968bfc8aa169d939a3160b1e4c6 \ - --hash=sha256:559ce714fe212aaf4abbe1493c5bb8920def00cc77ce0d45266f4fd9d8b3166f \ - --hash=sha256:5a907a4f1ffba86501b2cdb8682346249ea032b922fc69a92f082ba045cca548 \ - --hash=sha256:5ce6bbd4936977ec1114f2903eb4342781960d521b0d82f73afedb9335251f6f \ - --hash=sha256:6170873b1e5b6580ebb99e87fb6e4ea4c48785b910bd7af838cc6e44b2bccb04 \ - --hash=sha256:6192184b1f99372ff1d9594bd4b12264e3ff26440daba7eb043726785200ff77 \ - --hash=sha256:6807b7a3f3e6e594566100bd7fe04a2c42ce6d5792652677f1aaf5aa5adaef3d \ - --hash=sha256:687f576d7ff6ce483bc9a196d1ceac45144e8733b953620a026daed8e450bc38 \ - --hash=sha256:74025fdd6d1cb7ba4b5d087995339e9a09f0c16cf15dfe56368b23e41ffeaf7a \ - --hash=sha256:7a5263a0f2ddb7b1cfb2349e392cfc4f318722e0f48f886393e06946875d40f3 \ - --hash=sha256:7a6fe752205caae534f29fba907e2f59ff79aa42c6205ce9a467e9406cbac68c \ - --hash=sha256:7c1cde49631732356cb916ee1710507967f19913565ed5f9991e6c9cb37e3887 \ - --hash=sha256:811abb9c4fb6679e0058dfa123fb065d97b158b71959c0e048e7972bbb82ba0f \ - --hash=sha256:857c5351e9dc33a019700e171163f94fcc7e3ae0f6d2b026b10fda1e3c008ef1 \ - --hash=sha256:87cf439178f3eb45c1a889b2e4a17cbb4c450230d92c18d9c57e11271e239c55 \ - --hash=sha256:9970d384fb0c084b00945ef57d98d57a8d32be106d8f0bd31387f7cbfe411b5b \ - --hash=sha256:9ee35234f1da8fba7ddbc544856ff588243f1128ea778d7a1da3039be829a134 \ - --hash=sha256:addc9b23d6ff729d9f83d4a2846292d4c84f5eb2ec38f08489a6a0d66ac2b91e \ - --hash=sha256:b22b1299b666eebd5752ba7719da536075eae3053abcf2898b65f763c314d9da \ - --hash=sha256:b8f7a5094adb49e85db13ea3df5d99a976c2bdfd83b0ba26af20ebb742ac6786 \ - --hash=sha256:b96981f3a31b85074b73d97c8234a5ed9053d65a36b18f4a9c45a2120a5b7a0a \ - --hash=sha256:bbf0ed772d2ae7e8e5d7281fcc00123923ab130b94f7a843eee9af405918f924 \ - --hash=sha256:bd2a17b0193fbe4793c215d63ce1e01ae00a8183d81d7c04e77e1dfafc4b2b8a \ - --hash=sha256:c771b19dce2bfe06899247168c077d7ab4e273f6655d8174834f9a6034415096 \ - --hash=sha256:d941749bd8dc3f8be58fe37183143412a27bec3df8482d5abd6b4ec3f1ac2924 \ - --hash=sha256:dba6e32c87b4af29b5f475fb2f470f7ee3140bfc128644f17c6c59ddeb670680 \ - --hash=sha256:dd1e68c232fe01dd5312a8dbe52c50ecd2b5991d517d7f7446af4ba6334ba872 \ - --hash=sha256:e5614cf0960456d21d8a0f4902e3e5e3bcacc4e400bf22f196e5dd8aabb978b7 \ - --hash=sha256:e5c519a0d4ba1ab44a004fa144089738c59278233e2010b2cf4527dc667ff297 \ - --hash=sha256:e68dc4474f30cad11a965f0eb5d37720a032b4720afa0ec19dbcea2de73b5aae \ - --hash=sha256:e70d867c120d9849093b0ac24d861e378bc88af2552e743d83b9f642d2caa7c2 \ - --hash=sha256:e87cabac7969bdde309575edc2456357667a1b28262b2c1f12580ef48315b19d \ - --hash=sha256:eae27f9b16238e2aaee84c77b5923c6924d6dccb0bdd18435bf42acc8473ae1a \ - --hash=sha256:ec0e401e9a43d927d216d5169b03c61163fb52b665c5af2fed851357b15aef88 \ - --hash=sha256:ed30499340228d733ff69fcf4a66590ed7921f94eb5a2bf692258b1280b9dac7 \ - --hash=sha256:f10ef47460ce3c6fd400f05fe757b90df63486c9b84d1ecad42dcc5f80c8ac14 \ - --hash=sha256:f3d916606dcf5610d4367918245b3d9d8cd0d2ec0b7043d1bbb8c50fe9815c3a \ - --hash=sha256:f610384dee4b1ca705e8da66c5b5fe89a2de3d165c5282c3d1ddf40cb18924e4 \ - --hash=sha256:fb4df80868b3e397d5fbccc004c789d2668b622b51a9d2387b4c89c80d31e2c5 \ - --hash=sha256:fc01bc1079279ec342f0f1b6a107b3f5dc3169c33369cf96ada6e2e171f74e86 +grpcio-tools==1.60.1 \ + --hash=sha256:075bb67895970f96aabc1761ca674bf4db193f8fcad387f08e50402023b5f953 \ + --hash=sha256:0aa34c7c21cff2177a4096b2b0d51dfbc9f8a41f929847a434e89b352c5a215d \ + --hash=sha256:0b62cb2d43a7f0eacc6a6962dfff7c2564874012e1a72ae4167e762f449e2912 \ + --hash=sha256:15f13e8f3d77b96adcb1e3615acec5b100bd836c6010c58a51465bcb9c06d128 \ + --hash=sha256:184b27333b627a7cc0972fb70d21a8bb7c02ac4a6febc16768d78ea8ff883ddd \ + --hash=sha256:18d7737f29ef5bbe3352547d0eccd080807834f00df223867dfc860bf81e9180 \ + --hash=sha256:1e96a532d38411f0543fe1903ff522f7142a9901afb0ed94de58d79caf1905be \ + --hash=sha256:214281cdafb7acfdcde848eca2de7c888a6e2b5cd25ab579712b965ea09a9cd4 \ + --hash=sha256:22ce3e3d861321d208d8bfd6161ab976623520b179712c90b2c175151463a6b1 \ + --hash=sha256:26f91161a91f1601777751230eaaafdf416fed08a15c3ba2ae391088e4a906c6 \ + --hash=sha256:284749d20fb22418f17d3d351b9eb838caf4a0393a9cb02c36e5c32fa4bbe9db \ + --hash=sha256:28ae665113affebdd109247386786e5ab4dccfcfad1b5f68e9cce2e326b57ee6 \ + --hash=sha256:2973f75e8ba5c551033a1d59cc97654f6f386deaf2559082011d245d7ed87bba \ + --hash=sha256:2a7fa55bc62d4b8ebe6fb26f8cf89df3cf3b504eb6c5f3a2f0174689d35fddb0 \ + --hash=sha256:2c19be2bba5583e30f88bb5d71b430176c396f0d6d0db3785e5845bfa3d28cd2 \ + --hash=sha256:31294b534f25f02ead204e58dcbe0e5437a95a1a6f276bb9378905595b02ff6d \ + --hash=sha256:3aeecd5b8faa2aab67e6c8b8a57e888c00ce70d39f331ede0a21312e92def1a6 \ + --hash=sha256:3fb6f4d2df0388c35c2804ba170f511238a681b679ead013bfe5e39d0ea9cf48 \ + --hash=sha256:3fcabf484720a9fa1690e2825fc940027a05a0c79a1075a730008ef634bd8ad2 \ + --hash=sha256:402efeec36d8b12b792bae8a900085416fc2f57a34b599445ace2e847b6b0d75 \ + --hash=sha256:40cd8268a675269ce59c4fa50877597ec638bb1099c52237bb726c8ac9791868 \ + --hash=sha256:46b495bae31c5d3f6ac0240eb848f0642b5410f80dff2aacdea20cdea3938c1d \ + --hash=sha256:4e66fe204da15e08e599adb3060109a42927c0868fe8933e2d341ea649eceb03 \ + --hash=sha256:5b4a939097005531edec331f22d0b82bff26e71ede009354d2f375b5d41e74f0 \ + --hash=sha256:5c7ed086fef5ff59f46d53a052b1934b73e0f7d12365d656d6af3a88057d5a3e \ + --hash=sha256:5ea6e397d87f458bb2c387a4a6e1b65df74ce5b5194a1f16850c38309012e981 \ + --hash=sha256:652b08c9fef39186ce4f97f05f5440c0ed41f117db0f7d6cb0e0d75dbc6afd3f \ + --hash=sha256:6801cfc5a85f0fb6fd12cade45942aaa1c814422328d594d12d364815fe34123 \ + --hash=sha256:8540f6480428a52614db71dd6394f52cbc0d2565b5ea1136a982f26390a42c7a \ + --hash=sha256:8c4b917aa4fcdc77990773063f0f14540aab8d4a8bf6c862b964a45d891a31d2 \ + --hash=sha256:985ac476da365267a2367ab20060f9096fbfc2e190fb02dd394f9ec05edf03ca \ + --hash=sha256:9aadc9c00baa2064baa4414cff7c269455449f14805a355226674d89c507342c \ + --hash=sha256:9bba347000f57dae8aea79c0d76ef7d72895597524d30d0170c7d1974a3a03f3 \ + --hash=sha256:a2bb8efc2cd64bd8f2779b426dd7e94e60924078ba5150cbbb60a846e62d1ed2 \ + --hash=sha256:a8cfab27ba2bd36a3e3b522aed686133531e8b919703d0247a0885dae8815317 \ + --hash=sha256:aafc94616c5f89c891d859057b194a153c451f9921053454e9d7d4cbf79047eb \ + --hash=sha256:acdba77584981fe799104aa545d9d97910bcf88c69b668b768c1f3e7d7e5afac \ + --hash=sha256:af88a2062b9c35034a80b25f289034b9c3c00c42bb88efaa465503a06fbd6a87 \ + --hash=sha256:b1041377cf32ee2338284ee26e6b9c10f9ea7728092376b19803dcb9b91d510d \ + --hash=sha256:b5ae375207af9aa82f516dcd513d2e0c83690b7788d45844daad846ed87550f8 \ + --hash=sha256:b6ef213cb0aecb2832ee82a2eac32f29f31f50b17ce020604d82205096a6bd0c \ + --hash=sha256:bba7230c60238c7a4ffa29f1aff6d78edb41f2c79cbe4443406472b1c80ccb5d \ + --hash=sha256:bd85f6c368b93ae45edf8568473053cb1cc075ef3489efb18f9832d4ecce062f \ + --hash=sha256:c1047bd831de5d9da761e9dc246988d5f07d722186938dfd5f34807398101010 \ + --hash=sha256:c20e752ff5057758845f4e5c7a298739bfba291f373ed18ea9c7c7acbe69e8ab \ + --hash=sha256:c354505e6a3d170da374f20404ea6a78135502df4f5534e5c532bdf24c4cc2a5 \ + --hash=sha256:cc8ba358d2c658c6ecbc58e779bf0fc5a673fecac015a70db27fc5b4d37b76b6 \ + --hash=sha256:cf945bd22f396c0d0c691e0990db2bfc4e77816b1edc2aea8a69c35ae721aac9 \ + --hash=sha256:d2c26ce5f774c98bd2d3d8d1703048394018b55d297ebdb41ed2ba35b9a34f68 \ + --hash=sha256:da08224ab8675c6d464b988bd8ca02cccd2bf0275bceefe8f6219bfd4a4f5e85 \ + --hash=sha256:dffa326cf901fe08a0e218d9fdf593f12276088a8caa07fcbec7d051149cf9ef \ + --hash=sha256:e529cd3d4109a6f4a3f7bdaca68946eb33734e2d7ffe861785a0586abe99ee67 \ + --hash=sha256:eba5fafd70585fbd4cb6ae45e3c5e11d8598e2426c9f289b78f682c0606e81cb \ + --hash=sha256:f95bdc6c7c50b7fc442e53537bc5b4eb8cab2a671c1da80d40b5a4ab1fd5d416 # via -r requirements.in idna==3.4 \ --hash=sha256:814f528e8dead7d329833b91c5faa87d60bf71824cd12a7530b5526063d02cb4 \ diff --git a/examples/grpc-bridge/server/go.mod b/examples/grpc-bridge/server/go.mod index a7ce20e70616d..0a53091a82317 100644 --- a/examples/grpc-bridge/server/go.mod +++ b/examples/grpc-bridge/server/go.mod @@ -5,5 +5,5 @@ go 1.13 require ( github.com/golang/protobuf v1.5.3 golang.org/x/net v0.20.0 - google.golang.org/grpc v1.60.1 + google.golang.org/grpc v1.61.0 ) diff --git a/examples/grpc-bridge/server/go.sum b/examples/grpc-bridge/server/go.sum index 5b927ec7eabcb..26be4a0c43bfe 100644 --- a/examples/grpc-bridge/server/go.sum +++ b/examples/grpc-bridge/server/go.sum @@ -41,16 +41,24 @@ cloud.google.com/go v0.110.4/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5x cloud.google.com/go v0.110.6/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5xsI= cloud.google.com/go v0.110.7/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5xsI= cloud.google.com/go v0.110.8/go.mod h1:Iz8AkXJf1qmxC3Oxoep8R1T36w8B92yU29PcBhHO5fk= +cloud.google.com/go v0.110.9/go.mod h1:rpxevX/0Lqvlbc88b7Sc1SPNdyK1riNBTUU6JXhYNpM= +cloud.google.com/go v0.110.10/go.mod h1:v1OoFqYxiBkUrruItNM3eT4lLByNjxmJSV/xDKJNnic= cloud.google.com/go/accessapproval v1.4.0/go.mod h1:zybIuC3KpDOvotz59lFe5qxRZx6C75OtwbisN56xYB4= cloud.google.com/go/accessapproval v1.5.0/go.mod h1:HFy3tuiGvMdcd/u+Cu5b9NkO1pEICJ46IR82PoUdplw= cloud.google.com/go/accessapproval v1.6.0/go.mod h1:R0EiYnwV5fsRFiKZkPHr6mwyk2wxUJ30nL4j2pcFY2E= cloud.google.com/go/accessapproval v1.7.1/go.mod h1:JYczztsHRMK7NTXb6Xw+dwbs/WnOJxbo/2mTI+Kgg68= +cloud.google.com/go/accessapproval v1.7.2/go.mod h1:/gShiq9/kK/h8T/eEn1BTzalDvk0mZxJlhfw0p+Xuc0= +cloud.google.com/go/accessapproval v1.7.3/go.mod h1:4l8+pwIxGTNqSf4T3ds8nLO94NQf0W/KnMNuQ9PbnP8= +cloud.google.com/go/accessapproval v1.7.4/go.mod h1:/aTEh45LzplQgFYdQdwPMR9YdX0UlhBmvB84uAmQKUc= cloud.google.com/go/accesscontextmanager v1.3.0/go.mod h1:TgCBehyr5gNMz7ZaH9xubp+CE8dkrszb4oK9CWyvD4o= cloud.google.com/go/accesscontextmanager v1.4.0/go.mod h1:/Kjh7BBu/Gh83sv+K60vN9QE5NJcd80sU33vIe2IFPE= cloud.google.com/go/accesscontextmanager v1.6.0/go.mod h1:8XCvZWfYw3K/ji0iVnp+6pu7huxoQTLmxAbVjbloTtM= cloud.google.com/go/accesscontextmanager v1.7.0/go.mod h1:CEGLewx8dwa33aDAZQujl7Dx+uYhS0eay198wB/VumQ= cloud.google.com/go/accesscontextmanager v1.8.0/go.mod h1:uI+AI/r1oyWK99NN8cQ3UK76AMelMzgZCvJfsi2c+ps= cloud.google.com/go/accesscontextmanager v1.8.1/go.mod h1:JFJHfvuaTC+++1iL1coPiG1eu5D24db2wXCDWDjIrxo= +cloud.google.com/go/accesscontextmanager v1.8.2/go.mod h1:E6/SCRM30elQJ2PKtFMs2YhfJpZSNcJyejhuzoId4Zk= +cloud.google.com/go/accesscontextmanager v1.8.3/go.mod h1:4i/JkF2JiFbhLnnpnfoTX5vRXfhf9ukhU1ANOTALTOQ= +cloud.google.com/go/accesscontextmanager v1.8.4/go.mod h1:ParU+WbMpD34s5JFEnGAnPBYAgUHozaTmDJU7aCU9+M= cloud.google.com/go/aiplatform v1.22.0/go.mod h1:ig5Nct50bZlzV6NvKaTwmplLLddFx0YReh9WfTO5jKw= cloud.google.com/go/aiplatform v1.24.0/go.mod h1:67UUvRBKG6GTayHKV8DBv2RtR1t93YRu5B1P3x99mYY= cloud.google.com/go/aiplatform v1.27.0/go.mod h1:Bvxqtl40l0WImSb04d0hXFU7gDOiq9jQmorivIiWcKg= @@ -60,6 +68,10 @@ cloud.google.com/go/aiplatform v1.37.0/go.mod h1:IU2Cv29Lv9oCn/9LkFiiuKfwrRTq+QQ cloud.google.com/go/aiplatform v1.45.0/go.mod h1:Iu2Q7sC7QGhXUeOhAj/oCK9a+ULz1O4AotZiqjQ8MYA= cloud.google.com/go/aiplatform v1.48.0/go.mod h1:Iu2Q7sC7QGhXUeOhAj/oCK9a+ULz1O4AotZiqjQ8MYA= cloud.google.com/go/aiplatform v1.50.0/go.mod h1:IRc2b8XAMTa9ZmfJV1BCCQbieWWvDnP1A8znyz5N7y4= +cloud.google.com/go/aiplatform v1.51.0/go.mod h1:IRc2b8XAMTa9ZmfJV1BCCQbieWWvDnP1A8znyz5N7y4= +cloud.google.com/go/aiplatform v1.51.1/go.mod h1:kY3nIMAVQOK2XDqDPHaOuD9e+FdMA6OOpfBjsvaFSOo= +cloud.google.com/go/aiplatform v1.51.2/go.mod h1:hCqVYB3mY45w99TmetEoe8eCQEwZEp9WHxeZdcv9phw= +cloud.google.com/go/aiplatform v1.52.0/go.mod h1:pwZMGvqe0JRkI1GWSZCtnAfrR4K1bv65IHILGA//VEU= cloud.google.com/go/analytics v0.11.0/go.mod h1:DjEWCu41bVbYcKyvlws9Er60YE4a//bK6mnhWvQeFNI= cloud.google.com/go/analytics v0.12.0/go.mod h1:gkfj9h6XRf9+TS4bmuhPEShsh3hH8PAZzm/41OOhQd4= cloud.google.com/go/analytics v0.17.0/go.mod h1:WXFa3WSym4IZ+JiKmavYdJwGG/CvpqiqczmL59bTD9M= @@ -67,18 +79,30 @@ cloud.google.com/go/analytics v0.18.0/go.mod h1:ZkeHGQlcIPkw0R/GW+boWHhCOR43xz9R cloud.google.com/go/analytics v0.19.0/go.mod h1:k8liqf5/HCnOUkbawNtrWWc+UAzyDlW89doe8TtoDsE= cloud.google.com/go/analytics v0.21.2/go.mod h1:U8dcUtmDmjrmUTnnnRnI4m6zKn/yaA5N9RlEkYFHpQo= cloud.google.com/go/analytics v0.21.3/go.mod h1:U8dcUtmDmjrmUTnnnRnI4m6zKn/yaA5N9RlEkYFHpQo= +cloud.google.com/go/analytics v0.21.4/go.mod h1:zZgNCxLCy8b2rKKVfC1YkC2vTrpfZmeRCySM3aUbskA= +cloud.google.com/go/analytics v0.21.5/go.mod h1:BQtOBHWTlJ96axpPPnw5CvGJ6i3Ve/qX2fTxR8qWyr8= +cloud.google.com/go/analytics v0.21.6/go.mod h1:eiROFQKosh4hMaNhF85Oc9WO97Cpa7RggD40e/RBy8w= cloud.google.com/go/apigateway v1.3.0/go.mod h1:89Z8Bhpmxu6AmUxuVRg/ECRGReEdiP3vQtk4Z1J9rJk= cloud.google.com/go/apigateway v1.4.0/go.mod h1:pHVY9MKGaH9PQ3pJ4YLzoj6U5FUDeDFBllIz7WmzJoc= cloud.google.com/go/apigateway v1.5.0/go.mod h1:GpnZR3Q4rR7LVu5951qfXPJCHquZt02jf7xQx7kpqN8= cloud.google.com/go/apigateway v1.6.1/go.mod h1:ufAS3wpbRjqfZrzpvLC2oh0MFlpRJm2E/ts25yyqmXA= +cloud.google.com/go/apigateway v1.6.2/go.mod h1:CwMC90nnZElorCW63P2pAYm25AtQrHfuOkbRSHj0bT8= +cloud.google.com/go/apigateway v1.6.3/go.mod h1:k68PXWpEs6BVDTtnLQAyG606Q3mz8pshItwPXjgv44Y= +cloud.google.com/go/apigateway v1.6.4/go.mod h1:0EpJlVGH5HwAN4VF4Iec8TAzGN1aQgbxAWGJsnPCGGY= cloud.google.com/go/apigeeconnect v1.3.0/go.mod h1:G/AwXFAKo0gIXkPTVfZDd2qA1TxBXJ3MgMRBQkIi9jc= cloud.google.com/go/apigeeconnect v1.4.0/go.mod h1:kV4NwOKqjvt2JYR0AoIWo2QGfoRtn/pkS3QlHp0Ni04= cloud.google.com/go/apigeeconnect v1.5.0/go.mod h1:KFaCqvBRU6idyhSNyn3vlHXc8VMDJdRmwDF6JyFRqZ8= cloud.google.com/go/apigeeconnect v1.6.1/go.mod h1:C4awq7x0JpLtrlQCr8AzVIzAaYgngRqWf9S5Uhg+wWs= +cloud.google.com/go/apigeeconnect v1.6.2/go.mod h1:s6O0CgXT9RgAxlq3DLXvG8riw8PYYbU/v25jqP3Dy18= +cloud.google.com/go/apigeeconnect v1.6.3/go.mod h1:peG0HFQ0si2bN15M6QSjEW/W7Gy3NYkWGz7pFz13cbo= +cloud.google.com/go/apigeeconnect v1.6.4/go.mod h1:CapQCWZ8TCjnU0d7PobxhpOdVz/OVJ2Hr/Zcuu1xFx0= cloud.google.com/go/apigeeregistry v0.4.0/go.mod h1:EUG4PGcsZvxOXAdyEghIdXwAEi/4MEaoqLMLDMIwKXY= cloud.google.com/go/apigeeregistry v0.5.0/go.mod h1:YR5+s0BVNZfVOUkMa5pAR2xGd0A473vA5M7j247o1wM= cloud.google.com/go/apigeeregistry v0.6.0/go.mod h1:BFNzW7yQVLZ3yj0TKcwzb8n25CFBri51GVGOEUcgQsc= cloud.google.com/go/apigeeregistry v0.7.1/go.mod h1:1XgyjZye4Mqtw7T9TsY4NW10U7BojBvG4RMD+vRDrIw= +cloud.google.com/go/apigeeregistry v0.7.2/go.mod h1:9CA2B2+TGsPKtfi3F7/1ncCCsL62NXBRfM6iPoGSM+8= +cloud.google.com/go/apigeeregistry v0.8.1/go.mod h1:MW4ig1N4JZQsXmBSwH4rwpgDonocz7FPBSw6XPGHmYw= +cloud.google.com/go/apigeeregistry v0.8.2/go.mod h1:h4v11TDGdeXJDJvImtgK2AFVvMIgGWjSb0HRnBSjcX8= cloud.google.com/go/apikeys v0.4.0/go.mod h1:XATS/yqZbaBK0HOssf+ALHp8jAlNHUgyfprvNcBIszU= cloud.google.com/go/apikeys v0.5.0/go.mod h1:5aQfwY4D+ewMMWScd3hm2en3hCj+BROlyrt3ytS7KLI= cloud.google.com/go/apikeys v0.6.0/go.mod h1:kbpXu5upyiAlGkKrJgQl8A0rKNNJ7dQ377pdroRSSi8= @@ -88,11 +112,17 @@ cloud.google.com/go/appengine v1.6.0/go.mod h1:hg6i0J/BD2cKmDJbaFSYHFyZkgBEfQrDg cloud.google.com/go/appengine v1.7.0/go.mod h1:eZqpbHFCqRGa2aCdope7eC0SWLV1j0neb/QnMJVWx6A= cloud.google.com/go/appengine v1.7.1/go.mod h1:IHLToyb/3fKutRysUlFO0BPt5j7RiQ45nrzEJmKTo6E= cloud.google.com/go/appengine v1.8.1/go.mod h1:6NJXGLVhZCN9aQ/AEDvmfzKEfoYBlfB80/BHiKVputY= +cloud.google.com/go/appengine v1.8.2/go.mod h1:WMeJV9oZ51pvclqFN2PqHoGnys7rK0rz6s3Mp6yMvDo= +cloud.google.com/go/appengine v1.8.3/go.mod h1:2oUPZ1LVZ5EXi+AF1ihNAF+S8JrzQ3till5m9VQkrsk= +cloud.google.com/go/appengine v1.8.4/go.mod h1:TZ24v+wXBujtkK77CXCpjZbnuTvsFNT41MUaZ28D6vg= cloud.google.com/go/area120 v0.5.0/go.mod h1:DE/n4mp+iqVyvxHN41Vf1CR602GiHQjFPusMFW6bGR4= cloud.google.com/go/area120 v0.6.0/go.mod h1:39yFJqWVgm0UZqWTOdqkLhjoC7uFfgXRC8g/ZegeAh0= cloud.google.com/go/area120 v0.7.0/go.mod h1:a3+8EUD1SX5RUcCs3MY5YasiO1z6yLiNLRiFrykbynY= cloud.google.com/go/area120 v0.7.1/go.mod h1:j84i4E1RboTWjKtZVWXPqvK5VHQFJRF2c1Nm69pWm9k= cloud.google.com/go/area120 v0.8.1/go.mod h1:BVfZpGpB7KFVNxPiQBuHkX6Ed0rS51xIgmGyjrAfzsg= +cloud.google.com/go/area120 v0.8.2/go.mod h1:a5qfo+x77SRLXnCynFWPUZhnZGeSgvQ+Y0v1kSItkh4= +cloud.google.com/go/area120 v0.8.3/go.mod h1:5zj6pMzVTH+SVHljdSKC35sriR/CVvQZzG/Icdyriw0= +cloud.google.com/go/area120 v0.8.4/go.mod h1:jfawXjxf29wyBXr48+W+GyX/f8fflxp642D/bb9v68M= cloud.google.com/go/artifactregistry v1.6.0/go.mod h1:IYt0oBPSAGYj/kprzsBjZ/4LnG/zOcHyFHjWPCi6SAQ= cloud.google.com/go/artifactregistry v1.7.0/go.mod h1:mqTOFOnGZx8EtSqK/ZWcsm/4U8B77rbcLP6ruDU2Ixk= cloud.google.com/go/artifactregistry v1.8.0/go.mod h1:w3GQXkJX8hiKN0v+at4b0qotwijQbYUqF2GWkZzAhC0= @@ -102,6 +132,10 @@ cloud.google.com/go/artifactregistry v1.11.2/go.mod h1:nLZns771ZGAwVLzTX/7Al6R9e cloud.google.com/go/artifactregistry v1.12.0/go.mod h1:o6P3MIvtzTOnmvGagO9v/rOjjA0HmhJ+/6KAXrmYDCI= cloud.google.com/go/artifactregistry v1.13.0/go.mod h1:uy/LNfoOIivepGhooAUpL1i30Hgee3Cu0l4VTWHUC08= cloud.google.com/go/artifactregistry v1.14.1/go.mod h1:nxVdG19jTaSTu7yA7+VbWL346r3rIdkZ142BSQqhn5E= +cloud.google.com/go/artifactregistry v1.14.2/go.mod h1:Xk+QbsKEb0ElmyeMfdHAey41B+qBq3q5R5f5xD4XT3U= +cloud.google.com/go/artifactregistry v1.14.3/go.mod h1:A2/E9GXnsyXl7GUvQ/2CjHA+mVRoWAXC0brg2os+kNI= +cloud.google.com/go/artifactregistry v1.14.4/go.mod h1:SJJcZTMv6ce0LDMUnihCN7WSrI+kBSFV0KIKo8S8aYU= +cloud.google.com/go/artifactregistry v1.14.6/go.mod h1:np9LSFotNWHcjnOgh8UVK0RFPCTUGbO0ve3384xyHfE= cloud.google.com/go/asset v1.5.0/go.mod h1:5mfs8UvcM5wHhqtSv8J1CtxxaQq3AdBxxQi2jGW/K4o= cloud.google.com/go/asset v1.7.0/go.mod h1:YbENsRK4+xTiL+Ofoj5Ckf+O17kJtgp3Y3nn4uzZz5s= cloud.google.com/go/asset v1.8.0/go.mod h1:mUNGKhiqIdbr8X7KNayoYvyc4HbbFO9URsjbytpUaW0= @@ -111,6 +145,10 @@ cloud.google.com/go/asset v1.11.1/go.mod h1:fSwLhbRvC9p9CXQHJ3BgFeQNM4c9x10lqlrd cloud.google.com/go/asset v1.12.0/go.mod h1:h9/sFOa4eDIyKmH6QMpm4eUK3pDojWnUhTgJlk762Hg= cloud.google.com/go/asset v1.13.0/go.mod h1:WQAMyYek/b7NBpYq/K4KJWcRqzoalEsxz/t/dTk4THw= cloud.google.com/go/asset v1.14.1/go.mod h1:4bEJ3dnHCqWCDbWJ/6Vn7GVI9LerSi7Rfdi03hd+WTQ= +cloud.google.com/go/asset v1.15.0/go.mod h1:tpKafV6mEut3+vN9ScGvCHXHj7FALFVta+okxFECHcg= +cloud.google.com/go/asset v1.15.1/go.mod h1:yX/amTvFWRpp5rcFq6XbCxzKT8RJUam1UoboE179jU4= +cloud.google.com/go/asset v1.15.2/go.mod h1:B6H5tclkXvXz7PD22qCA2TDxSVQfasa3iDlM89O2NXs= +cloud.google.com/go/asset v1.15.3/go.mod h1:yYLfUD4wL4X589A9tYrv4rFrba0QlDeag0CMcM5ggXU= cloud.google.com/go/assuredworkloads v1.5.0/go.mod h1:n8HOZ6pff6re5KYfBXcFvSViQjDwxFkAkmUFffJRbbY= cloud.google.com/go/assuredworkloads v1.6.0/go.mod h1:yo2YOk37Yc89Rsd5QMVECvjaMKymF9OP+QXWlKXUkXw= cloud.google.com/go/assuredworkloads v1.7.0/go.mod h1:z/736/oNmtGAyU47reJgGN+KVoYoxeLBoj4XkKYscNI= @@ -118,28 +156,44 @@ cloud.google.com/go/assuredworkloads v1.8.0/go.mod h1:AsX2cqyNCOvEQC8RMPnoc0yEar cloud.google.com/go/assuredworkloads v1.9.0/go.mod h1:kFuI1P78bplYtT77Tb1hi0FMxM0vVpRC7VVoJC3ZoT0= cloud.google.com/go/assuredworkloads v1.10.0/go.mod h1:kwdUQuXcedVdsIaKgKTp9t0UJkE5+PAVNhdQm4ZVq2E= cloud.google.com/go/assuredworkloads v1.11.1/go.mod h1:+F04I52Pgn5nmPG36CWFtxmav6+7Q+c5QyJoL18Lry0= +cloud.google.com/go/assuredworkloads v1.11.2/go.mod h1:O1dfr+oZJMlE6mw0Bp0P1KZSlj5SghMBvTpZqIcUAW4= +cloud.google.com/go/assuredworkloads v1.11.3/go.mod h1:vEjfTKYyRUaIeA0bsGJceFV2JKpVRgyG2op3jfa59Zs= +cloud.google.com/go/assuredworkloads v1.11.4/go.mod h1:4pwwGNwy1RP0m+y12ef3Q/8PaiWrIDQ6nD2E8kvWI9U= cloud.google.com/go/automl v1.5.0/go.mod h1:34EjfoFGMZ5sgJ9EoLsRtdPSNZLcfflJR39VbVNS2M0= cloud.google.com/go/automl v1.6.0/go.mod h1:ugf8a6Fx+zP0D59WLhqgTDsQI9w07o64uf/Is3Nh5p8= cloud.google.com/go/automl v1.7.0/go.mod h1:RL9MYCCsJEOmt0Wf3z9uzG0a7adTT1fe+aObgSpkCt8= cloud.google.com/go/automl v1.8.0/go.mod h1:xWx7G/aPEe/NP+qzYXktoBSDfjO+vnKMGgsApGJJquM= cloud.google.com/go/automl v1.12.0/go.mod h1:tWDcHDp86aMIuHmyvjuKeeHEGq76lD7ZqfGLN6B0NuU= cloud.google.com/go/automl v1.13.1/go.mod h1:1aowgAHWYZU27MybSCFiukPO7xnyawv7pt3zK4bheQE= +cloud.google.com/go/automl v1.13.2/go.mod h1:gNY/fUmDEN40sP8amAX3MaXkxcqPIn7F1UIIPZpy4Mg= +cloud.google.com/go/automl v1.13.3/go.mod h1:Y8KwvyAZFOsMAPqUCfNu1AyclbC6ivCUF/MTwORymyY= +cloud.google.com/go/automl v1.13.4/go.mod h1:ULqwX/OLZ4hBVfKQaMtxMSTlPx0GqGbWN8uA/1EqCP8= cloud.google.com/go/baremetalsolution v0.3.0/go.mod h1:XOrocE+pvK1xFfleEnShBlNAXf+j5blPPxrhjKgnIFc= cloud.google.com/go/baremetalsolution v0.4.0/go.mod h1:BymplhAadOO/eBa7KewQ0Ppg4A4Wplbn+PsFKRLo0uI= cloud.google.com/go/baremetalsolution v0.5.0/go.mod h1:dXGxEkmR9BMwxhzBhV0AioD0ULBmuLZI8CdwalUxuss= cloud.google.com/go/baremetalsolution v1.1.1/go.mod h1:D1AV6xwOksJMV4OSlWHtWuFNZZYujJknMAP4Qa27QIA= cloud.google.com/go/baremetalsolution v1.2.0/go.mod h1:68wi9AwPYkEWIUT4SvSGS9UJwKzNpshjHsH4lzk8iOw= +cloud.google.com/go/baremetalsolution v1.2.1/go.mod h1:3qKpKIw12RPXStwQXcbhfxVj1dqQGEvcmA+SX/mUR88= +cloud.google.com/go/baremetalsolution v1.2.2/go.mod h1:O5V6Uu1vzVelYahKfwEWRMaS3AbCkeYHy3145s1FkhM= +cloud.google.com/go/baremetalsolution v1.2.3/go.mod h1:/UAQ5xG3faDdy180rCUv47e0jvpp3BFxT+Cl0PFjw5g= cloud.google.com/go/batch v0.3.0/go.mod h1:TR18ZoAekj1GuirsUsR1ZTKN3FC/4UDnScjT8NXImFE= cloud.google.com/go/batch v0.4.0/go.mod h1:WZkHnP43R/QCGQsZ+0JyG4i79ranE2u8xvjq/9+STPE= cloud.google.com/go/batch v0.7.0/go.mod h1:vLZN95s6teRUqRQ4s3RLDsH8PvboqBK+rn1oevL159g= cloud.google.com/go/batch v1.3.1/go.mod h1:VguXeQKXIYaeeIYbuozUmBR13AfL4SJP7IltNPS+A4A= cloud.google.com/go/batch v1.4.1/go.mod h1:KdBmDD61K0ovcxoRHGrN6GmOBWeAOyCgKD0Mugx4Fkk= +cloud.google.com/go/batch v1.5.0/go.mod h1:KdBmDD61K0ovcxoRHGrN6GmOBWeAOyCgKD0Mugx4Fkk= +cloud.google.com/go/batch v1.5.1/go.mod h1:RpBuIYLkQu8+CWDk3dFD/t/jOCGuUpkpX+Y0n1Xccs8= +cloud.google.com/go/batch v1.6.1/go.mod h1:urdpD13zPe6YOK+6iZs/8/x2VBRofvblLpx0t57vM98= +cloud.google.com/go/batch v1.6.3/go.mod h1:J64gD4vsNSA2O5TtDB5AAux3nJ9iV8U3ilg3JDBYejU= cloud.google.com/go/beyondcorp v0.2.0/go.mod h1:TB7Bd+EEtcw9PCPQhCJtJGjk/7TC6ckmnSFS+xwTfm4= cloud.google.com/go/beyondcorp v0.3.0/go.mod h1:E5U5lcrcXMsCuoDNyGrpyTm/hn7ne941Jz2vmksAxW8= cloud.google.com/go/beyondcorp v0.4.0/go.mod h1:3ApA0mbhHx6YImmuubf5pyW8srKnCEPON32/5hj+RmM= cloud.google.com/go/beyondcorp v0.5.0/go.mod h1:uFqj9X+dSfrheVp7ssLTaRHd2EHqSL4QZmH4e8WXGGU= cloud.google.com/go/beyondcorp v0.6.1/go.mod h1:YhxDWw946SCbmcWo3fAhw3V4XZMSpQ/VYfcKGAEU8/4= cloud.google.com/go/beyondcorp v1.0.0/go.mod h1:YhxDWw946SCbmcWo3fAhw3V4XZMSpQ/VYfcKGAEU8/4= +cloud.google.com/go/beyondcorp v1.0.1/go.mod h1:zl/rWWAFVeV+kx+X2Javly7o1EIQThU4WlkynffL/lk= +cloud.google.com/go/beyondcorp v1.0.2/go.mod h1:m8cpG7caD+5su+1eZr+TSvF6r21NdLJk4f9u4SP2Ntc= +cloud.google.com/go/beyondcorp v1.0.3/go.mod h1:HcBvnEd7eYr+HGDd5ZbuVmBYX019C6CEXBonXbCVwJo= cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o= cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE= cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= @@ -156,6 +210,8 @@ cloud.google.com/go/bigquery v1.50.0/go.mod h1:YrleYEh2pSEbgTBZYMJ5SuSr0ML3ypjRB cloud.google.com/go/bigquery v1.52.0/go.mod h1:3b/iXjRQGU4nKa87cXeg6/gogLjO8C6PmuM8i5Bi/u4= cloud.google.com/go/bigquery v1.53.0/go.mod h1:3b/iXjRQGU4nKa87cXeg6/gogLjO8C6PmuM8i5Bi/u4= cloud.google.com/go/bigquery v1.55.0/go.mod h1:9Y5I3PN9kQWuid6183JFhOGOW3GcirA5LpsKCUn+2ec= +cloud.google.com/go/bigquery v1.56.0/go.mod h1:KDcsploXTEY7XT3fDQzMUZlpQLHzE4itubHrnmhUrZA= +cloud.google.com/go/bigquery v1.57.1/go.mod h1:iYzC0tGVWt1jqSzBHqCr3lrRn0u13E8e+AqowBsDgug= cloud.google.com/go/billing v1.4.0/go.mod h1:g9IdKBEFlItS8bTtlrZdVLWSSdSyFUZKXNS02zKMOZY= cloud.google.com/go/billing v1.5.0/go.mod h1:mztb1tBc3QekhjSgmpf/CV4LzWXLzCArwpLmP2Gm88s= cloud.google.com/go/billing v1.6.0/go.mod h1:WoXzguj+BeHXPbKfNWkqVtDdzORazmCjraY+vrxcyvI= @@ -164,6 +220,10 @@ cloud.google.com/go/billing v1.12.0/go.mod h1:yKrZio/eu+okO/2McZEbch17O5CB5NpZhh cloud.google.com/go/billing v1.13.0/go.mod h1:7kB2W9Xf98hP9Sr12KfECgfGclsH3CQR0R08tnRlRbc= cloud.google.com/go/billing v1.16.0/go.mod h1:y8vx09JSSJG02k5QxbycNRrN7FGZB6F3CAcgum7jvGA= cloud.google.com/go/billing v1.17.0/go.mod h1:Z9+vZXEq+HwH7bhJkyI4OQcR6TSbeMrjlpEjO2vzY64= +cloud.google.com/go/billing v1.17.1/go.mod h1:Z9+vZXEq+HwH7bhJkyI4OQcR6TSbeMrjlpEjO2vzY64= +cloud.google.com/go/billing v1.17.2/go.mod h1:u/AdV/3wr3xoRBk5xvUzYMS1IawOAPwQMuHgHMdljDg= +cloud.google.com/go/billing v1.17.3/go.mod h1:z83AkoZ7mZwBGT3yTnt6rSGI1OOsHSIi6a5M3mJ8NaU= +cloud.google.com/go/billing v1.17.4/go.mod h1:5DOYQStCxquGprqfuid/7haD7th74kyMBHkjO/OvDtk= cloud.google.com/go/binaryauthorization v1.1.0/go.mod h1:xwnoWu3Y84jbuHa0zd526MJYmtnVXn0syOjaJgy4+dM= cloud.google.com/go/binaryauthorization v1.2.0/go.mod h1:86WKkJHtRcv5ViNABtYMhhNWRrD1Vpi//uKEy7aYEfI= cloud.google.com/go/binaryauthorization v1.3.0/go.mod h1:lRZbKgjDIIQvzYQS1p99A7/U1JqvqeZg0wiI5tp6tg0= @@ -171,16 +231,25 @@ cloud.google.com/go/binaryauthorization v1.4.0/go.mod h1:tsSPQrBd77VLplV70GUhBf/ cloud.google.com/go/binaryauthorization v1.5.0/go.mod h1:OSe4OU1nN/VswXKRBmciKpo9LulY41gch5c68htf3/Q= cloud.google.com/go/binaryauthorization v1.6.1/go.mod h1:TKt4pa8xhowwffiBmbrbcxijJRZED4zrqnwZ1lKH51U= cloud.google.com/go/binaryauthorization v1.7.0/go.mod h1:Zn+S6QqTMn6odcMU1zDZCJxPjU2tZPV1oDl45lWY154= +cloud.google.com/go/binaryauthorization v1.7.1/go.mod h1:GTAyfRWYgcbsP3NJogpV3yeunbUIjx2T9xVeYovtURE= +cloud.google.com/go/binaryauthorization v1.7.2/go.mod h1:kFK5fQtxEp97m92ziy+hbu+uKocka1qRRL8MVJIgjv0= +cloud.google.com/go/binaryauthorization v1.7.3/go.mod h1:VQ/nUGRKhrStlGr+8GMS8f6/vznYLkdK5vaKfdCIpvU= cloud.google.com/go/certificatemanager v1.3.0/go.mod h1:n6twGDvcUBFu9uBgt4eYvvf3sQ6My8jADcOVwHmzadg= cloud.google.com/go/certificatemanager v1.4.0/go.mod h1:vowpercVFyqs8ABSmrdV+GiFf2H/ch3KyudYQEMM590= cloud.google.com/go/certificatemanager v1.6.0/go.mod h1:3Hh64rCKjRAX8dXgRAyOcY5vQ/fE1sh8o+Mdd6KPgY8= cloud.google.com/go/certificatemanager v1.7.1/go.mod h1:iW8J3nG6SaRYImIa+wXQ0g8IgoofDFRp5UMzaNk1UqI= +cloud.google.com/go/certificatemanager v1.7.2/go.mod h1:15SYTDQMd00kdoW0+XY5d9e+JbOPjp24AvF48D8BbcQ= +cloud.google.com/go/certificatemanager v1.7.3/go.mod h1:T/sZYuC30PTag0TLo28VedIRIj1KPGcOQzjWAptHa00= +cloud.google.com/go/certificatemanager v1.7.4/go.mod h1:FHAylPe/6IIKuaRmHbjbdLhGhVQ+CWHSD5Jq0k4+cCE= cloud.google.com/go/channel v1.8.0/go.mod h1:W5SwCXDJsq/rg3tn3oG0LOxpAo6IMxNa09ngphpSlnk= cloud.google.com/go/channel v1.9.0/go.mod h1:jcu05W0my9Vx4mt3/rEHpfxc9eKi9XwsdDL8yBMbKUk= cloud.google.com/go/channel v1.11.0/go.mod h1:IdtI0uWGqhEeatSB62VOoJ8FSUhJ9/+iGkJVqp74CGE= cloud.google.com/go/channel v1.12.0/go.mod h1:VkxCGKASi4Cq7TbXxlaBezonAYpp1GCnKMY6tnMQnLU= cloud.google.com/go/channel v1.16.0/go.mod h1:eN/q1PFSl5gyu0dYdmxNXscY/4Fi7ABmeHCJNf/oHmc= cloud.google.com/go/channel v1.17.0/go.mod h1:RpbhJsGi/lXWAUM1eF4IbQGbsfVlg2o8Iiy2/YLfVT0= +cloud.google.com/go/channel v1.17.1/go.mod h1:xqfzcOZAcP4b/hUDH0GkGg1Sd5to6di1HOJn/pi5uBQ= +cloud.google.com/go/channel v1.17.2/go.mod h1:aT2LhnftnyfQceFql5I/mP8mIbiiJS4lWqgXA815zMk= +cloud.google.com/go/channel v1.17.3/go.mod h1:QcEBuZLGGrUMm7kNj9IbU1ZfmJq2apotsV83hbxX7eE= cloud.google.com/go/cloudbuild v1.3.0/go.mod h1:WequR4ULxlqvMsjDEEEFnOG5ZSRSgWOywXYDb1vPE6U= cloud.google.com/go/cloudbuild v1.4.0/go.mod h1:5Qwa40LHiOXmz3386FrjrYM93rM/hdRr7b53sySrTqA= cloud.google.com/go/cloudbuild v1.6.0/go.mod h1:UIbc/w9QCbH12xX+ezUsgblrWv+Cv4Tw83GiSMHOn9M= @@ -189,11 +258,17 @@ cloud.google.com/go/cloudbuild v1.9.0/go.mod h1:qK1d7s4QlO0VwfYn5YuClDGg2hfmLZEb cloud.google.com/go/cloudbuild v1.10.1/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= cloud.google.com/go/cloudbuild v1.13.0/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= cloud.google.com/go/cloudbuild v1.14.0/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= +cloud.google.com/go/cloudbuild v1.14.1/go.mod h1:K7wGc/3zfvmYWOWwYTgF/d/UVJhS4pu+HAy7PL7mCsU= +cloud.google.com/go/cloudbuild v1.14.2/go.mod h1:Bn6RO0mBYk8Vlrt+8NLrru7WXlQ9/RDWz2uo5KG1/sg= +cloud.google.com/go/cloudbuild v1.14.3/go.mod h1:eIXYWmRt3UtggLnFGx4JvXcMj4kShhVzGndL1LwleEM= cloud.google.com/go/clouddms v1.3.0/go.mod h1:oK6XsCDdW4Ib3jCCBugx+gVjevp2TMXFtgxvPSee3OM= cloud.google.com/go/clouddms v1.4.0/go.mod h1:Eh7sUGCC+aKry14O1NRljhjyrr0NFC0G2cjwX0cByRk= cloud.google.com/go/clouddms v1.5.0/go.mod h1:QSxQnhikCLUw13iAbffF2CZxAER3xDGNHjsTAkQJcQA= cloud.google.com/go/clouddms v1.6.1/go.mod h1:Ygo1vL52Ov4TBZQquhz5fiw2CQ58gvu+PlS6PVXCpZI= cloud.google.com/go/clouddms v1.7.0/go.mod h1:MW1dC6SOtI/tPNCciTsXtsGNEM0i0OccykPvv3hiYeM= +cloud.google.com/go/clouddms v1.7.1/go.mod h1:o4SR8U95+P7gZ/TX+YbJxehOCsM+fe6/brlrFquiszk= +cloud.google.com/go/clouddms v1.7.2/go.mod h1:Rk32TmWmHo64XqDvW7jgkFQet1tUKNVzs7oajtJT3jU= +cloud.google.com/go/clouddms v1.7.3/go.mod h1:fkN2HQQNUYInAU3NQ3vRLkV2iWs8lIdmBKOx4nrL6Hc= cloud.google.com/go/cloudtasks v1.5.0/go.mod h1:fD92REy1x5woxkKEkLdvavGnPJGEn8Uic9nWuLzqCpY= cloud.google.com/go/cloudtasks v1.6.0/go.mod h1:C6Io+sxuke9/KNRkbQpihnW93SWDU3uXt92nu85HkYI= cloud.google.com/go/cloudtasks v1.7.0/go.mod h1:ImsfdYWwlWNJbdgPIIGJWC+gemEGTBK/SunNQQNCAb4= @@ -202,6 +277,9 @@ cloud.google.com/go/cloudtasks v1.9.0/go.mod h1:w+EyLsVkLWHcOaqNEyvcKAsWp9p29dL6 cloud.google.com/go/cloudtasks v1.10.0/go.mod h1:NDSoTLkZ3+vExFEWu2UJV1arUyzVDAiZtdWcsUyNwBs= cloud.google.com/go/cloudtasks v1.11.1/go.mod h1:a9udmnou9KO2iulGscKR0qBYjreuX8oHwpmFsKspEvM= cloud.google.com/go/cloudtasks v1.12.1/go.mod h1:a9udmnou9KO2iulGscKR0qBYjreuX8oHwpmFsKspEvM= +cloud.google.com/go/cloudtasks v1.12.2/go.mod h1:A7nYkjNlW2gUoROg1kvJrQGhJP/38UaWwsnuBDOBVUk= +cloud.google.com/go/cloudtasks v1.12.3/go.mod h1:GPVXhIOSGEaR+3xT4Fp72ScI+HjHffSS4B8+BaBB5Ys= +cloud.google.com/go/cloudtasks v1.12.4/go.mod h1:BEPu0Gtt2dU6FxZHNqqNdGqIG86qyWKBPGnsb7udGY0= cloud.google.com/go/compute v0.1.0/go.mod h1:GAesmwr110a34z04OlxYkATPBEfVhkymfTBXtfbBFow= cloud.google.com/go/compute v1.3.0/go.mod h1:cCZiE1NHEtai4wiufUhW8I8S1JKkAnhnQJWM7YD99wM= cloud.google.com/go/compute v1.5.0/go.mod h1:9SMHyhJlzhlkJqrPAc839t2BZFTSk6Jdj6mkzQJeu0M= @@ -219,7 +297,11 @@ cloud.google.com/go/compute v1.19.0/go.mod h1:rikpw2y+UMidAe9tISo04EHNOIf42RLYF/ cloud.google.com/go/compute v1.19.1/go.mod h1:6ylj3a05WF8leseCdIf77NK0g1ey+nj5IKd5/kvShxE= cloud.google.com/go/compute v1.19.3/go.mod h1:qxvISKp/gYnXkSAD1ppcSOveRAmzxicEv/JlizULFrI= cloud.google.com/go/compute v1.20.1/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= +cloud.google.com/go/compute v1.21.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= cloud.google.com/go/compute v1.23.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= +cloud.google.com/go/compute v1.23.1/go.mod h1:CqB3xpmPKKt3OJpW2ndFIXnA9A4xAy/F3Xp1ixncW78= +cloud.google.com/go/compute v1.23.2/go.mod h1:JJ0atRC0J/oWYiiVBmsSsrRnh92DhZPG4hFDcR04Rns= +cloud.google.com/go/compute v1.23.3/go.mod h1:VCgBUoMnIVIR0CscqQiPJLAG25E3ZRZMzcFZeQ+h8CI= cloud.google.com/go/compute/metadata v0.1.0/go.mod h1:Z1VN+bulIf6bt4P/C37K4DyZYZEXYonfTBHHFPO/4UU= cloud.google.com/go/compute/metadata v0.2.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/compute/metadata v0.2.1/go.mod h1:jgHgmJd2RKBGzXqF5LR2EZMGxBkeanZ9wwa75XHJgOM= @@ -229,6 +311,10 @@ cloud.google.com/go/contactcenterinsights v1.4.0/go.mod h1:L2YzkGbPsv+vMQMCADxJo cloud.google.com/go/contactcenterinsights v1.6.0/go.mod h1:IIDlT6CLcDoyv79kDv8iWxMSTZhLxSCofVV5W6YFM/w= cloud.google.com/go/contactcenterinsights v1.9.1/go.mod h1:bsg/R7zGLYMVxFFzfh9ooLTruLRCG9fnzhH9KznHhbM= cloud.google.com/go/contactcenterinsights v1.10.0/go.mod h1:bsg/R7zGLYMVxFFzfh9ooLTruLRCG9fnzhH9KznHhbM= +cloud.google.com/go/contactcenterinsights v1.11.0/go.mod h1:hutBdImE4XNZ1NV4vbPJKSFOnQruhC5Lj9bZqWMTKiU= +cloud.google.com/go/contactcenterinsights v1.11.1/go.mod h1:FeNP3Kg8iteKM80lMwSk3zZZKVxr+PGnAId6soKuXwE= +cloud.google.com/go/contactcenterinsights v1.11.2/go.mod h1:A9PIR5ov5cRcd28KlDbmmXE8Aay+Gccer2h4wzkYFso= +cloud.google.com/go/contactcenterinsights v1.11.3/go.mod h1:HHX5wrz5LHVAwfI2smIotQG9x8Qd6gYilaHcLLLmNis= cloud.google.com/go/container v1.6.0/go.mod h1:Xazp7GjJSeUYo688S+6J5V+n/t+G5sKBTFkKNudGRxg= cloud.google.com/go/container v1.7.0/go.mod h1:Dp5AHtmothHGX3DwwIHPgq45Y8KmNsgN3amoYfxVkLo= cloud.google.com/go/container v1.13.1/go.mod h1:6wgbMPeQRw9rSnKBCAJXnds3Pzj03C4JHamr8asWKy4= @@ -237,12 +323,18 @@ cloud.google.com/go/container v1.15.0/go.mod h1:ft+9S0WGjAyjDggg5S06DXj+fHJICWg8 cloud.google.com/go/container v1.22.1/go.mod h1:lTNExE2R7f+DLbAN+rJiKTisauFCaoDq6NURZ83eVH4= cloud.google.com/go/container v1.24.0/go.mod h1:lTNExE2R7f+DLbAN+rJiKTisauFCaoDq6NURZ83eVH4= cloud.google.com/go/container v1.26.0/go.mod h1:YJCmRet6+6jnYYRS000T6k0D0xUXQgBSaJ7VwI8FBj4= +cloud.google.com/go/container v1.26.1/go.mod h1:5smONjPRUxeEpDG7bMKWfDL4sauswqEtnBK1/KKpR04= +cloud.google.com/go/container v1.26.2/go.mod h1:YlO84xCt5xupVbLaMY4s3XNE79MUJ+49VmkInr6HvF4= +cloud.google.com/go/container v1.27.1/go.mod h1:b1A1gJeTBXVLQ6GGw9/9M4FG94BEGsqJ5+t4d/3N7O4= cloud.google.com/go/containeranalysis v0.5.1/go.mod h1:1D92jd8gRR/c0fGMlymRgxWD3Qw9C1ff6/T7mLgVL8I= cloud.google.com/go/containeranalysis v0.6.0/go.mod h1:HEJoiEIu+lEXM+k7+qLCci0h33lX3ZqoYFdmPcoO7s4= cloud.google.com/go/containeranalysis v0.7.0/go.mod h1:9aUL+/vZ55P2CXfuZjS4UjQ9AgXoSw8Ts6lemfmxBxI= cloud.google.com/go/containeranalysis v0.9.0/go.mod h1:orbOANbwk5Ejoom+s+DUCTTJ7IBdBQJDcSylAx/on9s= cloud.google.com/go/containeranalysis v0.10.1/go.mod h1:Ya2jiILITMY68ZLPaogjmOMNkwsDrWBSTyBubGXO7j0= cloud.google.com/go/containeranalysis v0.11.0/go.mod h1:4n2e99ZwpGxpNcz+YsFT1dfOHPQFGcAC8FN2M2/ne/U= +cloud.google.com/go/containeranalysis v0.11.1/go.mod h1:rYlUOM7nem1OJMKwE1SadufX0JP3wnXj844EtZAwWLY= +cloud.google.com/go/containeranalysis v0.11.2/go.mod h1:xibioGBC1MD2j4reTyV1xY1/MvKaz+fyM9ENWhmIeP8= +cloud.google.com/go/containeranalysis v0.11.3/go.mod h1:kMeST7yWFQMGjiG9K7Eov+fPNQcGhb8mXj/UcTiWw9U= cloud.google.com/go/datacatalog v1.3.0/go.mod h1:g9svFY6tuR+j+hrTw3J2dNcmI0dzmSiyOzm8kpLq0a0= cloud.google.com/go/datacatalog v1.5.0/go.mod h1:M7GPLNQeLfWqeIm3iuiruhPzkt65+Bx8dAKvScX8jvs= cloud.google.com/go/datacatalog v1.6.0/go.mod h1:+aEyF8JKg+uXcIdAmmaMUmZ3q1b/lKLtXCmXdnc0lbc= @@ -255,24 +347,40 @@ cloud.google.com/go/datacatalog v1.14.0/go.mod h1:h0PrGtlihoutNMp/uvwhawLQ9+c63K cloud.google.com/go/datacatalog v1.14.1/go.mod h1:d2CevwTG4yedZilwe+v3E3ZBDRMobQfSG/a6cCCN5R4= cloud.google.com/go/datacatalog v1.16.0/go.mod h1:d2CevwTG4yedZilwe+v3E3ZBDRMobQfSG/a6cCCN5R4= cloud.google.com/go/datacatalog v1.17.1/go.mod h1:nCSYFHgtxh2MiEktWIz71s/X+7ds/UT9kp0PC7waCzE= +cloud.google.com/go/datacatalog v1.18.0/go.mod h1:nCSYFHgtxh2MiEktWIz71s/X+7ds/UT9kp0PC7waCzE= +cloud.google.com/go/datacatalog v1.18.1/go.mod h1:TzAWaz+ON1tkNr4MOcak8EBHX7wIRX/gZKM+yTVsv+A= +cloud.google.com/go/datacatalog v1.18.2/go.mod h1:SPVgWW2WEMuWHA+fHodYjmxPiMqcOiWfhc9OD5msigk= +cloud.google.com/go/datacatalog v1.18.3/go.mod h1:5FR6ZIF8RZrtml0VUao22FxhdjkoG+a0866rEnObryM= cloud.google.com/go/dataflow v0.6.0/go.mod h1:9QwV89cGoxjjSR9/r7eFDqqjtvbKxAK2BaYU6PVk9UM= cloud.google.com/go/dataflow v0.7.0/go.mod h1:PX526vb4ijFMesO1o202EaUmouZKBpjHsTlCtB4parQ= cloud.google.com/go/dataflow v0.8.0/go.mod h1:Rcf5YgTKPtQyYz8bLYhFoIV/vP39eL7fWNcSOyFfLJE= cloud.google.com/go/dataflow v0.9.1/go.mod h1:Wp7s32QjYuQDWqJPFFlnBKhkAtiFpMTdg00qGbnIHVw= +cloud.google.com/go/dataflow v0.9.2/go.mod h1:vBfdBZ/ejlTaYIGB3zB4T08UshH70vbtZeMD+urnUSo= +cloud.google.com/go/dataflow v0.9.3/go.mod h1:HI4kMVjcHGTs3jTHW/kv3501YW+eloiJSLxkJa/vqFE= +cloud.google.com/go/dataflow v0.9.4/go.mod h1:4G8vAkHYCSzU8b/kmsoR2lWyHJD85oMJPHMtan40K8w= cloud.google.com/go/dataform v0.3.0/go.mod h1:cj8uNliRlHpa6L3yVhDOBrUXH+BPAO1+KFMQQNSThKo= cloud.google.com/go/dataform v0.4.0/go.mod h1:fwV6Y4Ty2yIFL89huYlEkwUPtS7YZinZbzzj5S9FzCE= cloud.google.com/go/dataform v0.5.0/go.mod h1:GFUYRe8IBa2hcomWplodVmUx/iTL0FrsauObOM3Ipr0= cloud.google.com/go/dataform v0.6.0/go.mod h1:QPflImQy33e29VuapFdf19oPbE4aYTJxr31OAPV+ulA= cloud.google.com/go/dataform v0.7.0/go.mod h1:7NulqnVozfHvWUBpMDfKMUESr+85aJsC/2O0o3jWPDE= cloud.google.com/go/dataform v0.8.1/go.mod h1:3BhPSiw8xmppbgzeBbmDvmSWlwouuJkXsXsb8UBih9M= +cloud.google.com/go/dataform v0.8.2/go.mod h1:X9RIqDs6NbGPLR80tnYoPNiO1w0wenKTb8PxxlhTMKM= +cloud.google.com/go/dataform v0.8.3/go.mod h1:8nI/tvv5Fso0drO3pEjtowz58lodx8MVkdV2q0aPlqg= +cloud.google.com/go/dataform v0.9.1/go.mod h1:pWTg+zGQ7i16pyn0bS1ruqIE91SdL2FDMvEYu/8oQxs= cloud.google.com/go/datafusion v1.4.0/go.mod h1:1Zb6VN+W6ALo85cXnM1IKiPw+yQMKMhB9TsTSRDo/38= cloud.google.com/go/datafusion v1.5.0/go.mod h1:Kz+l1FGHB0J+4XF2fud96WMmRiq/wj8N9u007vyXZ2w= cloud.google.com/go/datafusion v1.6.0/go.mod h1:WBsMF8F1RhSXvVM8rCV3AeyWVxcC2xY6vith3iw3S+8= cloud.google.com/go/datafusion v1.7.1/go.mod h1:KpoTBbFmoToDExJUso/fcCiguGDk7MEzOWXUsJo0wsI= +cloud.google.com/go/datafusion v1.7.2/go.mod h1:62K2NEC6DRlpNmI43WHMWf9Vg/YvN6QVi8EVwifElI0= +cloud.google.com/go/datafusion v1.7.3/go.mod h1:eoLt1uFXKGBq48jy9LZ+Is8EAVLnmn50lNncLzwYokE= +cloud.google.com/go/datafusion v1.7.4/go.mod h1:BBs78WTOLYkT4GVZIXQCZT3GFpkpDN4aBY4NDX/jVlM= cloud.google.com/go/datalabeling v0.5.0/go.mod h1:TGcJ0G2NzcsXSE/97yWjIZO0bXj0KbVlINXMG9ud42I= cloud.google.com/go/datalabeling v0.6.0/go.mod h1:WqdISuk/+WIGeMkpw/1q7bK/tFEZxsrFJOJdY2bXvTQ= cloud.google.com/go/datalabeling v0.7.0/go.mod h1:WPQb1y08RJbmpM3ww0CSUAGweL0SxByuW2E+FU+wXcM= cloud.google.com/go/datalabeling v0.8.1/go.mod h1:XS62LBSVPbYR54GfYQsPXZjTW8UxCK2fkDciSrpRFdY= +cloud.google.com/go/datalabeling v0.8.2/go.mod h1:cyDvGHuJWu9U/cLDA7d8sb9a0tWLEletStu2sTmg3BE= +cloud.google.com/go/datalabeling v0.8.3/go.mod h1:tvPhpGyS/V7lqjmb3V0TaDdGvhzgR1JoW7G2bpi2UTI= +cloud.google.com/go/datalabeling v0.8.4/go.mod h1:Z1z3E6LHtffBGrNUkKwbwbDxTiXEApLzIgmymj8A3S8= cloud.google.com/go/dataplex v1.3.0/go.mod h1:hQuRtDg+fCiFgC8j0zV222HvzFQdRd+SVX8gdmFcZzA= cloud.google.com/go/dataplex v1.4.0/go.mod h1:X51GfLXEMVJ6UN47ESVqvlsRplbLhcsAt0kZCCKsU0A= cloud.google.com/go/dataplex v1.5.2/go.mod h1:cVMgQHsmfRoI5KFYq4JtIBEUbYwc3c7tXmIDhRmNNVQ= @@ -280,15 +388,24 @@ cloud.google.com/go/dataplex v1.6.0/go.mod h1:bMsomC/aEJOSpHXdFKFGQ1b0TDPIeL28nJ cloud.google.com/go/dataplex v1.8.1/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= cloud.google.com/go/dataplex v1.9.0/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= cloud.google.com/go/dataplex v1.9.1/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= +cloud.google.com/go/dataplex v1.10.1/go.mod h1:1MzmBv8FvjYfc7vDdxhnLFNskikkB+3vl475/XdCDhs= +cloud.google.com/go/dataplex v1.10.2/go.mod h1:xdC8URdTrCrZMW6keY779ZT1cTOfV8KEPNsw+LTRT1Y= +cloud.google.com/go/dataplex v1.11.1/go.mod h1:mHJYQQ2VEJHsyoC0OdNyy988DvEbPhqFs5OOLffLX0c= cloud.google.com/go/dataproc v1.7.0/go.mod h1:CKAlMjII9H90RXaMpSxQ8EU6dQx6iAYNPcYPOkSbi8s= cloud.google.com/go/dataproc v1.8.0/go.mod h1:5OW+zNAH0pMpw14JVrPONsxMQYMBqJuzORhIBfBn9uI= cloud.google.com/go/dataproc v1.12.0/go.mod h1:zrF3aX0uV3ikkMz6z4uBbIKyhRITnxvr4i3IjKsKrw4= cloud.google.com/go/dataproc/v2 v2.0.1/go.mod h1:7Ez3KRHdFGcfY7GcevBbvozX+zyWGcwLJvvAMwCaoZ4= cloud.google.com/go/dataproc/v2 v2.2.0/go.mod h1:lZR7AQtwZPvmINx5J87DSOOpTfof9LVZju6/Qo4lmcY= +cloud.google.com/go/dataproc/v2 v2.2.1/go.mod h1:QdAJLaBjh+l4PVlVZcmrmhGccosY/omC1qwfQ61Zv/o= +cloud.google.com/go/dataproc/v2 v2.2.2/go.mod h1:aocQywVmQVF4i8CL740rNI/ZRpsaaC1Wh2++BJ7HEJ4= +cloud.google.com/go/dataproc/v2 v2.2.3/go.mod h1:G5R6GBc9r36SXv/RtZIVfB8SipI+xVn0bX5SxUzVYbY= cloud.google.com/go/dataqna v0.5.0/go.mod h1:90Hyk596ft3zUQ8NkFfvICSIfHFh1Bc7C4cK3vbhkeo= cloud.google.com/go/dataqna v0.6.0/go.mod h1:1lqNpM7rqNLVgWBJyk5NF6Uen2PHym0jtVJonplVsDA= cloud.google.com/go/dataqna v0.7.0/go.mod h1:Lx9OcIIeqCrw1a6KdO3/5KMP1wAmTc0slZWwP12Qq3c= cloud.google.com/go/dataqna v0.8.1/go.mod h1:zxZM0Bl6liMePWsHA8RMGAfmTG34vJMapbHAxQ5+WA8= +cloud.google.com/go/dataqna v0.8.2/go.mod h1:KNEqgx8TTmUipnQsScOoDpq/VlXVptUqVMZnt30WAPs= +cloud.google.com/go/dataqna v0.8.3/go.mod h1:wXNBW2uvc9e7Gl5k8adyAMnLush1KVV6lZUhB+rqNu4= +cloud.google.com/go/dataqna v0.8.4/go.mod h1:mySRKjKg5Lz784P6sCov3p1QD+RZQONRMRjzGNcFd0c= cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE= cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= cloud.google.com/go/datastore v1.10.0/go.mod h1:PC5UzAmDEkAmkfaknstTYbNpgE49HAgW2J1gcgUfmdM= @@ -297,6 +414,7 @@ cloud.google.com/go/datastore v1.12.0/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1 cloud.google.com/go/datastore v1.12.1/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1EoLgSp6/N70= cloud.google.com/go/datastore v1.13.0/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1EoLgSp6/N70= cloud.google.com/go/datastore v1.14.0/go.mod h1:GAeStMBIt9bPS7jMJA85kgkpsMkvseWWXiaHya9Jes8= +cloud.google.com/go/datastore v1.15.0/go.mod h1:GAeStMBIt9bPS7jMJA85kgkpsMkvseWWXiaHya9Jes8= cloud.google.com/go/datastream v1.2.0/go.mod h1:i/uTP8/fZwgATHS/XFu0TcNUhuA0twZxxQ3EyCUQMwo= cloud.google.com/go/datastream v1.3.0/go.mod h1:cqlOX8xlyYF/uxhiKn6Hbv6WjwPPuI9W2M9SAXwaLLQ= cloud.google.com/go/datastream v1.4.0/go.mod h1:h9dpzScPhDTs5noEMQVWP8Wx8AFBRyS0s8KWPx/9r0g= @@ -305,12 +423,18 @@ cloud.google.com/go/datastream v1.6.0/go.mod h1:6LQSuswqLa7S4rPAOZFVjHIG3wJIjZcZ cloud.google.com/go/datastream v1.7.0/go.mod h1:uxVRMm2elUSPuh65IbZpzJNMbuzkcvu5CjMqVIUHrww= cloud.google.com/go/datastream v1.9.1/go.mod h1:hqnmr8kdUBmrnk65k5wNRoHSCYksvpdZIcZIEl8h43Q= cloud.google.com/go/datastream v1.10.0/go.mod h1:hqnmr8kdUBmrnk65k5wNRoHSCYksvpdZIcZIEl8h43Q= +cloud.google.com/go/datastream v1.10.1/go.mod h1:7ngSYwnw95YFyTd5tOGBxHlOZiL+OtpjheqU7t2/s/c= +cloud.google.com/go/datastream v1.10.2/go.mod h1:W42TFgKAs/om6x/CdXX5E4oiAsKlH+e8MTGy81zdYt0= +cloud.google.com/go/datastream v1.10.3/go.mod h1:YR0USzgjhqA/Id0Ycu1VvZe8hEWwrkjuXrGbzeDOSEA= cloud.google.com/go/deploy v1.4.0/go.mod h1:5Xghikd4VrmMLNaF6FiRFDlHb59VM59YoDQnOUdsH/c= cloud.google.com/go/deploy v1.5.0/go.mod h1:ffgdD0B89tToyW/U/D2eL0jN2+IEV/3EMuXHA0l4r+s= cloud.google.com/go/deploy v1.6.0/go.mod h1:f9PTHehG/DjCom3QH0cntOVRm93uGBDt2vKzAPwpXQI= cloud.google.com/go/deploy v1.8.0/go.mod h1:z3myEJnA/2wnB4sgjqdMfgxCA0EqC3RBTNcVPs93mtQ= cloud.google.com/go/deploy v1.11.0/go.mod h1:tKuSUV5pXbn67KiubiUNUejqLs4f5cxxiCNCeyl0F2g= cloud.google.com/go/deploy v1.13.0/go.mod h1:tKuSUV5pXbn67KiubiUNUejqLs4f5cxxiCNCeyl0F2g= +cloud.google.com/go/deploy v1.13.1/go.mod h1:8jeadyLkH9qu9xgO3hVWw8jVr29N1mnW42gRJT8GY6g= +cloud.google.com/go/deploy v1.14.1/go.mod h1:N8S0b+aIHSEeSr5ORVoC0+/mOPUysVt8ae4QkZYolAw= +cloud.google.com/go/deploy v1.14.2/go.mod h1:e5XOUI5D+YGldyLNZ21wbp9S8otJbBE4i88PtO9x/2g= cloud.google.com/go/dialogflow v1.15.0/go.mod h1:HbHDWs33WOGJgn6rfzBW1Kv807BE3O1+xGbn59zZWI4= cloud.google.com/go/dialogflow v1.16.1/go.mod h1:po6LlzGfK+smoSmTBnbkIZY2w8ffjz/RcGSS+sh1el0= cloud.google.com/go/dialogflow v1.17.0/go.mod h1:YNP09C/kXA1aZdBgC/VtXX74G/TKn7XVCcVumTflA+8= @@ -322,10 +446,17 @@ cloud.google.com/go/dialogflow v1.32.0/go.mod h1:jG9TRJl8CKrDhMEcvfcfFkkpp8ZhgPz cloud.google.com/go/dialogflow v1.38.0/go.mod h1:L7jnH+JL2mtmdChzAIcXQHXMvQkE3U4hTaNltEuxXn4= cloud.google.com/go/dialogflow v1.40.0/go.mod h1:L7jnH+JL2mtmdChzAIcXQHXMvQkE3U4hTaNltEuxXn4= cloud.google.com/go/dialogflow v1.43.0/go.mod h1:pDUJdi4elL0MFmt1REMvFkdsUTYSHq+rTCS8wg0S3+M= +cloud.google.com/go/dialogflow v1.44.0/go.mod h1:pDUJdi4elL0MFmt1REMvFkdsUTYSHq+rTCS8wg0S3+M= +cloud.google.com/go/dialogflow v1.44.1/go.mod h1:n/h+/N2ouKOO+rbe/ZnI186xImpqvCVj2DdsWS/0EAk= +cloud.google.com/go/dialogflow v1.44.2/go.mod h1:QzFYndeJhpVPElnFkUXxdlptx0wPnBWLCBT9BvtC3/c= +cloud.google.com/go/dialogflow v1.44.3/go.mod h1:mHly4vU7cPXVweuB5R0zsYKPMzy240aQdAu06SqBbAQ= cloud.google.com/go/dlp v1.6.0/go.mod h1:9eyB2xIhpU0sVwUixfBubDoRwP+GjeUoxxeueZmqvmM= cloud.google.com/go/dlp v1.7.0/go.mod h1:68ak9vCiMBjbasxeVD17hVPxDEck+ExiHavX8kiHG+Q= cloud.google.com/go/dlp v1.9.0/go.mod h1:qdgmqgTyReTz5/YNSSuueR8pl7hO0o9bQ39ZhtgkWp4= cloud.google.com/go/dlp v1.10.1/go.mod h1:IM8BWz1iJd8njcNcG0+Kyd9OPnqnRNkDV8j42VT5KOI= +cloud.google.com/go/dlp v1.10.2/go.mod h1:ZbdKIhcnyhILgccwVDzkwqybthh7+MplGC3kZVZsIOQ= +cloud.google.com/go/dlp v1.10.3/go.mod h1:iUaTc/ln8I+QT6Ai5vmuwfw8fqTk2kaz0FvCwhLCom0= +cloud.google.com/go/dlp v1.11.1/go.mod h1:/PA2EnioBeXTL/0hInwgj0rfsQb3lpE3R8XUJxqUNKI= cloud.google.com/go/documentai v1.7.0/go.mod h1:lJvftZB5NRiFSX4moiye1SMxHx0Bc3x1+p9e/RfXYiU= cloud.google.com/go/documentai v1.8.0/go.mod h1:xGHNEB7CtsnySCNrCFdCyyMz44RhFEEX2Q7UD0c5IhU= cloud.google.com/go/documentai v1.9.0/go.mod h1:FS5485S8R00U10GhgBC0aNGrJxBP8ZVpEeJ7PQDZd6k= @@ -335,35 +466,55 @@ cloud.google.com/go/documentai v1.18.0/go.mod h1:F6CK6iUH8J81FehpskRmhLq/3VlwQvb cloud.google.com/go/documentai v1.20.0/go.mod h1:yJkInoMcK0qNAEdRnqY/D5asy73tnPe88I1YTZT+a8E= cloud.google.com/go/documentai v1.22.0/go.mod h1:yJkInoMcK0qNAEdRnqY/D5asy73tnPe88I1YTZT+a8E= cloud.google.com/go/documentai v1.22.1/go.mod h1:LKs22aDHbJv7ufXuPypzRO7rG3ALLJxzdCXDPutw4Qc= +cloud.google.com/go/documentai v1.23.0/go.mod h1:LKs22aDHbJv7ufXuPypzRO7rG3ALLJxzdCXDPutw4Qc= +cloud.google.com/go/documentai v1.23.2/go.mod h1:Q/wcRT+qnuXOpjAkvOV4A+IeQl04q2/ReT7SSbytLSo= +cloud.google.com/go/documentai v1.23.4/go.mod h1:4MYAaEMnADPN1LPN5xboDR5QVB6AgsaxgFdJhitlE2Y= +cloud.google.com/go/documentai v1.23.5/go.mod h1:ghzBsyVTiVdkfKaUCum/9bGBEyBjDO4GfooEcYKhN+g= cloud.google.com/go/domains v0.6.0/go.mod h1:T9Rz3GasrpYk6mEGHh4rymIhjlnIuB4ofT1wTxDeT4Y= cloud.google.com/go/domains v0.7.0/go.mod h1:PtZeqS1xjnXuRPKE/88Iru/LdfoRyEHYA9nFQf4UKpg= cloud.google.com/go/domains v0.8.0/go.mod h1:M9i3MMDzGFXsydri9/vW+EWz9sWb4I6WyHqdlAk0idE= cloud.google.com/go/domains v0.9.1/go.mod h1:aOp1c0MbejQQ2Pjf1iJvnVyT+z6R6s8pX66KaCSDYfE= +cloud.google.com/go/domains v0.9.2/go.mod h1:3YvXGYzZG1Temjbk7EyGCuGGiXHJwVNmwIf+E/cUp5I= +cloud.google.com/go/domains v0.9.3/go.mod h1:29k66YNDLDY9LCFKpGFeh6Nj9r62ZKm5EsUJxAl84KU= +cloud.google.com/go/domains v0.9.4/go.mod h1:27jmJGShuXYdUNjyDG0SodTfT5RwLi7xmH334Gvi3fY= cloud.google.com/go/edgecontainer v0.1.0/go.mod h1:WgkZ9tp10bFxqO8BLPqv2LlfmQF1X8lZqwW4r1BTajk= cloud.google.com/go/edgecontainer v0.2.0/go.mod h1:RTmLijy+lGpQ7BXuTDa4C4ssxyXT34NIuHIgKuP4s5w= cloud.google.com/go/edgecontainer v0.3.0/go.mod h1:FLDpP4nykgwwIfcLt6zInhprzw0lEi2P1fjO6Ie0qbc= cloud.google.com/go/edgecontainer v1.0.0/go.mod h1:cttArqZpBB2q58W/upSG++ooo6EsblxDIolxa3jSjbY= cloud.google.com/go/edgecontainer v1.1.1/go.mod h1:O5bYcS//7MELQZs3+7mabRqoWQhXCzenBu0R8bz2rwk= +cloud.google.com/go/edgecontainer v1.1.2/go.mod h1:wQRjIzqxEs9e9wrtle4hQPSR1Y51kqN75dgF7UllZZ4= +cloud.google.com/go/edgecontainer v1.1.3/go.mod h1:Ll2DtIABzEfaxaVSbwj3QHFaOOovlDFiWVDu349jSsA= +cloud.google.com/go/edgecontainer v1.1.4/go.mod h1:AvFdVuZuVGdgaE5YvlL1faAoa1ndRR/5XhXZvPBHbsE= cloud.google.com/go/errorreporting v0.3.0/go.mod h1:xsP2yaAp+OAW4OIm60An2bbLpqIhKXdWR/tawvl7QzU= cloud.google.com/go/essentialcontacts v1.3.0/go.mod h1:r+OnHa5jfj90qIfZDO/VztSFqbQan7HV75p8sA+mdGI= cloud.google.com/go/essentialcontacts v1.4.0/go.mod h1:8tRldvHYsmnBCHdFpvU+GL75oWiBKl80BiqlFh9tp+8= cloud.google.com/go/essentialcontacts v1.5.0/go.mod h1:ay29Z4zODTuwliK7SnX8E86aUF2CTzdNtvv42niCX0M= cloud.google.com/go/essentialcontacts v1.6.2/go.mod h1:T2tB6tX+TRak7i88Fb2N9Ok3PvY3UNbUsMag9/BARh4= +cloud.google.com/go/essentialcontacts v1.6.3/go.mod h1:yiPCD7f2TkP82oJEFXFTou8Jl8L6LBRPeBEkTaO0Ggo= +cloud.google.com/go/essentialcontacts v1.6.4/go.mod h1:iju5Vy3d9tJUg0PYMd1nHhjV7xoCXaOAVabrwLaPBEM= +cloud.google.com/go/essentialcontacts v1.6.5/go.mod h1:jjYbPzw0x+yglXC890l6ECJWdYeZ5dlYACTFL0U/VuM= cloud.google.com/go/eventarc v1.7.0/go.mod h1:6ctpF3zTnaQCxUjHUdcfgcA1A2T309+omHZth7gDfmc= cloud.google.com/go/eventarc v1.8.0/go.mod h1:imbzxkyAU4ubfsaKYdQg04WS1NvncblHEup4kvF+4gw= cloud.google.com/go/eventarc v1.10.0/go.mod h1:u3R35tmZ9HvswGRBnF48IlYgYeBcPUCjkr4BTdem2Kw= cloud.google.com/go/eventarc v1.11.0/go.mod h1:PyUjsUKPWoRBCHeOxZd/lbOOjahV41icXyUY5kSTvVY= cloud.google.com/go/eventarc v1.12.1/go.mod h1:mAFCW6lukH5+IZjkvrEss+jmt2kOdYlN8aMx3sRJiAI= cloud.google.com/go/eventarc v1.13.0/go.mod h1:mAFCW6lukH5+IZjkvrEss+jmt2kOdYlN8aMx3sRJiAI= +cloud.google.com/go/eventarc v1.13.1/go.mod h1:EqBxmGHFrruIara4FUQ3RHlgfCn7yo1HYsu2Hpt/C3Y= +cloud.google.com/go/eventarc v1.13.2/go.mod h1:X9A80ShVu19fb4e5sc/OLV7mpFUKZMwfJFeeWhcIObM= +cloud.google.com/go/eventarc v1.13.3/go.mod h1:RWH10IAZIRcj1s/vClXkBgMHwh59ts7hSWcqD3kaclg= cloud.google.com/go/filestore v1.3.0/go.mod h1:+qbvHGvXU1HaKX2nD0WEPo92TP/8AQuCVEBXNY9z0+w= cloud.google.com/go/filestore v1.4.0/go.mod h1:PaG5oDfo9r224f8OYXURtAsY+Fbyq/bLYoINEK8XQAI= cloud.google.com/go/filestore v1.5.0/go.mod h1:FqBXDWBp4YLHqRnVGveOkHDf8svj9r5+mUDLupOWEDs= cloud.google.com/go/filestore v1.6.0/go.mod h1:di5unNuss/qfZTw2U9nhFqo8/ZDSc466dre85Kydllg= cloud.google.com/go/filestore v1.7.1/go.mod h1:y10jsorq40JJnjR/lQ8AfFbbcGlw3g+Dp8oN7i7FjV4= +cloud.google.com/go/filestore v1.7.2/go.mod h1:TYOlyJs25f/omgj+vY7/tIG/E7BX369triSPzE4LdgE= +cloud.google.com/go/filestore v1.7.3/go.mod h1:Qp8WaEERR3cSkxToxFPHh/b8AACkSut+4qlCjAmKTV0= +cloud.google.com/go/filestore v1.7.4/go.mod h1:S5JCxIbFjeBhWMTfIYH2Jx24J6BqjwpkkPl+nBA5DlI= cloud.google.com/go/firestore v1.9.0/go.mod h1:HMkjKHNTtRyZNiMzu7YAsLr9K3X2udY2AMwDaMEQiiE= cloud.google.com/go/firestore v1.11.0/go.mod h1:b38dKhgzlmNNGTNZZwe7ZRFEuRab1Hay3/DBsIGKKy4= cloud.google.com/go/firestore v1.12.0/go.mod h1:b38dKhgzlmNNGTNZZwe7ZRFEuRab1Hay3/DBsIGKKy4= cloud.google.com/go/firestore v1.13.0/go.mod h1:QojqqOh8IntInDUSTAh0c8ZsPYAr68Ma8c5DWOy8xb8= +cloud.google.com/go/firestore v1.14.0/go.mod h1:96MVaHLsEhbvkBEdZgfN+AS/GIkco1LRpH9Xp9YZfzQ= cloud.google.com/go/functions v1.6.0/go.mod h1:3H1UA3qiIPRWD7PeZKLvHZ9SaQhR26XIJcC0A5GbvAk= cloud.google.com/go/functions v1.7.0/go.mod h1:+d+QBcWM+RsrgZfV9xo6KfA1GlzJfxcfZcRPEhDDfzg= cloud.google.com/go/functions v1.8.0/go.mod h1:RTZ4/HsQjIqIYP9a9YPbU+QFoQsAlYgrwOXJWHn1POY= @@ -372,6 +523,9 @@ cloud.google.com/go/functions v1.10.0/go.mod h1:0D3hEOe3DbEvCXtYOZHQZmD+SzYsi1Yb cloud.google.com/go/functions v1.12.0/go.mod h1:AXWGrF3e2C/5ehvwYo/GH6O5s09tOPksiKhz+hH8WkA= cloud.google.com/go/functions v1.13.0/go.mod h1:EU4O007sQm6Ef/PwRsI8N2umygGqPBS/IZQKBQBcJ3c= cloud.google.com/go/functions v1.15.1/go.mod h1:P5yNWUTkyU+LvW/S9O6V+V423VZooALQlqoXdoPz5AE= +cloud.google.com/go/functions v1.15.2/go.mod h1:CHAjtcR6OU4XF2HuiVeriEdELNcnvRZSk1Q8RMqy4lE= +cloud.google.com/go/functions v1.15.3/go.mod h1:r/AMHwBheapkkySEhiZYLDBwVJCdlRwsm4ieJu35/Ug= +cloud.google.com/go/functions v1.15.4/go.mod h1:CAsTc3VlRMVvx+XqXxKqVevguqJpnVip4DdonFsX28I= cloud.google.com/go/gaming v1.5.0/go.mod h1:ol7rGcxP/qHTRQE/RO4bxkXq+Fix0j6D4LFPzYTIrDM= cloud.google.com/go/gaming v1.6.0/go.mod h1:YMU1GEvA39Qt3zWGyAVA9bpYz/yAhTvaQ1t2sK4KPUA= cloud.google.com/go/gaming v1.7.0/go.mod h1:LrB8U7MHdGgFG851iHAfqUdLcKBdQ55hzXy9xBJz0+w= @@ -383,26 +537,41 @@ cloud.google.com/go/gkebackup v0.3.0/go.mod h1:n/E671i1aOQvUxT541aTkCwExO/bTer2H cloud.google.com/go/gkebackup v0.4.0/go.mod h1:byAyBGUwYGEEww7xsbnUTBHIYcOPy/PgUWUtOeRm9Vg= cloud.google.com/go/gkebackup v1.3.0/go.mod h1:vUDOu++N0U5qs4IhG1pcOnD1Mac79xWy6GoBFlWCWBU= cloud.google.com/go/gkebackup v1.3.1/go.mod h1:vUDOu++N0U5qs4IhG1pcOnD1Mac79xWy6GoBFlWCWBU= +cloud.google.com/go/gkebackup v1.3.2/go.mod h1:OMZbXzEJloyXMC7gqdSB+EOEQ1AKcpGYvO3s1ec5ixk= +cloud.google.com/go/gkebackup v1.3.3/go.mod h1:eMk7/wVV5P22KBakhQnJxWSVftL1p4VBFLpv0kIft7I= +cloud.google.com/go/gkebackup v1.3.4/go.mod h1:gLVlbM8h/nHIs09ns1qx3q3eaXcGSELgNu1DWXYz1HI= cloud.google.com/go/gkeconnect v0.5.0/go.mod h1:c5lsNAg5EwAy7fkqX/+goqFsU1Da/jQFqArp+wGNr/o= cloud.google.com/go/gkeconnect v0.6.0/go.mod h1:Mln67KyU/sHJEBY8kFZ0xTeyPtzbq9StAVvEULYK16A= cloud.google.com/go/gkeconnect v0.7.0/go.mod h1:SNfmVqPkaEi3bF/B3CNZOAYPYdg7sU+obZ+QTky2Myw= cloud.google.com/go/gkeconnect v0.8.1/go.mod h1:KWiK1g9sDLZqhxB2xEuPV8V9NYzrqTUmQR9shJHpOZw= +cloud.google.com/go/gkeconnect v0.8.2/go.mod h1:6nAVhwchBJYgQCXD2pHBFQNiJNyAd/wyxljpaa6ZPrY= +cloud.google.com/go/gkeconnect v0.8.3/go.mod h1:i9GDTrfzBSUZGCe98qSu1B8YB8qfapT57PenIb820Jo= +cloud.google.com/go/gkeconnect v0.8.4/go.mod h1:84hZz4UMlDCKl8ifVW8layK4WHlMAFeq8vbzjU0yJkw= cloud.google.com/go/gkehub v0.9.0/go.mod h1:WYHN6WG8w9bXU0hqNxt8rm5uxnk8IH+lPY9J2TV7BK0= cloud.google.com/go/gkehub v0.10.0/go.mod h1:UIPwxI0DsrpsVoWpLB0stwKCP+WFVG9+y977wO+hBH0= cloud.google.com/go/gkehub v0.11.0/go.mod h1:JOWHlmN+GHyIbuWQPl47/C2RFhnFKH38jH9Ascu3n0E= cloud.google.com/go/gkehub v0.12.0/go.mod h1:djiIwwzTTBrF5NaXCGv3mf7klpEMcST17VBTVVDcuaw= cloud.google.com/go/gkehub v0.14.1/go.mod h1:VEXKIJZ2avzrbd7u+zeMtW00Y8ddk/4V9511C9CQGTY= +cloud.google.com/go/gkehub v0.14.2/go.mod h1:iyjYH23XzAxSdhrbmfoQdePnlMj2EWcvnR+tHdBQsCY= +cloud.google.com/go/gkehub v0.14.3/go.mod h1:jAl6WafkHHW18qgq7kqcrXYzN08hXeK/Va3utN8VKg8= +cloud.google.com/go/gkehub v0.14.4/go.mod h1:Xispfu2MqnnFt8rV/2/3o73SK1snL8s9dYJ9G2oQMfc= cloud.google.com/go/gkemulticloud v0.3.0/go.mod h1:7orzy7O0S+5kq95e4Hpn7RysVA7dPs8W/GgfUtsPbrA= cloud.google.com/go/gkemulticloud v0.4.0/go.mod h1:E9gxVBnseLWCk24ch+P9+B2CoDFJZTyIgLKSalC7tuI= cloud.google.com/go/gkemulticloud v0.5.0/go.mod h1:W0JDkiyi3Tqh0TJr//y19wyb1yf8llHVto2Htf2Ja3Y= cloud.google.com/go/gkemulticloud v0.6.1/go.mod h1:kbZ3HKyTsiwqKX7Yw56+wUGwwNZViRnxWK2DVknXWfw= cloud.google.com/go/gkemulticloud v1.0.0/go.mod h1:kbZ3HKyTsiwqKX7Yw56+wUGwwNZViRnxWK2DVknXWfw= +cloud.google.com/go/gkemulticloud v1.0.1/go.mod h1:AcrGoin6VLKT/fwZEYuqvVominLriQBCKmbjtnbMjG8= +cloud.google.com/go/gkemulticloud v1.0.2/go.mod h1:+ee5VXxKb3H1l4LZAcgWB/rvI16VTNTrInWxDjAGsGo= +cloud.google.com/go/gkemulticloud v1.0.3/go.mod h1:7NpJBN94U6DY1xHIbsDqB2+TFZUfjLUKLjUX8NGLor0= cloud.google.com/go/grafeas v0.2.0/go.mod h1:KhxgtF2hb0P191HlY5besjYm6MqTSTj3LSI+M+ByZHc= cloud.google.com/go/grafeas v0.3.0/go.mod h1:P7hgN24EyONOTMyeJH6DxG4zD7fwiYa5Q6GUgyFSOU8= cloud.google.com/go/gsuiteaddons v1.3.0/go.mod h1:EUNK/J1lZEZO8yPtykKxLXI6JSVN2rg9bN8SXOa0bgM= cloud.google.com/go/gsuiteaddons v1.4.0/go.mod h1:rZK5I8hht7u7HxFQcFei0+AtfS9uSushomRlg+3ua1o= cloud.google.com/go/gsuiteaddons v1.5.0/go.mod h1:TFCClYLd64Eaa12sFVmUyG62tk4mdIsI7pAnSXRkcFo= cloud.google.com/go/gsuiteaddons v1.6.1/go.mod h1:CodrdOqRZcLp5WOwejHWYBjZvfY0kOphkAKpF/3qdZY= +cloud.google.com/go/gsuiteaddons v1.6.2/go.mod h1:K65m9XSgs8hTF3X9nNTPi8IQueljSdYo9F+Mi+s4MyU= +cloud.google.com/go/gsuiteaddons v1.6.3/go.mod h1:sCFJkZoMrLZT3JTb8uJqgKPNshH2tfXeCwTFRebTq48= +cloud.google.com/go/gsuiteaddons v1.6.4/go.mod h1:rxtstw7Fx22uLOXBpsvb9DUbC+fiXs7rF4U29KHM/pE= cloud.google.com/go/iam v0.1.0/go.mod h1:vcUNEa0pEm0qRVpmWepWaFMIAI8/hjB9mO8rNCJtF6c= cloud.google.com/go/iam v0.3.0/go.mod h1:XzJPvDayI+9zsASAFO68Hk07u3z+f+JrT2xXNdp4bnY= cloud.google.com/go/iam v0.5.0/go.mod h1:wPU9Vt0P4UmCux7mqtRu6jcpPAb74cP1fh50J3QpkUc= @@ -416,6 +585,9 @@ cloud.google.com/go/iam v1.0.1/go.mod h1:yR3tmSL8BcZB4bxByRv2jkSIahVmCtfKZwLYGBa cloud.google.com/go/iam v1.1.0/go.mod h1:nxdHjaKfCr7fNYx/HJMM8LgiMugmveWlkatear5gVyk= cloud.google.com/go/iam v1.1.1/go.mod h1:A5avdyVL2tCppe4unb0951eI9jreack+RJ0/d+KUZOU= cloud.google.com/go/iam v1.1.2/go.mod h1:A5avdyVL2tCppe4unb0951eI9jreack+RJ0/d+KUZOU= +cloud.google.com/go/iam v1.1.3/go.mod h1:3khUlaBXfPKKe7huYgEpDn6FtgRyMEqbkvBxrQyY5SE= +cloud.google.com/go/iam v1.1.4/go.mod h1:l/rg8l1AaA+VFMho/HYx2Vv6xinPSLMF8qfhRPIZ0L8= +cloud.google.com/go/iam v1.1.5/go.mod h1:rB6P/Ic3mykPbFio+vo7403drjlgvoWfYpJhMXEbzv8= cloud.google.com/go/iap v1.4.0/go.mod h1:RGFwRJdihTINIe4wZ2iCP0zF/qu18ZwyKxrhMhygBEc= cloud.google.com/go/iap v1.5.0/go.mod h1:UH/CGgKd4KyohZL5Pt0jSKE4m3FR51qg6FKQ/z/Ix9A= cloud.google.com/go/iap v1.6.0/go.mod h1:NSuvI9C/j7UdjGjIde7t7HBz+QTwBcapPE07+sSRcLk= @@ -423,15 +595,24 @@ cloud.google.com/go/iap v1.7.0/go.mod h1:beqQx56T9O1G1yNPph+spKpNibDlYIiIixiqsQX cloud.google.com/go/iap v1.7.1/go.mod h1:WapEwPc7ZxGt2jFGB/C/bm+hP0Y6NXzOYGjpPnmMS74= cloud.google.com/go/iap v1.8.1/go.mod h1:sJCbeqg3mvWLqjZNsI6dfAtbbV1DL2Rl7e1mTyXYREQ= cloud.google.com/go/iap v1.9.0/go.mod h1:01OFxd1R+NFrg78S+hoPV5PxEzv22HXaNqUUlmNHFuY= +cloud.google.com/go/iap v1.9.1/go.mod h1:SIAkY7cGMLohLSdBR25BuIxO+I4fXJiL06IBL7cy/5Q= +cloud.google.com/go/iap v1.9.2/go.mod h1:GwDTOs047PPSnwRD0Us5FKf4WDRcVvHg1q9WVkKBhdI= +cloud.google.com/go/iap v1.9.3/go.mod h1:DTdutSZBqkkOm2HEOTBzhZxh2mwwxshfD/h3yofAiCw= cloud.google.com/go/ids v1.1.0/go.mod h1:WIuwCaYVOzHIj2OhN9HAwvW+DBdmUAdcWlFxRl+KubM= cloud.google.com/go/ids v1.2.0/go.mod h1:5WXvp4n25S0rA/mQWAg1YEEBBq6/s+7ml1RDCW1IrcY= cloud.google.com/go/ids v1.3.0/go.mod h1:JBdTYwANikFKaDP6LtW5JAi4gubs57SVNQjemdt6xV4= cloud.google.com/go/ids v1.4.1/go.mod h1:np41ed8YMU8zOgv53MMMoCntLTn2lF+SUzlM+O3u/jw= +cloud.google.com/go/ids v1.4.2/go.mod h1:3vw8DX6YddRu9BncxuzMyWn0g8+ooUjI2gslJ7FH3vk= +cloud.google.com/go/ids v1.4.3/go.mod h1:9CXPqI3GedjmkjbMWCUhMZ2P2N7TUMzAkVXYEH2orYU= +cloud.google.com/go/ids v1.4.4/go.mod h1:z+WUc2eEl6S/1aZWzwtVNWoSZslgzPxAboS0lZX0HjI= cloud.google.com/go/iot v1.3.0/go.mod h1:r7RGh2B61+B8oz0AGE+J72AhA0G7tdXItODWsaA2oLs= cloud.google.com/go/iot v1.4.0/go.mod h1:dIDxPOn0UvNDUMD8Ger7FIaTuvMkj+aGk94RPP0iV+g= cloud.google.com/go/iot v1.5.0/go.mod h1:mpz5259PDl3XJthEmh9+ap0affn/MqNSP4My77Qql9o= cloud.google.com/go/iot v1.6.0/go.mod h1:IqdAsmE2cTYYNO1Fvjfzo9po179rAtJeVGUvkLN3rLE= cloud.google.com/go/iot v1.7.1/go.mod h1:46Mgw7ev1k9KqK1ao0ayW9h0lI+3hxeanz+L1zmbbbk= +cloud.google.com/go/iot v1.7.2/go.mod h1:q+0P5zr1wRFpw7/MOgDXrG/HVA+l+cSwdObffkrpnSg= +cloud.google.com/go/iot v1.7.3/go.mod h1:t8itFchkol4VgNbHnIq9lXoOOtHNR3uAACQMYbN9N4I= +cloud.google.com/go/iot v1.7.4/go.mod h1:3TWqDVvsddYBG++nHSZmluoCAVGr1hAcabbWZNKEZLk= cloud.google.com/go/kms v1.4.0/go.mod h1:fajBHndQ+6ubNw6Ss2sSd+SWvjL26RNo/dr7uxsnnOA= cloud.google.com/go/kms v1.5.0/go.mod h1:QJS2YY0eJGBg3mnDfuaCyLauWwBJiHRboYxJ++1xJNg= cloud.google.com/go/kms v1.6.0/go.mod h1:Jjy850yySiasBUDi6KFUwUv2n1+o7QZFyuUJg6OgjA0= @@ -443,6 +624,9 @@ cloud.google.com/go/kms v1.11.0/go.mod h1:hwdiYC0xjnWsKQQCQQmIQnS9asjYVSK6jtXm+z cloud.google.com/go/kms v1.12.1/go.mod h1:c9J991h5DTl+kg7gi3MYomh12YEENGrf48ee/N/2CDM= cloud.google.com/go/kms v1.15.0/go.mod h1:c9J991h5DTl+kg7gi3MYomh12YEENGrf48ee/N/2CDM= cloud.google.com/go/kms v1.15.2/go.mod h1:3hopT4+7ooWRCjc2DxgnpESFxhIraaI2IpAVUEhbT/w= +cloud.google.com/go/kms v1.15.3/go.mod h1:AJdXqHxS2GlPyduM99s9iGqi2nwbviBbhV/hdmt4iOQ= +cloud.google.com/go/kms v1.15.4/go.mod h1:L3Sdj6QTHK8dfwK5D1JLsAyELsNMnd3tAIwGS4ltKpc= +cloud.google.com/go/kms v1.15.5/go.mod h1:cU2H5jnp6G2TDpUGZyqTCoy1n16fbubHZjmVXSMtwDI= cloud.google.com/go/language v1.4.0/go.mod h1:F9dRpNFQmJbkaop6g0JhSBXCNlO90e1KWx5iDdxbWic= cloud.google.com/go/language v1.6.0/go.mod h1:6dJ8t3B+lUYfStgls25GusK04NLh3eDLQnWM3mdEbhI= cloud.google.com/go/language v1.7.0/go.mod h1:DJ6dYN/W+SQOjF8e1hLQXMF21AkH2w9wiPzPCJa2MIE= @@ -450,10 +634,16 @@ cloud.google.com/go/language v1.8.0/go.mod h1:qYPVHf7SPoNNiCL2Dr0FfEFNil1qi3pQEy cloud.google.com/go/language v1.9.0/go.mod h1:Ns15WooPM5Ad/5no/0n81yUetis74g3zrbeJBE+ptUY= cloud.google.com/go/language v1.10.1/go.mod h1:CPp94nsdVNiQEt1CNjF5WkTcisLiHPyIbMhvR8H2AW0= cloud.google.com/go/language v1.11.0/go.mod h1:uDx+pFDdAKTY8ehpWbiXyQdz8tDSYLJbQcXsCkjYyvQ= +cloud.google.com/go/language v1.11.1/go.mod h1:Xyid9MG9WOX3utvDbpX7j3tXDmmDooMyMDqgUVpH17U= +cloud.google.com/go/language v1.12.1/go.mod h1:zQhalE2QlQIxbKIZt54IASBzmZpN/aDASea5zl1l+J4= +cloud.google.com/go/language v1.12.2/go.mod h1:9idWapzr/JKXBBQ4lWqVX/hcadxB194ry20m/bTrhWc= cloud.google.com/go/lifesciences v0.5.0/go.mod h1:3oIKy8ycWGPUyZDR/8RNnTOYevhaMLqh5vLUXs9zvT8= cloud.google.com/go/lifesciences v0.6.0/go.mod h1:ddj6tSX/7BOnhxCSd3ZcETvtNr8NZ6t/iPhY2Tyfu08= cloud.google.com/go/lifesciences v0.8.0/go.mod h1:lFxiEOMqII6XggGbOnKiyZ7IBwoIqA84ClvoezaA/bo= cloud.google.com/go/lifesciences v0.9.1/go.mod h1:hACAOd1fFbCGLr/+weUKRAJas82Y4vrL3O5326N//Wc= +cloud.google.com/go/lifesciences v0.9.2/go.mod h1:QHEOO4tDzcSAzeJg7s2qwnLM2ji8IRpQl4p6m5Z9yTA= +cloud.google.com/go/lifesciences v0.9.3/go.mod h1:gNGBOJV80IWZdkd+xz4GQj4mbqaz737SCLHn2aRhQKM= +cloud.google.com/go/lifesciences v0.9.4/go.mod h1:bhm64duKhMi7s9jR9WYJYvjAFJwRqNj+Nia7hF0Z7JA= cloud.google.com/go/logging v1.6.1/go.mod h1:5ZO0mHHbvm8gEmeEUHrmDlTDSu5imF6MUP9OfilNXBw= cloud.google.com/go/logging v1.7.0/go.mod h1:3xjP2CjkM3ZkO73aj4ASA5wRPGGCRrPIAeNqVNkzY8M= cloud.google.com/go/logging v1.8.1/go.mod h1:TJjR+SimHwuC8MZ9cjByQulAMgni+RkXeI3wwctHJEI= @@ -463,25 +653,40 @@ cloud.google.com/go/longrunning v0.4.1/go.mod h1:4iWDqhBZ70CvZ6BfETbvam3T8FMvLK+ cloud.google.com/go/longrunning v0.4.2/go.mod h1:OHrnaYyLUV6oqwh0xiS7e5sLQhP1m0QU9R+WhGDMgIQ= cloud.google.com/go/longrunning v0.5.0/go.mod h1:0JNuqRShmscVAhIACGtskSAWtqtOoPkwP0YF1oVEchc= cloud.google.com/go/longrunning v0.5.1/go.mod h1:spvimkwdz6SPWKEt/XBij79E9fiTkHSQl/fRUUQJYJc= +cloud.google.com/go/longrunning v0.5.2/go.mod h1:nqo6DQbNV2pXhGDbDMoN2bWz68MjZUzqv2YttZiveCs= +cloud.google.com/go/longrunning v0.5.3/go.mod h1:y/0ga59EYu58J6SHmmQOvekvND2qODbu8ywBBW7EK7Y= +cloud.google.com/go/longrunning v0.5.4/go.mod h1:zqNVncI0BOP8ST6XQD1+VcvuShMmq7+xFSzOL++V0dI= cloud.google.com/go/managedidentities v1.3.0/go.mod h1:UzlW3cBOiPrzucO5qWkNkh0w33KFtBJU281hacNvsdE= cloud.google.com/go/managedidentities v1.4.0/go.mod h1:NWSBYbEMgqmbZsLIyKvxrYbtqOsxY1ZrGM+9RgDqInM= cloud.google.com/go/managedidentities v1.5.0/go.mod h1:+dWcZ0JlUmpuxpIDfyP5pP5y0bLdRwOS4Lp7gMni/LA= cloud.google.com/go/managedidentities v1.6.1/go.mod h1:h/irGhTN2SkZ64F43tfGPMbHnypMbu4RB3yl8YcuEak= +cloud.google.com/go/managedidentities v1.6.2/go.mod h1:5c2VG66eCa0WIq6IylRk3TBW83l161zkFvCj28X7jn8= +cloud.google.com/go/managedidentities v1.6.3/go.mod h1:tewiat9WLyFN0Fi7q1fDD5+0N4VUoL0SCX0OTCthZq4= +cloud.google.com/go/managedidentities v1.6.4/go.mod h1:WgyaECfHmF00t/1Uk8Oun3CQ2PGUtjc3e9Alh79wyiM= cloud.google.com/go/maps v0.1.0/go.mod h1:BQM97WGyfw9FWEmQMpZ5T6cpovXXSd1cGmFma94eubI= cloud.google.com/go/maps v0.6.0/go.mod h1:o6DAMMfb+aINHz/p/jbcY+mYeXBoZoxTfdSQ8VAJaCw= cloud.google.com/go/maps v0.7.0/go.mod h1:3GnvVl3cqeSvgMcpRlQidXsPYuDGQ8naBis7MVzpXsY= cloud.google.com/go/maps v1.3.0/go.mod h1:6mWTUv+WhnOwAgjVsSW2QPPECmW+s3PcRyOa9vgG/5s= cloud.google.com/go/maps v1.4.0/go.mod h1:6mWTUv+WhnOwAgjVsSW2QPPECmW+s3PcRyOa9vgG/5s= +cloud.google.com/go/maps v1.4.1/go.mod h1:BxSa0BnW1g2U2gNdbq5zikLlHUuHW0GFWh7sgML2kIY= +cloud.google.com/go/maps v1.5.1/go.mod h1:NPMZw1LJwQZYCfz4y+EIw+SI+24A4bpdFJqdKVr0lt4= +cloud.google.com/go/maps v1.6.1/go.mod h1:4+buOHhYXFBp58Zj/K+Lc1rCmJssxxF4pJ5CJnhdz18= cloud.google.com/go/mediatranslation v0.5.0/go.mod h1:jGPUhGTybqsPQn91pNXw0xVHfuJ3leR1wj37oU3y1f4= cloud.google.com/go/mediatranslation v0.6.0/go.mod h1:hHdBCTYNigsBxshbznuIMFNe5QXEowAuNmmC7h8pu5w= cloud.google.com/go/mediatranslation v0.7.0/go.mod h1:LCnB/gZr90ONOIQLgSXagp8XUW1ODs2UmUMvcgMfI2I= cloud.google.com/go/mediatranslation v0.8.1/go.mod h1:L/7hBdEYbYHQJhX2sldtTO5SZZ1C1vkapubj0T2aGig= +cloud.google.com/go/mediatranslation v0.8.2/go.mod h1:c9pUaDRLkgHRx3irYE5ZC8tfXGrMYwNZdmDqKMSfFp8= +cloud.google.com/go/mediatranslation v0.8.3/go.mod h1:F9OnXTy336rteOEywtY7FOqCk+J43o2RF638hkOQl4Y= +cloud.google.com/go/mediatranslation v0.8.4/go.mod h1:9WstgtNVAdN53m6TQa5GjIjLqKQPXe74hwSCxUP6nj4= cloud.google.com/go/memcache v1.4.0/go.mod h1:rTOfiGZtJX1AaFUrOgsMHX5kAzaTQ8azHiuDoTPzNsE= cloud.google.com/go/memcache v1.5.0/go.mod h1:dk3fCK7dVo0cUU2c36jKb4VqKPS22BTkf81Xq617aWM= cloud.google.com/go/memcache v1.6.0/go.mod h1:XS5xB0eQZdHtTuTF9Hf8eJkKtR3pVRCcvJwtm68T3rA= cloud.google.com/go/memcache v1.7.0/go.mod h1:ywMKfjWhNtkQTxrWxCkCFkoPjLHPW6A7WOTVI8xy3LY= cloud.google.com/go/memcache v1.9.0/go.mod h1:8oEyzXCu+zo9RzlEaEjHl4KkgjlNDaXbCQeQWlzNFJM= cloud.google.com/go/memcache v1.10.1/go.mod h1:47YRQIarv4I3QS5+hoETgKO40InqzLP6kpNLvyXuyaA= +cloud.google.com/go/memcache v1.10.2/go.mod h1:f9ZzJHLBrmd4BkguIAa/l/Vle6uTHzHokdnzSWOdQ6A= +cloud.google.com/go/memcache v1.10.3/go.mod h1:6z89A41MT2DVAW0P4iIRdu5cmRTsbsFn4cyiIx8gbwo= +cloud.google.com/go/memcache v1.10.4/go.mod h1:v/d8PuC8d1gD6Yn5+I3INzLR01IDn0N4Ym56RgikSI0= cloud.google.com/go/metastore v1.5.0/go.mod h1:2ZNrDcQwghfdtCwJ33nM0+GrBGlVuh8rakL3vdPY3XY= cloud.google.com/go/metastore v1.6.0/go.mod h1:6cyQTls8CWXzk45G55x57DVQ9gWg7RiH65+YgPsNh9s= cloud.google.com/go/metastore v1.7.0/go.mod h1:s45D0B4IlsINu87/AsWiEVYbLaIMeUSoxlKKDqBGFS8= @@ -489,12 +694,19 @@ cloud.google.com/go/metastore v1.8.0/go.mod h1:zHiMc4ZUpBiM7twCIFQmJ9JMEkDSyZS9U cloud.google.com/go/metastore v1.10.0/go.mod h1:fPEnH3g4JJAk+gMRnrAnoqyv2lpUCqJPWOodSaf45Eo= cloud.google.com/go/metastore v1.11.1/go.mod h1:uZuSo80U3Wd4zi6C22ZZliOUJ3XeM/MlYi/z5OAOWRA= cloud.google.com/go/metastore v1.12.0/go.mod h1:uZuSo80U3Wd4zi6C22ZZliOUJ3XeM/MlYi/z5OAOWRA= +cloud.google.com/go/metastore v1.13.0/go.mod h1:URDhpG6XLeh5K+Glq0NOt74OfrPKTwS62gEPZzb5SOk= +cloud.google.com/go/metastore v1.13.1/go.mod h1:IbF62JLxuZmhItCppcIfzBBfUFq0DIB9HPDoLgWrVOU= +cloud.google.com/go/metastore v1.13.2/go.mod h1:KS59dD+unBji/kFebVp8XU/quNSyo8b6N6tPGspKszA= +cloud.google.com/go/metastore v1.13.3/go.mod h1:K+wdjXdtkdk7AQg4+sXS8bRrQa9gcOr+foOMF2tqINE= cloud.google.com/go/monitoring v1.7.0/go.mod h1:HpYse6kkGo//7p6sT0wsIC6IBDET0RhIsnmlA53dvEk= cloud.google.com/go/monitoring v1.8.0/go.mod h1:E7PtoMJ1kQXWxPjB6mv2fhC5/15jInuulFdYYtlcvT4= cloud.google.com/go/monitoring v1.12.0/go.mod h1:yx8Jj2fZNEkL/GYZyTLS4ZtZEZN8WtDEiEqG4kLK50w= cloud.google.com/go/monitoring v1.13.0/go.mod h1:k2yMBAB1H9JT/QETjNkgdCGD9bPF712XiLTVr+cBrpw= cloud.google.com/go/monitoring v1.15.1/go.mod h1:lADlSAlFdbqQuwwpaImhsJXu1QSdd3ojypXrFSMr2rM= cloud.google.com/go/monitoring v1.16.0/go.mod h1:Ptp15HgAyM1fNICAojDMoNc/wUmn67mLHQfyqbw+poY= +cloud.google.com/go/monitoring v1.16.1/go.mod h1:6HsxddR+3y9j+o/cMJH6q/KJ/CBTvM/38L/1m7bTRJ4= +cloud.google.com/go/monitoring v1.16.2/go.mod h1:B44KGwi4ZCF8Rk/5n+FWeispDXoKSk9oss2QNlXJBgc= +cloud.google.com/go/monitoring v1.16.3/go.mod h1:KwSsX5+8PnXv5NJnICZzW2R8pWTis8ypC4zmdRD63Tw= cloud.google.com/go/networkconnectivity v1.4.0/go.mod h1:nOl7YL8odKyAOtzNX73/M5/mGZgqqMeryi6UPZTk/rA= cloud.google.com/go/networkconnectivity v1.5.0/go.mod h1:3GzqJx7uhtlM3kln0+x5wyFvuVH1pIBJjhCpjzSt75o= cloud.google.com/go/networkconnectivity v1.6.0/go.mod h1:OJOoEXW+0LAxHh89nXd64uGG+FbQoeH8DtxCHVOMlaM= @@ -503,16 +715,26 @@ cloud.google.com/go/networkconnectivity v1.10.0/go.mod h1:UP4O4sWXJG13AqrTdQCD9T cloud.google.com/go/networkconnectivity v1.11.0/go.mod h1:iWmDD4QF16VCDLXUqvyspJjIEtBR/4zq5hwnY2X3scM= cloud.google.com/go/networkconnectivity v1.12.1/go.mod h1:PelxSWYM7Sh9/guf8CFhi6vIqf19Ir/sbfZRUwXh92E= cloud.google.com/go/networkconnectivity v1.13.0/go.mod h1:SAnGPes88pl7QRLUen2HmcBSE9AowVAcdug8c0RSBFk= +cloud.google.com/go/networkconnectivity v1.14.0/go.mod h1:SAnGPes88pl7QRLUen2HmcBSE9AowVAcdug8c0RSBFk= +cloud.google.com/go/networkconnectivity v1.14.1/go.mod h1:LyGPXR742uQcDxZ/wv4EI0Vu5N6NKJ77ZYVnDe69Zug= +cloud.google.com/go/networkconnectivity v1.14.2/go.mod h1:5UFlwIisZylSkGG1AdwK/WZUaoz12PKu6wODwIbFzJo= +cloud.google.com/go/networkconnectivity v1.14.3/go.mod h1:4aoeFdrJpYEXNvrnfyD5kIzs8YtHg945Og4koAjHQek= cloud.google.com/go/networkmanagement v1.4.0/go.mod h1:Q9mdLLRn60AsOrPc8rs8iNV6OHXaGcDdsIQe1ohekq8= cloud.google.com/go/networkmanagement v1.5.0/go.mod h1:ZnOeZ/evzUdUsnvRt792H0uYEnHQEMaz+REhhzJRcf4= cloud.google.com/go/networkmanagement v1.6.0/go.mod h1:5pKPqyXjB/sgtvB5xqOemumoQNB7y95Q7S+4rjSOPYY= cloud.google.com/go/networkmanagement v1.8.0/go.mod h1:Ho/BUGmtyEqrttTgWEe7m+8vDdK74ibQc+Be0q7Fof0= cloud.google.com/go/networkmanagement v1.9.0/go.mod h1:UTUaEU9YwbCAhhz3jEOHr+2/K/MrBk2XxOLS89LQzFw= +cloud.google.com/go/networkmanagement v1.9.1/go.mod h1:CCSYgrQQvW73EJawO2QamemYcOb57LvrDdDU51F0mcI= +cloud.google.com/go/networkmanagement v1.9.2/go.mod h1:iDGvGzAoYRghhp4j2Cji7sF899GnfGQcQRQwgVOWnDw= +cloud.google.com/go/networkmanagement v1.9.3/go.mod h1:y7WMO1bRLaP5h3Obm4tey+NquUvB93Co1oh4wpL+XcU= cloud.google.com/go/networksecurity v0.5.0/go.mod h1:xS6fOCoqpVC5zx15Z/MqkfDwH4+m/61A3ODiDV1xmiQ= cloud.google.com/go/networksecurity v0.6.0/go.mod h1:Q5fjhTr9WMI5mbpRYEbiexTzROf7ZbDzvzCrNl14nyU= cloud.google.com/go/networksecurity v0.7.0/go.mod h1:mAnzoxx/8TBSyXEeESMy9OOYwo1v+gZ5eMRnsT5bC8k= cloud.google.com/go/networksecurity v0.8.0/go.mod h1:B78DkqsxFG5zRSVuwYFRZ9Xz8IcQ5iECsNrPn74hKHU= cloud.google.com/go/networksecurity v0.9.1/go.mod h1:MCMdxOKQ30wsBI1eI659f9kEp4wuuAueoC9AJKSPWZQ= +cloud.google.com/go/networksecurity v0.9.2/go.mod h1:jG0SeAttWzPMUILEHDUvFYdQTl8L/E/KC8iZDj85lEI= +cloud.google.com/go/networksecurity v0.9.3/go.mod h1:l+C0ynM6P+KV9YjOnx+kk5IZqMSLccdBqW6GUoF4p/0= +cloud.google.com/go/networksecurity v0.9.4/go.mod h1:E9CeMZ2zDsNBkr8axKSYm8XyTqNhiCHf1JO/Vb8mD1w= cloud.google.com/go/notebooks v1.2.0/go.mod h1:9+wtppMfVPUeJ8fIWPOq1UnATHISkGXGqTkxeieQ6UY= cloud.google.com/go/notebooks v1.3.0/go.mod h1:bFR5lj07DtCPC7YAAJ//vHskFBxA5JzYlH68kXVdk34= cloud.google.com/go/notebooks v1.4.0/go.mod h1:4QPMngcwmgb6uw7Po99B2xv5ufVoIQ7nOGDyL4P8AgA= @@ -521,20 +743,32 @@ cloud.google.com/go/notebooks v1.7.0/go.mod h1:PVlaDGfJgj1fl1S3dUwhFMXFgfYGhYQt2 cloud.google.com/go/notebooks v1.8.0/go.mod h1:Lq6dYKOYOWUCTvw5t2q1gp1lAp0zxAxRycayS0iJcqQ= cloud.google.com/go/notebooks v1.9.1/go.mod h1:zqG9/gk05JrzgBt4ghLzEepPHNwE5jgPcHZRKhlC1A8= cloud.google.com/go/notebooks v1.10.0/go.mod h1:SOPYMZnttHxqot0SGSFSkRrwE29eqnKPBJFqgWmiK2k= +cloud.google.com/go/notebooks v1.10.1/go.mod h1:5PdJc2SgAybE76kFQCWrTfJolCOUQXF97e+gteUUA6A= +cloud.google.com/go/notebooks v1.11.1/go.mod h1:V2Zkv8wX9kDCGRJqYoI+bQAaoVeE5kSiz4yYHd2yJwQ= +cloud.google.com/go/notebooks v1.11.2/go.mod h1:z0tlHI/lREXC8BS2mIsUeR3agM1AkgLiS+Isov3SS70= cloud.google.com/go/optimization v1.1.0/go.mod h1:5po+wfvX5AQlPznyVEZjGJTMr4+CAkJf2XSTQOOl9l4= cloud.google.com/go/optimization v1.2.0/go.mod h1:Lr7SOHdRDENsh+WXVmQhQTrzdu9ybg0NecjHidBq6xs= cloud.google.com/go/optimization v1.3.1/go.mod h1:IvUSefKiwd1a5p0RgHDbWCIbDFgKuEdB+fPPuP0IDLI= cloud.google.com/go/optimization v1.4.1/go.mod h1:j64vZQP7h9bO49m2rVaTVoNM0vEBEN5eKPUPbZyXOrk= cloud.google.com/go/optimization v1.5.0/go.mod h1:evo1OvTxeBRBu6ydPlrIRizKY/LJKo/drDMMRKqGEUU= +cloud.google.com/go/optimization v1.5.1/go.mod h1:NC0gnUD5MWVAF7XLdoYVPmYYVth93Q6BUzqAq3ZwtV8= +cloud.google.com/go/optimization v1.6.1/go.mod h1:hH2RYPTTM9e9zOiTaYPTiGPcGdNZVnBSBxjIAJzUkqo= +cloud.google.com/go/optimization v1.6.2/go.mod h1:mWNZ7B9/EyMCcwNl1frUGEuY6CPijSkz88Fz2vwKPOY= cloud.google.com/go/orchestration v1.3.0/go.mod h1:Sj5tq/JpWiB//X/q3Ngwdl5K7B7Y0KZ7bfv0wL6fqVA= cloud.google.com/go/orchestration v1.4.0/go.mod h1:6W5NLFWs2TlniBphAViZEVhrXRSMgUGDfW7vrWKvsBk= cloud.google.com/go/orchestration v1.6.0/go.mod h1:M62Bevp7pkxStDfFfTuCOaXgaaqRAga1yKyoMtEoWPQ= cloud.google.com/go/orchestration v1.8.1/go.mod h1:4sluRF3wgbYVRqz7zJ1/EUNc90TTprliq9477fGobD8= +cloud.google.com/go/orchestration v1.8.2/go.mod h1:T1cP+6WyTmh6LSZzeUhvGf0uZVmJyTx7t8z7Vg87+A0= +cloud.google.com/go/orchestration v1.8.3/go.mod h1:xhgWAYqlbYjlz2ftbFghdyqENYW+JXuhBx9KsjMoGHs= +cloud.google.com/go/orchestration v1.8.4/go.mod h1:d0lywZSVYtIoSZXb0iFjv9SaL13PGyVOKDxqGxEf/qI= cloud.google.com/go/orgpolicy v1.4.0/go.mod h1:xrSLIV4RePWmP9P3tBl8S93lTmlAxjm06NSm2UTmKvE= cloud.google.com/go/orgpolicy v1.5.0/go.mod h1:hZEc5q3wzwXJaKrsx5+Ewg0u1LxJ51nNFlext7Tanwc= cloud.google.com/go/orgpolicy v1.10.0/go.mod h1:w1fo8b7rRqlXlIJbVhOMPrwVljyuW5mqssvBtU18ONc= cloud.google.com/go/orgpolicy v1.11.0/go.mod h1:2RK748+FtVvnfuynxBzdnyu7sygtoZa1za/0ZfpOs1M= cloud.google.com/go/orgpolicy v1.11.1/go.mod h1:8+E3jQcpZJQliP+zaFfayC2Pg5bmhuLK755wKhIIUCE= +cloud.google.com/go/orgpolicy v1.11.2/go.mod h1:biRDpNwfyytYnmCRWZWxrKF22Nkz9eNVj9zyaBdpm1o= +cloud.google.com/go/orgpolicy v1.11.3/go.mod h1:oKAtJ/gkMjum5icv2aujkP4CxROxPXsBbYGCDbPO8MM= +cloud.google.com/go/orgpolicy v1.11.4/go.mod h1:0+aNV/nrfoTQ4Mytv+Aw+stBDBjNf4d8fYRA9herfJI= cloud.google.com/go/osconfig v1.7.0/go.mod h1:oVHeCeZELfJP7XLxcBGTMBvRO+1nQ5tFG9VQTmYS2Fs= cloud.google.com/go/osconfig v1.8.0/go.mod h1:EQqZLu5w5XA7eKizepumcvWx+m8mJUhEwiPqWiZeEdg= cloud.google.com/go/osconfig v1.9.0/go.mod h1:Yx+IeIZJ3bdWmzbQU4fxNl8xsZ4amB+dygAwFPlvnNo= @@ -542,16 +776,26 @@ cloud.google.com/go/osconfig v1.10.0/go.mod h1:uMhCzqC5I8zfD9zDEAfvgVhDS8oIjySWh cloud.google.com/go/osconfig v1.11.0/go.mod h1:aDICxrur2ogRd9zY5ytBLV89KEgT2MKB2L/n6x1ooPw= cloud.google.com/go/osconfig v1.12.0/go.mod h1:8f/PaYzoS3JMVfdfTubkowZYGmAhUCjjwnjqWI7NVBc= cloud.google.com/go/osconfig v1.12.1/go.mod h1:4CjBxND0gswz2gfYRCUoUzCm9zCABp91EeTtWXyz0tE= +cloud.google.com/go/osconfig v1.12.2/go.mod h1:eh9GPaMZpI6mEJEuhEjUJmaxvQ3gav+fFEJon1Y8Iw0= +cloud.google.com/go/osconfig v1.12.3/go.mod h1:L/fPS8LL6bEYUi1au832WtMnPeQNT94Zo3FwwV1/xGM= +cloud.google.com/go/osconfig v1.12.4/go.mod h1:B1qEwJ/jzqSRslvdOCI8Kdnp0gSng0xW4LOnIebQomA= cloud.google.com/go/oslogin v1.4.0/go.mod h1:YdgMXWRaElXz/lDk1Na6Fh5orF7gvmJ0FGLIs9LId4E= cloud.google.com/go/oslogin v1.5.0/go.mod h1:D260Qj11W2qx/HVF29zBg+0fd6YCSjSqLUkY/qEenQU= cloud.google.com/go/oslogin v1.6.0/go.mod h1:zOJ1O3+dTU8WPlGEkFSh7qeHPPSoxrcMbbK1Nm2iX70= cloud.google.com/go/oslogin v1.7.0/go.mod h1:e04SN0xO1UNJ1M5GP0vzVBFicIe4O53FOfcixIqTyXo= cloud.google.com/go/oslogin v1.9.0/go.mod h1:HNavntnH8nzrn8JCTT5fj18FuJLFJc4NaZJtBnQtKFs= cloud.google.com/go/oslogin v1.10.1/go.mod h1:x692z7yAue5nE7CsSnoG0aaMbNoRJRXO4sn73R+ZqAs= +cloud.google.com/go/oslogin v1.11.0/go.mod h1:8GMTJs4X2nOAUVJiPGqIWVcDaF0eniEto3xlOxaboXE= +cloud.google.com/go/oslogin v1.11.1/go.mod h1:OhD2icArCVNUxKqtK0mcSmKL7lgr0LVlQz+v9s1ujTg= +cloud.google.com/go/oslogin v1.12.1/go.mod h1:VfwTeFJGbnakxAY236eN8fsnglLiVXndlbcNomY4iZU= +cloud.google.com/go/oslogin v1.12.2/go.mod h1:CQ3V8Jvw4Qo4WRhNPF0o+HAM4DiLuE27Ul9CX9g2QdY= cloud.google.com/go/phishingprotection v0.5.0/go.mod h1:Y3HZknsK9bc9dMi+oE8Bim0lczMU6hrX0UpADuMefr0= cloud.google.com/go/phishingprotection v0.6.0/go.mod h1:9Y3LBLgy0kDTcYET8ZH3bq/7qni15yVUoAxiFxnlSUA= cloud.google.com/go/phishingprotection v0.7.0/go.mod h1:8qJI4QKHoda/sb/7/YmMQ2omRLSLYSu9bU0EKCNI+Lk= cloud.google.com/go/phishingprotection v0.8.1/go.mod h1:AxonW7GovcA8qdEk13NfHq9hNx5KPtfxXNeUxTDxB6I= +cloud.google.com/go/phishingprotection v0.8.2/go.mod h1:LhJ91uyVHEYKSKcMGhOa14zMMWfbEdxG032oT6ECbC8= +cloud.google.com/go/phishingprotection v0.8.3/go.mod h1:3B01yO7T2Ra/TMojifn8EoGd4G9jts/6cIO0DgDY9J8= +cloud.google.com/go/phishingprotection v0.8.4/go.mod h1:6b3kNPAc2AQ6jZfFHioZKg9MQNybDg4ixFd4RPZZ2nE= cloud.google.com/go/policytroubleshooter v1.3.0/go.mod h1:qy0+VwANja+kKrjlQuOzmlvscn4RNsAc0e15GGqfMxg= cloud.google.com/go/policytroubleshooter v1.4.0/go.mod h1:DZT4BcRw3QoO8ota9xw/LKtPa8lKeCByYeKTIf/vxdE= cloud.google.com/go/policytroubleshooter v1.5.0/go.mod h1:Rz1WfV+1oIpPdN2VvvuboLVRsB1Hclg3CKQ53j9l8vw= @@ -559,11 +803,17 @@ cloud.google.com/go/policytroubleshooter v1.6.0/go.mod h1:zYqaPTsmfvpjm5ULxAyD/l cloud.google.com/go/policytroubleshooter v1.7.1/go.mod h1:0NaT5v3Ag1M7U5r0GfDCpUFkWd9YqpubBWsQlhanRv0= cloud.google.com/go/policytroubleshooter v1.8.0/go.mod h1:tmn5Ir5EToWe384EuboTcVQT7nTag2+DuH3uHmKd1HU= cloud.google.com/go/policytroubleshooter v1.9.0/go.mod h1:+E2Lga7TycpeSTj2FsH4oXxTnrbHJGRlKhVZBLGgU64= +cloud.google.com/go/policytroubleshooter v1.9.1/go.mod h1:MYI8i0bCrL8cW+VHN1PoiBTyNZTstCg2WUw2eVC4c4U= +cloud.google.com/go/policytroubleshooter v1.10.1/go.mod h1:5C0rhT3TDZVxAu8813bwmTvd57Phbl8mr9F4ipOsxEs= +cloud.google.com/go/policytroubleshooter v1.10.2/go.mod h1:m4uF3f6LseVEnMV6nknlN2vYGRb+75ylQwJdnOXfnv0= cloud.google.com/go/privatecatalog v0.5.0/go.mod h1:XgosMUvvPyxDjAVNDYxJ7wBW8//hLDDYmnsNcMGq1K0= cloud.google.com/go/privatecatalog v0.6.0/go.mod h1:i/fbkZR0hLN29eEWiiwue8Pb+GforiEIBnV9yrRUOKI= cloud.google.com/go/privatecatalog v0.7.0/go.mod h1:2s5ssIFO69F5csTXcwBP7NPFTZvps26xGzvQ2PQaBYg= cloud.google.com/go/privatecatalog v0.8.0/go.mod h1:nQ6pfaegeDAq/Q5lrfCQzQLhubPiZhSaNhIgfJlnIXs= cloud.google.com/go/privatecatalog v0.9.1/go.mod h1:0XlDXW2unJXdf9zFz968Hp35gl/bhF4twwpXZAW50JA= +cloud.google.com/go/privatecatalog v0.9.2/go.mod h1:RMA4ATa8IXfzvjrhhK8J6H4wwcztab+oZph3c6WmtFc= +cloud.google.com/go/privatecatalog v0.9.3/go.mod h1:K5pn2GrVmOPjXz3T26mzwXLcKivfIJ9R5N79AFCF9UE= +cloud.google.com/go/privatecatalog v0.9.4/go.mod h1:SOjm93f+5hp/U3PqMZAHTtBtluqLygrDrVO8X8tYtG0= cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= @@ -587,10 +837,17 @@ cloud.google.com/go/recaptchaenterprise/v2 v2.5.0/go.mod h1:O8LzcHXN3rz0j+LBC91j cloud.google.com/go/recaptchaenterprise/v2 v2.6.0/go.mod h1:RPauz9jeLtB3JVzg6nCbe12qNoaa8pXc4d/YukAmcnA= cloud.google.com/go/recaptchaenterprise/v2 v2.7.0/go.mod h1:19wVj/fs5RtYtynAPJdDTb69oW0vNHYDBTbB4NvMD9c= cloud.google.com/go/recaptchaenterprise/v2 v2.7.2/go.mod h1:kR0KjsJS7Jt1YSyWFkseQ756D45kaYNTlDPPaRAvDBU= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.0/go.mod h1:QuE8EdU9dEnesG8/kG3XuJyNsjEqMlMzg3v3scCJ46c= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.1/go.mod h1:JZYZJOeZjgSSTGP4uz7NlQ4/d1w5hGmksVgM0lbEij0= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.2/go.mod h1:kpaDBOpkwD4G0GVMzG1W6Doy1tFFC97XAV3xy+Rd/pw= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.3/go.mod h1:Dak54rw6lC2gBY8FBznpOCAR58wKf+R+ZSJRoeJok4w= cloud.google.com/go/recommendationengine v0.5.0/go.mod h1:E5756pJcVFeVgaQv3WNpImkFP8a+RptV6dDLGPILjvg= cloud.google.com/go/recommendationengine v0.6.0/go.mod h1:08mq2umu9oIqc7tDy8sx+MNJdLG0fUi3vaSVbztHgJ4= cloud.google.com/go/recommendationengine v0.7.0/go.mod h1:1reUcE3GIu6MeBz/h5xZJqNLuuVjNg1lmWMPyjatzac= cloud.google.com/go/recommendationengine v0.8.1/go.mod h1:MrZihWwtFYWDzE6Hz5nKcNz3gLizXVIDI/o3G1DLcrE= +cloud.google.com/go/recommendationengine v0.8.2/go.mod h1:QIybYHPK58qir9CV2ix/re/M//Ty10OxjnnhWdaKS1Y= +cloud.google.com/go/recommendationengine v0.8.3/go.mod h1:m3b0RZV02BnODE9FeSvGv1qibFo8g0OnmB/RMwYy4V8= +cloud.google.com/go/recommendationengine v0.8.4/go.mod h1:GEteCf1PATl5v5ZsQ60sTClUE0phbWmo3rQ1Js8louU= cloud.google.com/go/recommender v1.5.0/go.mod h1:jdoeiBIVrJe9gQjwd759ecLJbxCDED4A6p+mqoqDvTg= cloud.google.com/go/recommender v1.6.0/go.mod h1:+yETpm25mcoiECKh9DEScGzIRyDKpZ0cEhWGo+8bo+c= cloud.google.com/go/recommender v1.7.0/go.mod h1:XLHs/W+T8olwlGOgfQenXBTbIseGclClff6lhFVe9Bs= @@ -598,33 +855,52 @@ cloud.google.com/go/recommender v1.8.0/go.mod h1:PkjXrTT05BFKwxaUxQmtIlrtj0kph10 cloud.google.com/go/recommender v1.9.0/go.mod h1:PnSsnZY7q+VL1uax2JWkt/UegHssxjUVVCrX52CuEmQ= cloud.google.com/go/recommender v1.10.1/go.mod h1:XFvrE4Suqn5Cq0Lf+mCP6oBHD/yRMA8XxP5sb7Q7gpA= cloud.google.com/go/recommender v1.11.0/go.mod h1:kPiRQhPyTJ9kyXPCG6u/dlPLbYfFlkwHNRwdzPVAoII= +cloud.google.com/go/recommender v1.11.1/go.mod h1:sGwFFAyI57v2Hc5LbIj+lTwXipGu9NW015rkaEM5B18= +cloud.google.com/go/recommender v1.11.2/go.mod h1:AeoJuzOvFR/emIcXdVFkspVXVTYpliRCmKNYDnyBv6Y= +cloud.google.com/go/recommender v1.11.3/go.mod h1:+FJosKKJSId1MBFeJ/TTyoGQZiEelQQIZMKYYD8ruK4= cloud.google.com/go/redis v1.7.0/go.mod h1:V3x5Jq1jzUcg+UNsRvdmsfuFnit1cfe3Z/PGyq/lm4Y= cloud.google.com/go/redis v1.8.0/go.mod h1:Fm2szCDavWzBk2cDKxrkmWBqoCiL1+Ctwq7EyqBCA/A= cloud.google.com/go/redis v1.9.0/go.mod h1:HMYQuajvb2D0LvMgZmLDZW8V5aOC/WxstZHiy4g8OiA= cloud.google.com/go/redis v1.10.0/go.mod h1:ThJf3mMBQtW18JzGgh41/Wld6vnDDc/F/F35UolRZPM= cloud.google.com/go/redis v1.11.0/go.mod h1:/X6eicana+BWcUda5PpwZC48o37SiFVTFSs0fWAJ7uQ= cloud.google.com/go/redis v1.13.1/go.mod h1:VP7DGLpE91M6bcsDdMuyCm2hIpB6Vp2hI090Mfd1tcg= +cloud.google.com/go/redis v1.13.2/go.mod h1:0Hg7pCMXS9uz02q+LoEVl5dNHUkIQv+C/3L76fandSA= +cloud.google.com/go/redis v1.13.3/go.mod h1:vbUpCKUAZSYzFcWKmICnYgRAhTFg9r+djWqFxDYXi4U= +cloud.google.com/go/redis v1.14.1/go.mod h1:MbmBxN8bEnQI4doZPC1BzADU4HGocHBk2de3SbgOkqs= cloud.google.com/go/resourcemanager v1.3.0/go.mod h1:bAtrTjZQFJkiWTPDb1WBjzvc6/kifjj4QBYuKCCoqKA= cloud.google.com/go/resourcemanager v1.4.0/go.mod h1:MwxuzkumyTX7/a3n37gmsT3py7LIXwrShilPh3P1tR0= cloud.google.com/go/resourcemanager v1.5.0/go.mod h1:eQoXNAiAvCf5PXxWxXjhKQoTMaUSNrEfg+6qdf/wots= cloud.google.com/go/resourcemanager v1.6.0/go.mod h1:YcpXGRs8fDzcUl1Xw8uOVmI8JEadvhRIkoXXUNVYcVo= cloud.google.com/go/resourcemanager v1.7.0/go.mod h1:HlD3m6+bwhzj9XCouqmeiGuni95NTrExfhoSrkC/3EI= cloud.google.com/go/resourcemanager v1.9.1/go.mod h1:dVCuosgrh1tINZ/RwBufr8lULmWGOkPS8gL5gqyjdT8= +cloud.google.com/go/resourcemanager v1.9.2/go.mod h1:OujkBg1UZg5lX2yIyMo5Vz9O5hf7XQOSV7WxqxxMtQE= +cloud.google.com/go/resourcemanager v1.9.3/go.mod h1:IqrY+g0ZgLsihcfcmqSe+RKp1hzjXwG904B92AwBz6U= +cloud.google.com/go/resourcemanager v1.9.4/go.mod h1:N1dhP9RFvo3lUfwtfLWVxfUWq8+KUQ+XLlHLH3BoFJ0= cloud.google.com/go/resourcesettings v1.3.0/go.mod h1:lzew8VfESA5DQ8gdlHwMrqZs1S9V87v3oCnKCWoOuQU= cloud.google.com/go/resourcesettings v1.4.0/go.mod h1:ldiH9IJpcrlC3VSuCGvjR5of/ezRrOxFtpJoJo5SmXg= cloud.google.com/go/resourcesettings v1.5.0/go.mod h1:+xJF7QSG6undsQDfsCJyqWXyBwUoJLhetkRMDRnIoXA= cloud.google.com/go/resourcesettings v1.6.1/go.mod h1:M7mk9PIZrC5Fgsu1kZJci6mpgN8o0IUzVx3eJU3y4Jw= +cloud.google.com/go/resourcesettings v1.6.2/go.mod h1:mJIEDd9MobzunWMeniaMp6tzg4I2GvD3TTmPkc8vBXk= +cloud.google.com/go/resourcesettings v1.6.3/go.mod h1:pno5D+7oDYkMWZ5BpPsb4SO0ewg3IXcmmrUZaMJrFic= +cloud.google.com/go/resourcesettings v1.6.4/go.mod h1:pYTTkWdv2lmQcjsthbZLNBP4QW140cs7wqA3DuqErVI= cloud.google.com/go/retail v1.8.0/go.mod h1:QblKS8waDmNUhghY2TI9O3JLlFk8jybHeV4BF19FrE4= cloud.google.com/go/retail v1.9.0/go.mod h1:g6jb6mKuCS1QKnH/dpu7isX253absFl6iE92nHwlBUY= cloud.google.com/go/retail v1.10.0/go.mod h1:2gDk9HsL4HMS4oZwz6daui2/jmKvqShXKQuB2RZ+cCc= cloud.google.com/go/retail v1.11.0/go.mod h1:MBLk1NaWPmh6iVFSz9MeKG/Psyd7TAgm6y/9L2B4x9Y= cloud.google.com/go/retail v1.12.0/go.mod h1:UMkelN/0Z8XvKymXFbD4EhFJlYKRx1FGhQkVPU5kF14= cloud.google.com/go/retail v1.14.1/go.mod h1:y3Wv3Vr2k54dLNIrCzenyKG8g8dhvhncT2NcNjb/6gE= +cloud.google.com/go/retail v1.14.2/go.mod h1:W7rrNRChAEChX336QF7bnMxbsjugcOCPU44i5kbLiL8= +cloud.google.com/go/retail v1.14.3/go.mod h1:Omz2akDHeSlfCq8ArPKiBxlnRpKEBjUH386JYFLUvXo= +cloud.google.com/go/retail v1.14.4/go.mod h1:l/N7cMtY78yRnJqp5JW8emy7MB1nz8E4t2yfOmklYfg= cloud.google.com/go/run v0.2.0/go.mod h1:CNtKsTA1sDcnqqIFR3Pb5Tq0usWxJJvsWOCPldRU3Do= cloud.google.com/go/run v0.3.0/go.mod h1:TuyY1+taHxTjrD0ZFk2iAR+xyOXEA0ztb7U3UNA0zBo= cloud.google.com/go/run v0.8.0/go.mod h1:VniEnuBwqjigv0A7ONfQUaEItaiCRVujlMqerPPiktM= cloud.google.com/go/run v0.9.0/go.mod h1:Wwu+/vvg8Y+JUApMwEDfVfhetv30hCG4ZwDR/IXl2Qg= cloud.google.com/go/run v1.2.0/go.mod h1:36V1IlDzQ0XxbQjUx6IYbw8H3TJnWvhii963WW3B/bo= +cloud.google.com/go/run v1.3.0/go.mod h1:S/osX/4jIPZGg+ssuqh6GNgg7syixKe3YnprwehzHKU= +cloud.google.com/go/run v1.3.1/go.mod h1:cymddtZOzdwLIAsmS6s+Asl4JoXIDm/K1cpZTxV4Q5s= +cloud.google.com/go/run v1.3.2/go.mod h1:SIhmqArbjdU/D9M6JoHaAqnAMKLFtXaVdNeq04NjnVE= +cloud.google.com/go/run v1.3.3/go.mod h1:WSM5pGyJ7cfYyYbONVQBN4buz42zFqwG67Q3ch07iK4= cloud.google.com/go/scheduler v1.4.0/go.mod h1:drcJBmxF3aqZJRhmkHQ9b3uSSpQoltBPGPxGAWROx6s= cloud.google.com/go/scheduler v1.5.0/go.mod h1:ri073ym49NW3AfT6DZi21vLZrG07GXr5p3H1KxN5QlI= cloud.google.com/go/scheduler v1.6.0/go.mod h1:SgeKVM7MIwPn3BqtcBntpLyrIJftQISRrYB5ZtT+KOk= @@ -632,11 +908,17 @@ cloud.google.com/go/scheduler v1.7.0/go.mod h1:jyCiBqWW956uBjjPMMuX09n3x37mtyPJe cloud.google.com/go/scheduler v1.8.0/go.mod h1:TCET+Y5Gp1YgHT8py4nlg2Sew8nUHMqcpousDgXJVQc= cloud.google.com/go/scheduler v1.9.0/go.mod h1:yexg5t+KSmqu+njTIh3b7oYPheFtBWGcbVUYF1GGMIc= cloud.google.com/go/scheduler v1.10.1/go.mod h1:R63Ldltd47Bs4gnhQkmNDse5w8gBRrhObZ54PxgR2Oo= +cloud.google.com/go/scheduler v1.10.2/go.mod h1:O3jX6HRH5eKCA3FutMw375XHZJudNIKVonSCHv7ropY= +cloud.google.com/go/scheduler v1.10.3/go.mod h1:8ANskEM33+sIbpJ+R4xRfw/jzOG+ZFE8WVLy7/yGvbc= +cloud.google.com/go/scheduler v1.10.4/go.mod h1:MTuXcrJC9tqOHhixdbHDFSIuh7xZF2IysiINDuiq6NI= cloud.google.com/go/secretmanager v1.6.0/go.mod h1:awVa/OXF6IiyaU1wQ34inzQNc4ISIDIrId8qE5QGgKA= cloud.google.com/go/secretmanager v1.8.0/go.mod h1:hnVgi/bN5MYHd3Gt0SPuTPPp5ENina1/LxM+2W9U9J4= cloud.google.com/go/secretmanager v1.9.0/go.mod h1:b71qH2l1yHmWQHt9LC80akm86mX8AL6X1MA01dW8ht4= cloud.google.com/go/secretmanager v1.10.0/go.mod h1:MfnrdvKMPNra9aZtQFvBcvRU54hbPD8/HayQdlUgJpU= cloud.google.com/go/secretmanager v1.11.1/go.mod h1:znq9JlXgTNdBeQk9TBW/FnR/W4uChEKGeqQWAJ8SXFw= +cloud.google.com/go/secretmanager v1.11.2/go.mod h1:MQm4t3deoSub7+WNwiC4/tRYgDBHJgJPvswqQVB1Vss= +cloud.google.com/go/secretmanager v1.11.3/go.mod h1:0bA2o6FabmShrEy328i67aV+65XoUFFSmVeLBn/51jI= +cloud.google.com/go/secretmanager v1.11.4/go.mod h1:wreJlbS9Zdq21lMzWmJ0XhWW2ZxgPeahsqeV/vZoJ3w= cloud.google.com/go/security v1.5.0/go.mod h1:lgxGdyOKKjHL4YG3/YwIL2zLqMFCKs0UbQwgyZmfJl4= cloud.google.com/go/security v1.7.0/go.mod h1:mZklORHl6Bg7CNnnjLH//0UlAlaXqiG7Lb9PsPXLfD0= cloud.google.com/go/security v1.8.0/go.mod h1:hAQOwgmaHhztFhiQ41CjDODdWP0+AE1B3sX4OFlq+GU= @@ -645,6 +927,9 @@ cloud.google.com/go/security v1.10.0/go.mod h1:QtOMZByJVlibUT2h9afNDWRZ1G96gVywH cloud.google.com/go/security v1.12.0/go.mod h1:rV6EhrpbNHrrxqlvW0BWAIawFWq3X90SduMJdFwtLB8= cloud.google.com/go/security v1.13.0/go.mod h1:Q1Nvxl1PAgmeW0y3HTt54JYIvUdtcpYKVfIB8AOMZ+0= cloud.google.com/go/security v1.15.1/go.mod h1:MvTnnbsWnehoizHi09zoiZob0iCHVcL4AUBj76h9fXA= +cloud.google.com/go/security v1.15.2/go.mod h1:2GVE/v1oixIRHDaClVbHuPcZwAqFM28mXuAKCfMgYIg= +cloud.google.com/go/security v1.15.3/go.mod h1:gQ/7Q2JYUZZgOzqKtw9McShH+MjNvtDpL40J1cT+vBs= +cloud.google.com/go/security v1.15.4/go.mod h1:oN7C2uIZKhxCLiAAijKUCuHLZbIt/ghYEo8MqwD/Ty4= cloud.google.com/go/securitycenter v1.13.0/go.mod h1:cv5qNAqjY84FCN6Y9z28WlkKXyWsgLO832YiWwkCWcU= cloud.google.com/go/securitycenter v1.14.0/go.mod h1:gZLAhtyKv85n52XYWt6RmeBdydyxfPeTrpToDPw4Auc= cloud.google.com/go/securitycenter v1.15.0/go.mod h1:PeKJ0t8MoFmmXLXWm41JidyzI3PJjd8sXWaVqg43WWk= @@ -652,6 +937,9 @@ cloud.google.com/go/securitycenter v1.16.0/go.mod h1:Q9GMaLQFUD+5ZTabrbujNWLtSLZ cloud.google.com/go/securitycenter v1.18.1/go.mod h1:0/25gAzCM/9OL9vVx4ChPeM/+DlfGQJDwBy/UC8AKK0= cloud.google.com/go/securitycenter v1.19.0/go.mod h1:LVLmSg8ZkkyaNy4u7HCIshAngSQ8EcIRREP3xBnyfag= cloud.google.com/go/securitycenter v1.23.0/go.mod h1:8pwQ4n+Y9WCWM278R8W3nF65QtY172h4S8aXyI9/hsQ= +cloud.google.com/go/securitycenter v1.23.1/go.mod h1:w2HV3Mv/yKhbXKwOCu2i8bCuLtNP1IMHuiYQn4HJq5s= +cloud.google.com/go/securitycenter v1.24.1/go.mod h1:3h9IdjjHhVMXdQnmqzVnM7b0wMn/1O/U20eWVpMpZjI= +cloud.google.com/go/securitycenter v1.24.2/go.mod h1:l1XejOngggzqwr4Fa2Cn+iWZGf+aBLTXtB/vXjy5vXM= cloud.google.com/go/servicecontrol v1.4.0/go.mod h1:o0hUSJ1TXJAmi/7fLJAedOovnujSEvjKCAFNXPQ1RaU= cloud.google.com/go/servicecontrol v1.5.0/go.mod h1:qM0CnXHhyqKVuiZnGKrIurvVImCs8gmqWsDoqe9sU1s= cloud.google.com/go/servicecontrol v1.10.0/go.mod h1:pQvyvSRh7YzUF2efw7H87V92mxU8FnFDawMClGCNuAA= @@ -665,6 +953,9 @@ cloud.google.com/go/servicedirectory v1.8.0/go.mod h1:srXodfhY1GFIPvltunswqXpVxF cloud.google.com/go/servicedirectory v1.9.0/go.mod h1:29je5JjiygNYlmsGz8k6o+OZ8vd4f//bQLtvzkPPT/s= cloud.google.com/go/servicedirectory v1.10.1/go.mod h1:Xv0YVH8s4pVOwfM/1eMTl0XJ6bzIOSLDt8f8eLaGOxQ= cloud.google.com/go/servicedirectory v1.11.0/go.mod h1:Xv0YVH8s4pVOwfM/1eMTl0XJ6bzIOSLDt8f8eLaGOxQ= +cloud.google.com/go/servicedirectory v1.11.1/go.mod h1:tJywXimEWzNzw9FvtNjsQxxJ3/41jseeILgwU/QLrGI= +cloud.google.com/go/servicedirectory v1.11.2/go.mod h1:KD9hCLhncWRV5jJphwIpugKwM5bn1x0GyVVD4NO8mGg= +cloud.google.com/go/servicedirectory v1.11.3/go.mod h1:LV+cHkomRLr67YoQy3Xq2tUXBGOs5z5bPofdq7qtiAw= cloud.google.com/go/servicemanagement v1.4.0/go.mod h1:d8t8MDbezI7Z2R1O/wu8oTggo3BI2GKYbdG4y/SJTco= cloud.google.com/go/servicemanagement v1.5.0/go.mod h1:XGaCRe57kfqu4+lRxaFEAuqmjzF0r+gWHjWqKqBvKFo= cloud.google.com/go/servicemanagement v1.6.0/go.mod h1:aWns7EeeCOtGEX4OvZUWCCJONRZeFKiptqKf1D0l/Jc= @@ -677,11 +968,16 @@ cloud.google.com/go/shell v1.3.0/go.mod h1:VZ9HmRjZBsjLGXusm7K5Q5lzzByZmJHf1d0IW cloud.google.com/go/shell v1.4.0/go.mod h1:HDxPzZf3GkDdhExzD/gs8Grqk+dmYcEjGShZgYa9URw= cloud.google.com/go/shell v1.6.0/go.mod h1:oHO8QACS90luWgxP3N9iZVuEiSF84zNyLytb+qE2f9A= cloud.google.com/go/shell v1.7.1/go.mod h1:u1RaM+huXFaTojTbW4g9P5emOrrmLE69KrxqQahKn4g= +cloud.google.com/go/shell v1.7.2/go.mod h1:KqRPKwBV0UyLickMn0+BY1qIyE98kKyI216sH/TuHmc= +cloud.google.com/go/shell v1.7.3/go.mod h1:cTTEz/JdaBsQAeTQ3B6HHldZudFoYBOqjteev07FbIc= +cloud.google.com/go/shell v1.7.4/go.mod h1:yLeXB8eKLxw0dpEmXQ/FjriYrBijNsONpwnWsdPqlKM= cloud.google.com/go/spanner v1.41.0/go.mod h1:MLYDBJR/dY4Wt7ZaMIQ7rXOTLjYrmxLE/5ve9vFfWos= cloud.google.com/go/spanner v1.44.0/go.mod h1:G8XIgYdOK+Fbcpbs7p2fiprDw4CaZX63whnSMLVBxjk= cloud.google.com/go/spanner v1.45.0/go.mod h1:FIws5LowYz8YAE1J8fOS7DJup8ff7xJeetWEo5REA2M= cloud.google.com/go/spanner v1.47.0/go.mod h1:IXsJwVW2j4UKs0eYDqodab6HgGuA1bViSqW4uH9lfUI= cloud.google.com/go/spanner v1.49.0/go.mod h1:eGj9mQGK8+hkgSVbHNQ06pQ4oS+cyc4tXXd6Dif1KoM= +cloud.google.com/go/spanner v1.50.0/go.mod h1:eGj9mQGK8+hkgSVbHNQ06pQ4oS+cyc4tXXd6Dif1KoM= +cloud.google.com/go/spanner v1.51.0/go.mod h1:c5KNo5LQ1X5tJwma9rSQZsXNBDNvj4/n8BVc3LNahq0= cloud.google.com/go/speech v1.6.0/go.mod h1:79tcr4FHCimOp56lwC01xnt/WPJZc4v3gzyT7FoBkCM= cloud.google.com/go/speech v1.7.0/go.mod h1:KptqL+BAQIhMsj1kOP2la5DSEEerPDuOP/2mmkhHhZQ= cloud.google.com/go/speech v1.8.0/go.mod h1:9bYIl1/tjsAnMgKGHKmBZzXKEkGgtU+MpdDPTE9f7y0= @@ -690,6 +986,9 @@ cloud.google.com/go/speech v1.14.1/go.mod h1:gEosVRPJ9waG7zqqnsHpYTOoAS4KouMRLDF cloud.google.com/go/speech v1.15.0/go.mod h1:y6oH7GhqCaZANH7+Oe0BhgIogsNInLlz542tg3VqeYI= cloud.google.com/go/speech v1.17.1/go.mod h1:8rVNzU43tQvxDaGvqOhpDqgkJTFowBpDvCJ14kGlJYo= cloud.google.com/go/speech v1.19.0/go.mod h1:8rVNzU43tQvxDaGvqOhpDqgkJTFowBpDvCJ14kGlJYo= +cloud.google.com/go/speech v1.19.1/go.mod h1:WcuaWz/3hOlzPFOVo9DUsblMIHwxP589y6ZMtaG+iAA= +cloud.google.com/go/speech v1.19.2/go.mod h1:2OYFfj+Ch5LWjsaSINuCZsre/789zlcCI3SY4oAi2oI= +cloud.google.com/go/speech v1.20.1/go.mod h1:wwolycgONvfz2EDU8rKuHRW3+wc9ILPsAWoikBEWavY= cloud.google.com/go/storage v1.0.0/go.mod h1:IhtSnM/ZTZV8YYJWCY8RULGVqBDmpoyjwiyrjsg+URw= cloud.google.com/go/storage v1.5.0/go.mod h1:tpKbwo567HUNpVclU5sGELwQWBDZ8gh0ZeosJ0Rtdos= cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk= @@ -707,25 +1006,40 @@ cloud.google.com/go/storagetransfer v1.6.0/go.mod h1:y77xm4CQV/ZhFZH75PLEXY0ROiS cloud.google.com/go/storagetransfer v1.7.0/go.mod h1:8Giuj1QNb1kfLAiWM1bN6dHzfdlDAVC9rv9abHot2W4= cloud.google.com/go/storagetransfer v1.8.0/go.mod h1:JpegsHHU1eXg7lMHkvf+KE5XDJ7EQu0GwNJbbVGanEw= cloud.google.com/go/storagetransfer v1.10.0/go.mod h1:DM4sTlSmGiNczmV6iZyceIh2dbs+7z2Ayg6YAiQlYfA= +cloud.google.com/go/storagetransfer v1.10.1/go.mod h1:rS7Sy0BtPviWYTTJVWCSV4QrbBitgPeuK4/FKa4IdLs= +cloud.google.com/go/storagetransfer v1.10.2/go.mod h1:meIhYQup5rg9juQJdyppnA/WLQCOguxtk1pr3/vBWzA= +cloud.google.com/go/storagetransfer v1.10.3/go.mod h1:Up8LY2p6X68SZ+WToswpQbQHnJpOty/ACcMafuey8gc= cloud.google.com/go/talent v1.1.0/go.mod h1:Vl4pt9jiHKvOgF9KoZo6Kob9oV4lwd/ZD5Cto54zDRw= cloud.google.com/go/talent v1.2.0/go.mod h1:MoNF9bhFQbiJ6eFD3uSsg0uBALw4n4gaCaEjBw9zo8g= cloud.google.com/go/talent v1.3.0/go.mod h1:CmcxwJ/PKfRgd1pBjQgU6W3YBwiewmUzQYH5HHmSCmM= cloud.google.com/go/talent v1.4.0/go.mod h1:ezFtAgVuRf8jRsvyE6EwmbTK5LKciD4KVnHuDEFmOOA= cloud.google.com/go/talent v1.5.0/go.mod h1:G+ODMj9bsasAEJkQSzO2uHQWXHHXUomArjWQQYkqK6c= cloud.google.com/go/talent v1.6.2/go.mod h1:CbGvmKCG61mkdjcqTcLOkb2ZN1SrQI8MDyma2l7VD24= +cloud.google.com/go/talent v1.6.3/go.mod h1:xoDO97Qd4AK43rGjJvyBHMskiEf3KulgYzcH6YWOVoo= +cloud.google.com/go/talent v1.6.4/go.mod h1:QsWvi5eKeh6gG2DlBkpMaFYZYrYUnIpo34f6/V5QykY= +cloud.google.com/go/talent v1.6.5/go.mod h1:Mf5cma696HmE+P2BWJ/ZwYqeJXEeU0UqjHFXVLadEDI= cloud.google.com/go/texttospeech v1.4.0/go.mod h1:FX8HQHA6sEpJ7rCMSfXuzBcysDAuWusNNNvN9FELDd8= cloud.google.com/go/texttospeech v1.5.0/go.mod h1:oKPLhR4n4ZdQqWKURdwxMy0uiTS1xU161C8W57Wkea4= cloud.google.com/go/texttospeech v1.6.0/go.mod h1:YmwmFT8pj1aBblQOI3TfKmwibnsfvhIBzPXcW4EBovc= cloud.google.com/go/texttospeech v1.7.1/go.mod h1:m7QfG5IXxeneGqTapXNxv2ItxP/FS0hCZBwXYqucgSk= +cloud.google.com/go/texttospeech v1.7.2/go.mod h1:VYPT6aTOEl3herQjFHYErTlSZJ4vB00Q2ZTmuVgluD4= +cloud.google.com/go/texttospeech v1.7.3/go.mod h1:Av/zpkcgWfXlDLRYob17lqMstGZ3GqlvJXqKMp2u8so= +cloud.google.com/go/texttospeech v1.7.4/go.mod h1:vgv0002WvR4liGuSd5BJbWy4nDn5Ozco0uJymY5+U74= cloud.google.com/go/tpu v1.3.0/go.mod h1:aJIManG0o20tfDQlRIej44FcwGGl/cD0oiRyMKG19IQ= cloud.google.com/go/tpu v1.4.0/go.mod h1:mjZaX8p0VBgllCzF6wcU2ovUXN9TONFLd7iz227X2Xg= cloud.google.com/go/tpu v1.5.0/go.mod h1:8zVo1rYDFuW2l4yZVY0R0fb/v44xLh3llq7RuV61fPM= cloud.google.com/go/tpu v1.6.1/go.mod h1:sOdcHVIgDEEOKuqUoi6Fq53MKHJAtOwtz0GuKsWSH3E= +cloud.google.com/go/tpu v1.6.2/go.mod h1:NXh3NDwt71TsPZdtGWgAG5ThDfGd32X1mJ2cMaRlVgU= +cloud.google.com/go/tpu v1.6.3/go.mod h1:lxiueqfVMlSToZY1151IaZqp89ELPSrk+3HIQ5HRkbY= +cloud.google.com/go/tpu v1.6.4/go.mod h1:NAm9q3Rq2wIlGnOhpYICNI7+bpBebMJbh0yyp3aNw1Y= cloud.google.com/go/trace v1.3.0/go.mod h1:FFUE83d9Ca57C+K8rDl/Ih8LwOzWIV1krKgxg6N0G28= cloud.google.com/go/trace v1.4.0/go.mod h1:UG0v8UBqzusp+z63o7FK74SdFE+AXpCLdFb1rshXG+Y= cloud.google.com/go/trace v1.8.0/go.mod h1:zH7vcsbAhklH8hWFig58HvxcxyQbaIqMarMg9hn5ECA= cloud.google.com/go/trace v1.9.0/go.mod h1:lOQqpE5IaWY0Ixg7/r2SjixMuc6lfTFeO4QGM4dQWOk= cloud.google.com/go/trace v1.10.1/go.mod h1:gbtL94KE5AJLH3y+WVpfWILmqgc6dXcqgNXdOPAQTYk= +cloud.google.com/go/trace v1.10.2/go.mod h1:NPXemMi6MToRFcSxRl2uDnu/qAlAQ3oULUphcHGh1vA= +cloud.google.com/go/trace v1.10.3/go.mod h1:Ke1bgfc73RV3wUFml+uQp7EsDw4dGaETLxB7Iq/r4CY= +cloud.google.com/go/trace v1.10.4/go.mod h1:Nso99EDIK8Mj5/zmB+iGr9dosS/bzWCJ8wGmE6TXNWY= cloud.google.com/go/translate v1.3.0/go.mod h1:gzMUwRjvOqj5i69y/LYLd8RrNQk+hOmIXTi9+nb3Djs= cloud.google.com/go/translate v1.4.0/go.mod h1:06Dn/ppvLD6WvA5Rhdp029IX2Mi3Mn7fpMRLPvXT5Wg= cloud.google.com/go/translate v1.5.0/go.mod h1:29YDSYveqqpA1CQFD7NQuP49xymq17RXNaUDdc0mNu0= @@ -734,6 +1048,9 @@ cloud.google.com/go/translate v1.7.0/go.mod h1:lMGRudH1pu7I3n3PETiOB2507gf3HnfLV cloud.google.com/go/translate v1.8.1/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= cloud.google.com/go/translate v1.8.2/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= cloud.google.com/go/translate v1.9.0/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= +cloud.google.com/go/translate v1.9.1/go.mod h1:TWIgDZknq2+JD4iRcojgeDtqGEp154HN/uL6hMvylS8= +cloud.google.com/go/translate v1.9.2/go.mod h1:E3Tc6rUTsQkVrXW6avbUhKJSr7ZE3j7zNmqzXKHqRrY= +cloud.google.com/go/translate v1.9.3/go.mod h1:Kbq9RggWsbqZ9W5YpM94Q1Xv4dshw/gr/SHfsl5yCZ0= cloud.google.com/go/video v1.8.0/go.mod h1:sTzKFc0bUSByE8Yoh8X0mn8bMymItVGPfTuUBUyRgxk= cloud.google.com/go/video v1.9.0/go.mod h1:0RhNKFRF5v92f8dQt0yhaHrEuH95m068JYOvLZYnJSw= cloud.google.com/go/video v1.12.0/go.mod h1:MLQew95eTuaNDEGriQdcYn0dTwf9oWiA4uYebxM5kdg= @@ -743,12 +1060,18 @@ cloud.google.com/go/video v1.15.0/go.mod h1:SkgaXwT+lIIAKqWAJfktHT/RbgjSuY6DobxE cloud.google.com/go/video v1.17.1/go.mod h1:9qmqPqw/Ib2tLqaeHgtakU+l5TcJxCJbhFXM7UJjVzU= cloud.google.com/go/video v1.19.0/go.mod h1:9qmqPqw/Ib2tLqaeHgtakU+l5TcJxCJbhFXM7UJjVzU= cloud.google.com/go/video v1.20.0/go.mod h1:U3G3FTnsvAGqglq9LxgqzOiBc/Nt8zis8S+850N2DUM= +cloud.google.com/go/video v1.20.1/go.mod h1:3gJS+iDprnj8SY6pe0SwLeC5BUW80NjhwX7INWEuWGU= +cloud.google.com/go/video v1.20.2/go.mod h1:lrixr5JeKNThsgfM9gqtwb6Okuqzfo4VrY2xynaViTA= +cloud.google.com/go/video v1.20.3/go.mod h1:TnH/mNZKVHeNtpamsSPygSR0iHtvrR/cW1/GDjN5+GU= cloud.google.com/go/videointelligence v1.6.0/go.mod h1:w0DIDlVRKtwPCn/C4iwZIJdvC69yInhW0cfi+p546uU= cloud.google.com/go/videointelligence v1.7.0/go.mod h1:k8pI/1wAhjznARtVT9U1llUaFNPh7muw8QyOUpavru4= cloud.google.com/go/videointelligence v1.8.0/go.mod h1:dIcCn4gVDdS7yte/w+koiXn5dWVplOZkE+xwG9FgK+M= cloud.google.com/go/videointelligence v1.9.0/go.mod h1:29lVRMPDYHikk3v8EdPSaL8Ku+eMzDljjuvRs105XoU= cloud.google.com/go/videointelligence v1.10.0/go.mod h1:LHZngX1liVtUhZvi2uNS0VQuOzNi2TkY1OakiuoUOjU= cloud.google.com/go/videointelligence v1.11.1/go.mod h1:76xn/8InyQHarjTWsBR058SmlPCwQjgcvoW0aZykOvo= +cloud.google.com/go/videointelligence v1.11.2/go.mod h1:ocfIGYtIVmIcWk1DsSGOoDiXca4vaZQII1C85qtoplc= +cloud.google.com/go/videointelligence v1.11.3/go.mod h1:tf0NUaGTjU1iS2KEkGWvO5hRHeCkFK3nPo0/cOZhZAo= +cloud.google.com/go/videointelligence v1.11.4/go.mod h1:kPBMAYsTPFiQxMLmmjpcZUMklJp3nC9+ipJJtprccD8= cloud.google.com/go/vision v1.2.0/go.mod h1:SmNwgObm5DpFBme2xpyOyasvBc1aPdjvMk2bBk0tKD0= cloud.google.com/go/vision/v2 v2.2.0/go.mod h1:uCdV4PpN1S0jyCyq8sIM42v2Y6zOLkZs+4R9LrGYwFo= cloud.google.com/go/vision/v2 v2.3.0/go.mod h1:UO61abBx9QRMFkNBbf1D8B1LXdS2cGiiCRx0vSpZoUo= @@ -757,30 +1080,48 @@ cloud.google.com/go/vision/v2 v2.5.0/go.mod h1:MmaezXOOE+IWa+cS7OhRRLK2cNv1ZL98z cloud.google.com/go/vision/v2 v2.6.0/go.mod h1:158Hes0MvOS9Z/bDMSFpjwsUrZ5fPrdwuyyvKSGAGMY= cloud.google.com/go/vision/v2 v2.7.0/go.mod h1:H89VysHy21avemp6xcf9b9JvZHVehWbET0uT/bcuY/0= cloud.google.com/go/vision/v2 v2.7.2/go.mod h1:jKa8oSYBWhYiXarHPvP4USxYANYUEdEsQrloLjrSwJU= +cloud.google.com/go/vision/v2 v2.7.3/go.mod h1:V0IcLCY7W+hpMKXK1JYE0LV5llEqVmj+UJChjvA1WsM= +cloud.google.com/go/vision/v2 v2.7.4/go.mod h1:ynDKnsDN/0RtqkKxQZ2iatv3Dm9O+HfRb5djl7l4Vvw= +cloud.google.com/go/vision/v2 v2.7.5/go.mod h1:GcviprJLFfK9OLf0z8Gm6lQb6ZFUulvpZws+mm6yPLM= cloud.google.com/go/vmmigration v1.2.0/go.mod h1:IRf0o7myyWFSmVR1ItrBSFLFD/rJkfDCUTO4vLlJvsE= cloud.google.com/go/vmmigration v1.3.0/go.mod h1:oGJ6ZgGPQOFdjHuocGcLqX4lc98YQ7Ygq8YQwHh9A7g= cloud.google.com/go/vmmigration v1.5.0/go.mod h1:E4YQ8q7/4W9gobHjQg4JJSgXXSgY21nA5r8swQV+Xxc= cloud.google.com/go/vmmigration v1.6.0/go.mod h1:bopQ/g4z+8qXzichC7GW1w2MjbErL54rk3/C843CjfY= cloud.google.com/go/vmmigration v1.7.1/go.mod h1:WD+5z7a/IpZ5bKK//YmT9E047AD+rjycCAvyMxGJbro= +cloud.google.com/go/vmmigration v1.7.2/go.mod h1:iA2hVj22sm2LLYXGPT1pB63mXHhrH1m/ruux9TwWLd8= +cloud.google.com/go/vmmigration v1.7.3/go.mod h1:ZCQC7cENwmSWlwyTrZcWivchn78YnFniEQYRWQ65tBo= +cloud.google.com/go/vmmigration v1.7.4/go.mod h1:yBXCmiLaB99hEl/G9ZooNx2GyzgsjKnw5fWcINRgD70= cloud.google.com/go/vmwareengine v0.1.0/go.mod h1:RsdNEf/8UDvKllXhMz5J40XxDrNJNN4sagiox+OI208= cloud.google.com/go/vmwareengine v0.2.2/go.mod h1:sKdctNJxb3KLZkE/6Oui94iw/xs9PRNC2wnNLXsHvH8= cloud.google.com/go/vmwareengine v0.3.0/go.mod h1:wvoyMvNWdIzxMYSpH/R7y2h5h3WFkx6d+1TIsP39WGY= cloud.google.com/go/vmwareengine v0.4.1/go.mod h1:Px64x+BvjPZwWuc4HdmVhoygcXqEkGHXoa7uyfTgSI0= cloud.google.com/go/vmwareengine v1.0.0/go.mod h1:Px64x+BvjPZwWuc4HdmVhoygcXqEkGHXoa7uyfTgSI0= +cloud.google.com/go/vmwareengine v1.0.1/go.mod h1:aT3Xsm5sNx0QShk1Jc1B8OddrxAScYLwzVoaiXfdzzk= +cloud.google.com/go/vmwareengine v1.0.2/go.mod h1:xMSNjIk8/itYrz1JA8nV3Ajg4L4n3N+ugP8JKzk3OaA= +cloud.google.com/go/vmwareengine v1.0.3/go.mod h1:QSpdZ1stlbfKtyt6Iu19M6XRxjmXO+vb5a/R6Fvy2y4= cloud.google.com/go/vpcaccess v1.4.0/go.mod h1:aQHVbTWDYUR1EbTApSVvMq1EnT57ppDmQzZ3imqIk4w= cloud.google.com/go/vpcaccess v1.5.0/go.mod h1:drmg4HLk9NkZpGfCmZ3Tz0Bwnm2+DKqViEpeEpOq0m8= cloud.google.com/go/vpcaccess v1.6.0/go.mod h1:wX2ILaNhe7TlVa4vC5xce1bCnqE3AeH27RV31lnmZes= cloud.google.com/go/vpcaccess v1.7.1/go.mod h1:FogoD46/ZU+JUBX9D606X21EnxiszYi2tArQwLY4SXs= +cloud.google.com/go/vpcaccess v1.7.2/go.mod h1:mmg/MnRHv+3e8FJUjeSibVFvQF1cCy2MsFaFqxeY1HU= +cloud.google.com/go/vpcaccess v1.7.3/go.mod h1:YX4skyfW3NC8vI3Fk+EegJnlYFatA+dXK4o236EUCUc= +cloud.google.com/go/vpcaccess v1.7.4/go.mod h1:lA0KTvhtEOb/VOdnH/gwPuOzGgM+CWsmGu6bb4IoMKk= cloud.google.com/go/webrisk v1.4.0/go.mod h1:Hn8X6Zr+ziE2aNd8SliSDWpEnSS1u4R9+xXZmFiHmGE= cloud.google.com/go/webrisk v1.5.0/go.mod h1:iPG6fr52Tv7sGk0H6qUFzmL3HHZev1htXuWDEEsqMTg= cloud.google.com/go/webrisk v1.6.0/go.mod h1:65sW9V9rOosnc9ZY7A7jsy1zoHS5W9IAXv6dGqhMQMc= cloud.google.com/go/webrisk v1.7.0/go.mod h1:mVMHgEYH0r337nmt1JyLthzMr6YxwN1aAIEc2fTcq7A= cloud.google.com/go/webrisk v1.8.0/go.mod h1:oJPDuamzHXgUc+b8SiHRcVInZQuybnvEW72PqTc7sSg= cloud.google.com/go/webrisk v1.9.1/go.mod h1:4GCmXKcOa2BZcZPn6DCEvE7HypmEJcJkr4mtM+sqYPc= +cloud.google.com/go/webrisk v1.9.2/go.mod h1:pY9kfDgAqxUpDBOrG4w8deLfhvJmejKB0qd/5uQIPBc= +cloud.google.com/go/webrisk v1.9.3/go.mod h1:RUYXe9X/wBDXhVilss7EDLW9ZNa06aowPuinUOPCXH8= +cloud.google.com/go/webrisk v1.9.4/go.mod h1:w7m4Ib4C+OseSr2GL66m0zMBywdrVNTDKsdEsfMl7X0= cloud.google.com/go/websecurityscanner v1.3.0/go.mod h1:uImdKm2wyeXQevQJXeh8Uun/Ym1VqworNDlBXQevGMo= cloud.google.com/go/websecurityscanner v1.4.0/go.mod h1:ebit/Fp0a+FWu5j4JOmJEV8S8CzdTkAS77oDsiSqYWQ= cloud.google.com/go/websecurityscanner v1.5.0/go.mod h1:Y6xdCPy81yi0SQnDY1xdNTNpfY1oAgXUlcfN3B3eSng= cloud.google.com/go/websecurityscanner v1.6.1/go.mod h1:Njgaw3rttgRHXzwCB8kgCYqv5/rGpFCsBOvPbYgszpg= +cloud.google.com/go/websecurityscanner v1.6.2/go.mod h1:7YgjuU5tun7Eg2kpKgGnDuEOXWIrh8x8lWrJT4zfmas= +cloud.google.com/go/websecurityscanner v1.6.3/go.mod h1:x9XANObUFR+83Cya3g/B9M/yoHVqzxPnFtgF8yYGAXw= +cloud.google.com/go/websecurityscanner v1.6.4/go.mod h1:mUiyMQ+dGpPPRkHgknIZeCzSHJ45+fY4F52nZFDHm2o= cloud.google.com/go/workflows v1.6.0/go.mod h1:6t9F5h/unJz41YqfBmqSASJSXccBLtD1Vwf+KmJENM0= cloud.google.com/go/workflows v1.7.0/go.mod h1:JhSrZuVZWuiDfKEFxU0/F1PQjmpnpcoISEXH2bcHC3M= cloud.google.com/go/workflows v1.8.0/go.mod h1:ysGhmEajwZxGn1OhGOGKsTXc5PyxOc0vfKf5Af+to4M= @@ -788,6 +1129,9 @@ cloud.google.com/go/workflows v1.9.0/go.mod h1:ZGkj1aFIOd9c8Gerkjjq7OW7I5+l6cSvT cloud.google.com/go/workflows v1.10.0/go.mod h1:fZ8LmRmZQWacon9UCX1r/g/DfAXx5VcPALq2CxzdePw= cloud.google.com/go/workflows v1.11.1/go.mod h1:Z+t10G1wF7h8LgdY/EmRcQY8ptBD/nvofaL6FqlET6g= cloud.google.com/go/workflows v1.12.0/go.mod h1:PYhSk2b6DhZ508tj8HXKaBh+OFe+xdl0dHF/tJdzPQM= +cloud.google.com/go/workflows v1.12.1/go.mod h1:5A95OhD/edtOhQd/O741NSfIMezNTbCwLM1P1tBRGHM= +cloud.google.com/go/workflows v1.12.2/go.mod h1:+OmBIgNqYJPVggnMo9nqmizW0qEXHhmnAzK/CnBqsHc= +cloud.google.com/go/workflows v1.12.3/go.mod h1:fmOUeeqEwPzIU81foMjTRQIdwQHADi/vEr1cx9R1m5g= dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= gioui.org v0.0.0-20210308172011-57750fc8a0a6/go.mod h1:RSH6KIUZ0p2xy5zHDxgAM4zumjgTw83q2ge/PI+yyw8= git.sr.ht/~sbinet/gg v0.3.1/go.mod h1:KGYtlADtqsqANL9ueOFkWymvzUvLMQllU5Ixo+8v3pc= @@ -832,6 +1176,7 @@ github.com/cncf/xds/go v0.0.0-20230105202645-06c439db220b/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20230310173818-32f1caf87195/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230428030218-4003588d1b74/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20231109132714-523115ebc101/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -930,8 +1275,11 @@ github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/ github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.7/go.mod h1:n+brtR0CgQNWTVd5ZUFpTBC8YFBDLK/h/bpaJ8/DtOE= github.com/google/go-cmp v0.5.8/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= -github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38= github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/google/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-pkcs11 v0.2.0/go.mod h1:6eQoGcuNJpa7jnd5pMGdkSaQpNDYvPlXWMcjXXThLlY= +github.com/google/go-pkcs11 v0.2.1-0.20230907215043-c6f79328ddf9/go.mod h1:6eQoGcuNJpa7jnd5pMGdkSaQpNDYvPlXWMcjXXThLlY= github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= github.com/google/martian/v3 v3.0.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= github.com/google/martian/v3 v3.1.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= @@ -956,15 +1304,19 @@ github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm4 github.com/google/s2a-go v0.1.0/go.mod h1:OJpEgntRZo8ugHpF9hkoLJbS5dSI20XZeXJ9JVywLlM= github.com/google/s2a-go v0.1.3/go.mod h1:Ej+mSEMGRnqRzjc7VtF+jdBwYG5fuJfiZ8ELkjEwM0A= github.com/google/s2a-go v0.1.4/go.mod h1:Ej+mSEMGRnqRzjc7VtF+jdBwYG5fuJfiZ8ELkjEwM0A= +github.com/google/s2a-go v0.1.7/go.mod h1:50CgR4k1jNlWBu4UfS4AcfhVe1r6pdZPygJ3R8F0Qdw= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.4.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/enterprise-certificate-proxy v0.0.0-20220520183353-fd19c99a87aa/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.1.0/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.2.0/go.mod h1:8C0jb7/mgJe/9KK8Lm7X9ctZC2t60YyIpYEI16jx0Qg= github.com/googleapis/enterprise-certificate-proxy v0.2.1/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= github.com/googleapis/enterprise-certificate-proxy v0.2.3/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= github.com/googleapis/enterprise-certificate-proxy v0.2.4/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= +github.com/googleapis/enterprise-certificate-proxy v0.2.5/go.mod h1:RxW0N9901Cko1VOCW3SXCpWP+mlIEkk2tP7jnHy9a3w= +github.com/googleapis/enterprise-certificate-proxy v0.3.2/go.mod h1:VLSiSSBs/ksPL8kq3OBOQ6WRI2QnaFynd1DCjZ62+V0= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= github.com/googleapis/gax-go/v2 v2.1.0/go.mod h1:Q3nei7sK6ybPYH7twZdmQpAd1MKb7pfu6SK+H1/DsU0= @@ -1090,7 +1442,11 @@ golang.org/x/crypto v0.1.0/go.mod h1:RecgLatLF4+eUMCP1PoPZQb+cVrJcOPbHkTkbkB9sbw golang.org/x/crypto v0.7.0/go.mod h1:pYwdfH91IfpZVANVyUOhSIPZaFoJGxTFbZhFTx+dXZU= golang.org/x/crypto v0.9.0/go.mod h1:yrmDGqONDYtNj3tH8X9dzUun2m2lzPa9ngI6/RUPGR0= golang.org/x/crypto v0.10.0/go.mod h1:o4eNf7Ede1fv+hwOwZsTHl9EsPFO6q6ZvYR8vYfY45I= +golang.org/x/crypto v0.11.0/go.mod h1:xgJhtzW8F9jGdVFWZESrid1U1bjeNy4zgy5cRr/CIio= +golang.org/x/crypto v0.12.0/go.mod h1:NF0Gs7EO5K4qLn+Ylc+fih8BSTeIjAP05siRnAh98yw= +golang.org/x/crypto v0.13.0/go.mod h1:y6Z2r+Rw4iayiXXAIxJIDAJ1zMW4yaTpebo8fPOliYc= golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4= +golang.org/x/crypto v0.15.0/go.mod h1:4ChreQoLWfG3xLDer1WdlH5NdlQ3+mwnQq1YTKY+72g= golang.org/x/crypto v0.18.0/go.mod h1:R0j02AL6hcrfOiy9T4ZYp/rcWeMxM3L6QYxlOuEG1mg= golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20180807140117-3d87b88a115f/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= @@ -1212,7 +1568,11 @@ golang.org/x/net v0.8.0/go.mod h1:QVkue5JL9kW//ek3r6jTKnTFis1tRmNAW2P1shuFdJc= golang.org/x/net v0.9.0/go.mod h1:d48xBJpPfHeWQsugry2m+kC02ZBRGRgulfHnEXEuWns= golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg= golang.org/x/net v0.11.0/go.mod h1:2L/ixqYpgIVXmeoSA/4Lu7BzTG4KIyPIryS4IsOd1oQ= +golang.org/x/net v0.12.0/go.mod h1:zEVYFnQC7m/vmpQFELhcD1EWkZlX69l4oqgmer6hfKA= +golang.org/x/net v0.14.0/go.mod h1:PpSgVXXLK0OxS0F31C1/tv6XNguvCrnXIDrFMspZIUI= golang.org/x/net v0.16.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= +golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= +golang.org/x/net v0.18.0/go.mod h1:/czyP5RqHAH4odGYxBJ1qz0+CE5WZ+2j1YgoEo8F2jQ= golang.org/x/net v0.20.0 h1:aCL9BSgETF1k+blQaYUBx9hJ9LOGP3gAVemcZlf1Kpo= golang.org/x/net v0.20.0/go.mod h1:z8BVo6PvndSri0LbOE3hAn0apkU+1YvI6E70E9jsnvY= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= @@ -1245,7 +1605,10 @@ golang.org/x/oauth2 v0.5.0/go.mod h1:9/XBHVqLaWO3/BRHs5jbpYCnOZVjj5V0ndyaAM7KB4I golang.org/x/oauth2 v0.6.0/go.mod h1:ycmewcwgD4Rpr3eZJLSB4Kyyljb3qDh40vJ8STE5HKw= golang.org/x/oauth2 v0.7.0/go.mod h1:hPLQkd9LyjfXTiRohC/41GhcFqxisoUQ99sCUOHO9x4= golang.org/x/oauth2 v0.8.0/go.mod h1:yr7u4HXZRm1R1kBWqr/xKNqewf0plRYoB7sla+BCIXE= +golang.org/x/oauth2 v0.10.0/go.mod h1:kTpgurOux7LqtuxjuyZa4Gj2gdezIt/jQtGnNFfypQI= +golang.org/x/oauth2 v0.11.0/go.mod h1:LdF7O/8bLR/qWK9DrpXmbHLTouvRHK0SgJl0GmDBchk= golang.org/x/oauth2 v0.13.0/go.mod h1:/JMhi4ZRXAf4HG9LiNmxvk+45+96RUlVThiH8FzNBn0= +golang.org/x/oauth2 v0.14.0/go.mod h1:lAtNWgaWfL4cm7j2OV8TxGi9Qb7ECORx8DktCY74OwM= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -1265,6 +1628,7 @@ golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.2.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= golang.org/x/sync v0.4.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= +golang.org/x/sync v0.5.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/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-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -1345,7 +1709,11 @@ golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.9.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.10.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.14.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/sys v0.16.0 h1:xWw16ngr6ZMtmxDyKyIgsE93KNKz5HKmMa3b8ALHidU= golang.org/x/sys v0.16.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= @@ -1359,7 +1727,11 @@ golang.org/x/term v0.6.0/go.mod h1:m6U89DPEgQRMq3DNkDClhWw02AUbt2daBVO4cn4Hv9U= golang.org/x/term v0.7.0/go.mod h1:P32HKFT3hSsZrRxla30E9HqToFYAQPCMs/zFMBUFqPY= golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo= golang.org/x/term v0.9.0/go.mod h1:M6DEAAIenWoTxdKrOltXcmDY3rSplQUkrvaDU5FcQyo= +golang.org/x/term v0.10.0/go.mod h1:lpqdcUyK/oCiQxvxVrppt5ggO2KCZ5QblwqPnfZ6d5o= +golang.org/x/term v0.11.0/go.mod h1:zC9APTIj3jG3FdV/Ons+XE1riIZXG4aZ4GTHiPZJPIU= +golang.org/x/term v0.12.0/go.mod h1:owVbMEjm3cBLCHdkQu9b1opXd4ETQWc3BhuQGKgXgvU= golang.org/x/term v0.13.0/go.mod h1:LTmsnFJwVN6bCy1rVCoS+qHT1HhALEFxKncY3WNNh4U= +golang.org/x/term v0.14.0/go.mod h1:TySc+nGkYR6qt8km8wUhuFRTVSMIX3XPR58y2lC8vww= golang.org/x/term v0.16.0/go.mod h1:yn7UURbUtPyrVJPGPq404EukNFxcm/foM+bV/bfcDsY= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -1378,6 +1750,8 @@ golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= golang.org/x/text v0.8.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.10.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= +golang.org/x/text v0.11.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= +golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ= golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= @@ -1530,6 +1904,8 @@ google.golang.org/api v0.124.0/go.mod h1:xu2HQurE5gi/3t1aFCvhPD781p0a3p11sdunTJ2 google.golang.org/api v0.125.0/go.mod h1:mBwVAtz+87bEN6CbA1GtZPDOqY2R5ONPqJeIlvyo4Aw= google.golang.org/api v0.126.0/go.mod h1:mBwVAtz+87bEN6CbA1GtZPDOqY2R5ONPqJeIlvyo4Aw= google.golang.org/api v0.128.0/go.mod h1:Y611qgqaE92On/7g65MQgxYul3c0rEB894kniWLY750= +google.golang.org/api v0.139.0/go.mod h1:CVagp6Eekz9CjGZ718Z+sloknzkDJE7Vc1Ckj9+viBk= +google.golang.org/api v0.149.0/go.mod h1:Mwn1B7JTXrzXtnvmzQE2BD6bYZQ8DShKZDZbeN9I7qI= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -1677,37 +2053,57 @@ google.golang.org/genproto v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:zqTuNwFl google.golang.org/genproto v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:xZnkP7mREFX5MORlOPEzLMr+90PPZQ2QWzrVTWfAq64= google.golang.org/genproto v0.0.0-20230629202037-9506855d4529/go.mod h1:xZnkP7mREFX5MORlOPEzLMr+90PPZQ2QWzrVTWfAq64= google.golang.org/genproto v0.0.0-20230706204954-ccb25ca9f130/go.mod h1:O9kGHb51iE/nOGvQaDUuadVYqovW56s5emA88lQnj6Y= +google.golang.org/genproto v0.0.0-20230711160842-782d3b101e98/go.mod h1:S7mY02OqCJTD0E1OiQy1F72PWFB4bZJ87cAtLPYgDR0= google.golang.org/genproto v0.0.0-20230726155614-23370e0ffb3e/go.mod h1:0ggbjUrZYpy1q+ANUS30SEoGZ53cdfwtbuG7Ptgy108= google.golang.org/genproto v0.0.0-20230803162519-f966b187b2e5/go.mod h1:oH/ZOT02u4kWEp7oYBGYFFkCdKS/uYR9Z7+0/xuuFp8= google.golang.org/genproto v0.0.0-20230821184602-ccc8af3d0e93/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= +google.golang.org/genproto v0.0.0-20230822172742-b8732ec3820d/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= google.golang.org/genproto v0.0.0-20230913181813-007df8e322eb/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= google.golang.org/genproto v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:CCviP9RmpZ1mxVr8MUjCnSiY09IbAXZxhLE6EhHIdPU= -google.golang.org/genproto v0.0.0-20231002182017-d307bd883b97 h1:SeZZZx0cP0fqUyA+oRzP9k7cSwJlvDFiROO72uwD6i0= google.golang.org/genproto v0.0.0-20231002182017-d307bd883b97/go.mod h1:t1VqOqqvce95G3hIDCT5FeO3YUc6Q4Oe24L/+rNMxRk= +google.golang.org/genproto v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:EMfReVxb80Dq1hhioy0sOsY9jCE46YDgHlJ7fWVUWRE= +google.golang.org/genproto v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:CgAqfJo+Xmu0GwA0411Ht3OU3OntXwsGmrmjI8ioGXI= +google.golang.org/genproto v0.0.0-20231030173426-d783a09b4405/go.mod h1:3WDQMjmJk36UQhjQ89emUzb1mdaHcPeeAh4SCBKznB4= +google.golang.org/genproto v0.0.0-20231106174013-bbf56f31fb17 h1:wpZ8pe2x1Q3f2KyT5f8oP/fa9rHAKgFPr/HZdNuS+PQ= +google.golang.org/genproto v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:J7XzRzVy1+IPwWHZUzoD0IccYZIrXILAQpc+Qy9CMhY= google.golang.org/genproto/googleapis/api v0.0.0-20230525234020-1aefcd67740a/go.mod h1:ts19tUU+Z0ZShN1y3aPyq2+O3d5FUNNgT6FtOzmrNn8= google.golang.org/genproto/googleapis/api v0.0.0-20230525234035-dd9d682886f9/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= google.golang.org/genproto/googleapis/api v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= google.golang.org/genproto/googleapis/api v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= google.golang.org/genproto/googleapis/api v0.0.0-20230629202037-9506855d4529/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= google.golang.org/genproto/googleapis/api v0.0.0-20230706204954-ccb25ca9f130/go.mod h1:mPBs5jNgx2GuQGvFwUvVKqtn6HsUw9nP64BedgvqEsQ= +google.golang.org/genproto/googleapis/api v0.0.0-20230711160842-782d3b101e98/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ= google.golang.org/genproto/googleapis/api v0.0.0-20230726155614-23370e0ffb3e/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ= google.golang.org/genproto/googleapis/api v0.0.0-20230803162519-f966b187b2e5/go.mod h1:5DZzOUPCLYL3mNkQ0ms0F3EuUNZ7py1Bqeq6sxzI7/Q= +google.golang.org/genproto/googleapis/api v0.0.0-20230822172742-b8732ec3820d/go.mod h1:KjSP20unUpOx5kyQUFa7k4OJg0qeJ7DEZflGDu2p6Bk= google.golang.org/genproto/googleapis/api v0.0.0-20230913181813-007df8e322eb/go.mod h1:KjSP20unUpOx5kyQUFa7k4OJg0qeJ7DEZflGDu2p6Bk= google.golang.org/genproto/googleapis/api v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:RdyHbowztCGQySiCvQPgWQWgWhGnouTdCflKoDBt32U= google.golang.org/genproto/googleapis/api v0.0.0-20231002182017-d307bd883b97/go.mod h1:iargEX0SFPm3xcfMI0d1domjg0ZF4Aa0p2awqyxhvF0= +google.golang.org/genproto/googleapis/api v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:SUBoKXbI1Efip18FClrQVGjWcyd0QZd8KkvdP34t7ww= +google.golang.org/genproto/googleapis/api v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:IBQ646DjkDkvUIsVq/cc03FUFQ9wbZu7yE396YcL870= +google.golang.org/genproto/googleapis/api v0.0.0-20231030173426-d783a09b4405/go.mod h1:oT32Z4o8Zv2xPQTg0pbVaPr0MPOH6f14RgXt7zfIpwg= +google.golang.org/genproto/googleapis/api v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:0xJLfVdJqpAPl8tDg1ujOCGzx6LFLttXT5NhllGOXY4= google.golang.org/genproto/googleapis/bytestream v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:ylj+BE99M198VPbBh6A8d9n3w8fChvyLK3wwBOjXBFA= +google.golang.org/genproto/googleapis/bytestream v0.0.0-20230807174057-1744710a1577/go.mod h1:NjCQG/D8JandXxM57PZbAJL1DCNL6EypA0vPPwfsc7c= +google.golang.org/genproto/googleapis/bytestream v0.0.0-20231030173426-d783a09b4405/go.mod h1:GRUCuLdzVqZte8+Dl/D4N25yLzcGqqWaYkeVOwulFqw= google.golang.org/genproto/googleapis/rpc v0.0.0-20230525234015-3fc162c6f38a/go.mod h1:xURIpW9ES5+/GZhnV6beoEtxQrnkRGIfP5VQG2tCBLc= google.golang.org/genproto/googleapis/rpc v0.0.0-20230525234030-28d5490b6b19/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= google.golang.org/genproto/googleapis/rpc v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= google.golang.org/genproto/googleapis/rpc v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= google.golang.org/genproto/googleapis/rpc v0.0.0-20230629202037-9506855d4529/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= google.golang.org/genproto/googleapis/rpc v0.0.0-20230706204954-ccb25ca9f130/go.mod h1:8mL13HKkDa+IuJ8yruA3ci0q+0vsUz4m//+ottjwS5o= +google.golang.org/genproto/googleapis/rpc v0.0.0-20230711160842-782d3b101e98/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM= google.golang.org/genproto/googleapis/rpc v0.0.0-20230731190214-cbb8c96f2d6d/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM= google.golang.org/genproto/googleapis/rpc v0.0.0-20230803162519-f966b187b2e5/go.mod h1:zBEcrKX2ZOcEkHWxBPAIvYUWOKKMIhYcmNiUIu2ji3I= +google.golang.org/genproto/googleapis/rpc v0.0.0-20230822172742-b8732ec3820d/go.mod h1:+Bk1OCOj40wS2hwAMA+aCW9ypzm63QTBBHp6lQ3p+9M= google.golang.org/genproto/googleapis/rpc v0.0.0-20230920183334-c177e329c48b/go.mod h1:+Bk1OCOj40wS2hwAMA+aCW9ypzm63QTBBHp6lQ3p+9M= google.golang.org/genproto/googleapis/rpc v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:KSqppvjFjtoCI+KGd4PELB0qLNxdJHRGqRI09mB6pQA= -google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97 h1:6GQBEOdGkX6MMTLT9V+TjtIRZCw9VPD5Z+yHY9wMgS0= google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97/go.mod h1:v7nGkzlmW8P3n/bKmWBn2WpBjpOEx8Q6gMueudAmKfY= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:4cYg8o5yUbm77w8ZX00LhMVNl/YVBFJRYWDc0uYWMs0= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:swOH3j0KzcDDgGUWr+SNpyTen5YrXjS3eyPzFYKc6lc= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231030173426-d783a09b4405/go.mod h1:67X1fPuzjcrkymZzZV1vvkFeTn2Rvc6lYF9MYFGCcwE= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17 h1:Jyp0Hsi0bmHXG6k9eATXoYtjd6e2UzZ1SCn/wIupY14= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:oQ5rr10WTTMvP4A36n8JpR1OrO1BEiV4f78CneXZxkA= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= @@ -1753,8 +2149,11 @@ google.golang.org/grpc v1.55.0/go.mod h1:iYEXKGkEBhg1PjZQvoYEVPTDkHo1/bjTnfwTeGO google.golang.org/grpc v1.56.1/go.mod h1:I9bI3vqKfayGqPUAwGdOSu7kt6oIJLixfffKrpXqQ9s= google.golang.org/grpc v1.56.2/go.mod h1:I9bI3vqKfayGqPUAwGdOSu7kt6oIJLixfffKrpXqQ9s= google.golang.org/grpc v1.57.0/go.mod h1:Sd+9RMTACXwmub0zcNY2c4arhtrbBYD1AUHI/dt16Mo= -google.golang.org/grpc v1.60.1 h1:26+wFr+cNqSGFcOXcabYC0lUVJVRa2Sb2ortSK7VrEU= -google.golang.org/grpc v1.60.1/go.mod h1:OlCHIeLYqSSsLi6i49B5QGdzaMZK9+M7LXN2FKz4eGM= +google.golang.org/grpc v1.58.2/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0= +google.golang.org/grpc v1.58.3/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0= +google.golang.org/grpc v1.59.0/go.mod h1:aUPDwccQo6OTjy7Hct4AfBPD1GptF4fyUjIkQ9YtF98= +google.golang.org/grpc v1.61.0 h1:TOvOcuXn30kRao+gfcvsebNEa5iZIiLkisYEkf7R7o0= +google.golang.org/grpc v1.61.0/go.mod h1:VUbo7IFqmF1QtCAstipjG0GIoq49KvMe9+h1jFLBNJs= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= diff --git a/examples/load-reporting-service/go.mod b/examples/load-reporting-service/go.mod index 505cd31104e2d..72b460b37f3df 100644 --- a/examples/load-reporting-service/go.mod +++ b/examples/load-reporting-service/go.mod @@ -5,5 +5,5 @@ go 1.13 require ( github.com/envoyproxy/go-control-plane v0.12.0 github.com/golang/protobuf v1.5.3 - google.golang.org/grpc v1.60.1 + google.golang.org/grpc v1.61.0 ) diff --git a/examples/load-reporting-service/go.sum b/examples/load-reporting-service/go.sum index 25019aec0e7c2..52de68a071178 100644 --- a/examples/load-reporting-service/go.sum +++ b/examples/load-reporting-service/go.sum @@ -41,16 +41,24 @@ cloud.google.com/go v0.110.4/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5x cloud.google.com/go v0.110.6/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5xsI= cloud.google.com/go v0.110.7/go.mod h1:+EYjdK8e5RME/VY/qLCAtuyALQ9q67dvuum8i+H5xsI= cloud.google.com/go v0.110.8/go.mod h1:Iz8AkXJf1qmxC3Oxoep8R1T36w8B92yU29PcBhHO5fk= +cloud.google.com/go v0.110.9/go.mod h1:rpxevX/0Lqvlbc88b7Sc1SPNdyK1riNBTUU6JXhYNpM= +cloud.google.com/go v0.110.10/go.mod h1:v1OoFqYxiBkUrruItNM3eT4lLByNjxmJSV/xDKJNnic= cloud.google.com/go/accessapproval v1.4.0/go.mod h1:zybIuC3KpDOvotz59lFe5qxRZx6C75OtwbisN56xYB4= cloud.google.com/go/accessapproval v1.5.0/go.mod h1:HFy3tuiGvMdcd/u+Cu5b9NkO1pEICJ46IR82PoUdplw= cloud.google.com/go/accessapproval v1.6.0/go.mod h1:R0EiYnwV5fsRFiKZkPHr6mwyk2wxUJ30nL4j2pcFY2E= cloud.google.com/go/accessapproval v1.7.1/go.mod h1:JYczztsHRMK7NTXb6Xw+dwbs/WnOJxbo/2mTI+Kgg68= +cloud.google.com/go/accessapproval v1.7.2/go.mod h1:/gShiq9/kK/h8T/eEn1BTzalDvk0mZxJlhfw0p+Xuc0= +cloud.google.com/go/accessapproval v1.7.3/go.mod h1:4l8+pwIxGTNqSf4T3ds8nLO94NQf0W/KnMNuQ9PbnP8= +cloud.google.com/go/accessapproval v1.7.4/go.mod h1:/aTEh45LzplQgFYdQdwPMR9YdX0UlhBmvB84uAmQKUc= cloud.google.com/go/accesscontextmanager v1.3.0/go.mod h1:TgCBehyr5gNMz7ZaH9xubp+CE8dkrszb4oK9CWyvD4o= cloud.google.com/go/accesscontextmanager v1.4.0/go.mod h1:/Kjh7BBu/Gh83sv+K60vN9QE5NJcd80sU33vIe2IFPE= cloud.google.com/go/accesscontextmanager v1.6.0/go.mod h1:8XCvZWfYw3K/ji0iVnp+6pu7huxoQTLmxAbVjbloTtM= cloud.google.com/go/accesscontextmanager v1.7.0/go.mod h1:CEGLewx8dwa33aDAZQujl7Dx+uYhS0eay198wB/VumQ= cloud.google.com/go/accesscontextmanager v1.8.0/go.mod h1:uI+AI/r1oyWK99NN8cQ3UK76AMelMzgZCvJfsi2c+ps= cloud.google.com/go/accesscontextmanager v1.8.1/go.mod h1:JFJHfvuaTC+++1iL1coPiG1eu5D24db2wXCDWDjIrxo= +cloud.google.com/go/accesscontextmanager v1.8.2/go.mod h1:E6/SCRM30elQJ2PKtFMs2YhfJpZSNcJyejhuzoId4Zk= +cloud.google.com/go/accesscontextmanager v1.8.3/go.mod h1:4i/JkF2JiFbhLnnpnfoTX5vRXfhf9ukhU1ANOTALTOQ= +cloud.google.com/go/accesscontextmanager v1.8.4/go.mod h1:ParU+WbMpD34s5JFEnGAnPBYAgUHozaTmDJU7aCU9+M= cloud.google.com/go/aiplatform v1.22.0/go.mod h1:ig5Nct50bZlzV6NvKaTwmplLLddFx0YReh9WfTO5jKw= cloud.google.com/go/aiplatform v1.24.0/go.mod h1:67UUvRBKG6GTayHKV8DBv2RtR1t93YRu5B1P3x99mYY= cloud.google.com/go/aiplatform v1.27.0/go.mod h1:Bvxqtl40l0WImSb04d0hXFU7gDOiq9jQmorivIiWcKg= @@ -60,6 +68,10 @@ cloud.google.com/go/aiplatform v1.37.0/go.mod h1:IU2Cv29Lv9oCn/9LkFiiuKfwrRTq+QQ cloud.google.com/go/aiplatform v1.45.0/go.mod h1:Iu2Q7sC7QGhXUeOhAj/oCK9a+ULz1O4AotZiqjQ8MYA= cloud.google.com/go/aiplatform v1.48.0/go.mod h1:Iu2Q7sC7QGhXUeOhAj/oCK9a+ULz1O4AotZiqjQ8MYA= cloud.google.com/go/aiplatform v1.50.0/go.mod h1:IRc2b8XAMTa9ZmfJV1BCCQbieWWvDnP1A8znyz5N7y4= +cloud.google.com/go/aiplatform v1.51.0/go.mod h1:IRc2b8XAMTa9ZmfJV1BCCQbieWWvDnP1A8znyz5N7y4= +cloud.google.com/go/aiplatform v1.51.1/go.mod h1:kY3nIMAVQOK2XDqDPHaOuD9e+FdMA6OOpfBjsvaFSOo= +cloud.google.com/go/aiplatform v1.51.2/go.mod h1:hCqVYB3mY45w99TmetEoe8eCQEwZEp9WHxeZdcv9phw= +cloud.google.com/go/aiplatform v1.52.0/go.mod h1:pwZMGvqe0JRkI1GWSZCtnAfrR4K1bv65IHILGA//VEU= cloud.google.com/go/analytics v0.11.0/go.mod h1:DjEWCu41bVbYcKyvlws9Er60YE4a//bK6mnhWvQeFNI= cloud.google.com/go/analytics v0.12.0/go.mod h1:gkfj9h6XRf9+TS4bmuhPEShsh3hH8PAZzm/41OOhQd4= cloud.google.com/go/analytics v0.17.0/go.mod h1:WXFa3WSym4IZ+JiKmavYdJwGG/CvpqiqczmL59bTD9M= @@ -67,18 +79,30 @@ cloud.google.com/go/analytics v0.18.0/go.mod h1:ZkeHGQlcIPkw0R/GW+boWHhCOR43xz9R cloud.google.com/go/analytics v0.19.0/go.mod h1:k8liqf5/HCnOUkbawNtrWWc+UAzyDlW89doe8TtoDsE= cloud.google.com/go/analytics v0.21.2/go.mod h1:U8dcUtmDmjrmUTnnnRnI4m6zKn/yaA5N9RlEkYFHpQo= cloud.google.com/go/analytics v0.21.3/go.mod h1:U8dcUtmDmjrmUTnnnRnI4m6zKn/yaA5N9RlEkYFHpQo= +cloud.google.com/go/analytics v0.21.4/go.mod h1:zZgNCxLCy8b2rKKVfC1YkC2vTrpfZmeRCySM3aUbskA= +cloud.google.com/go/analytics v0.21.5/go.mod h1:BQtOBHWTlJ96axpPPnw5CvGJ6i3Ve/qX2fTxR8qWyr8= +cloud.google.com/go/analytics v0.21.6/go.mod h1:eiROFQKosh4hMaNhF85Oc9WO97Cpa7RggD40e/RBy8w= cloud.google.com/go/apigateway v1.3.0/go.mod h1:89Z8Bhpmxu6AmUxuVRg/ECRGReEdiP3vQtk4Z1J9rJk= cloud.google.com/go/apigateway v1.4.0/go.mod h1:pHVY9MKGaH9PQ3pJ4YLzoj6U5FUDeDFBllIz7WmzJoc= cloud.google.com/go/apigateway v1.5.0/go.mod h1:GpnZR3Q4rR7LVu5951qfXPJCHquZt02jf7xQx7kpqN8= cloud.google.com/go/apigateway v1.6.1/go.mod h1:ufAS3wpbRjqfZrzpvLC2oh0MFlpRJm2E/ts25yyqmXA= +cloud.google.com/go/apigateway v1.6.2/go.mod h1:CwMC90nnZElorCW63P2pAYm25AtQrHfuOkbRSHj0bT8= +cloud.google.com/go/apigateway v1.6.3/go.mod h1:k68PXWpEs6BVDTtnLQAyG606Q3mz8pshItwPXjgv44Y= +cloud.google.com/go/apigateway v1.6.4/go.mod h1:0EpJlVGH5HwAN4VF4Iec8TAzGN1aQgbxAWGJsnPCGGY= cloud.google.com/go/apigeeconnect v1.3.0/go.mod h1:G/AwXFAKo0gIXkPTVfZDd2qA1TxBXJ3MgMRBQkIi9jc= cloud.google.com/go/apigeeconnect v1.4.0/go.mod h1:kV4NwOKqjvt2JYR0AoIWo2QGfoRtn/pkS3QlHp0Ni04= cloud.google.com/go/apigeeconnect v1.5.0/go.mod h1:KFaCqvBRU6idyhSNyn3vlHXc8VMDJdRmwDF6JyFRqZ8= cloud.google.com/go/apigeeconnect v1.6.1/go.mod h1:C4awq7x0JpLtrlQCr8AzVIzAaYgngRqWf9S5Uhg+wWs= +cloud.google.com/go/apigeeconnect v1.6.2/go.mod h1:s6O0CgXT9RgAxlq3DLXvG8riw8PYYbU/v25jqP3Dy18= +cloud.google.com/go/apigeeconnect v1.6.3/go.mod h1:peG0HFQ0si2bN15M6QSjEW/W7Gy3NYkWGz7pFz13cbo= +cloud.google.com/go/apigeeconnect v1.6.4/go.mod h1:CapQCWZ8TCjnU0d7PobxhpOdVz/OVJ2Hr/Zcuu1xFx0= cloud.google.com/go/apigeeregistry v0.4.0/go.mod h1:EUG4PGcsZvxOXAdyEghIdXwAEi/4MEaoqLMLDMIwKXY= cloud.google.com/go/apigeeregistry v0.5.0/go.mod h1:YR5+s0BVNZfVOUkMa5pAR2xGd0A473vA5M7j247o1wM= cloud.google.com/go/apigeeregistry v0.6.0/go.mod h1:BFNzW7yQVLZ3yj0TKcwzb8n25CFBri51GVGOEUcgQsc= cloud.google.com/go/apigeeregistry v0.7.1/go.mod h1:1XgyjZye4Mqtw7T9TsY4NW10U7BojBvG4RMD+vRDrIw= +cloud.google.com/go/apigeeregistry v0.7.2/go.mod h1:9CA2B2+TGsPKtfi3F7/1ncCCsL62NXBRfM6iPoGSM+8= +cloud.google.com/go/apigeeregistry v0.8.1/go.mod h1:MW4ig1N4JZQsXmBSwH4rwpgDonocz7FPBSw6XPGHmYw= +cloud.google.com/go/apigeeregistry v0.8.2/go.mod h1:h4v11TDGdeXJDJvImtgK2AFVvMIgGWjSb0HRnBSjcX8= cloud.google.com/go/apikeys v0.4.0/go.mod h1:XATS/yqZbaBK0HOssf+ALHp8jAlNHUgyfprvNcBIszU= cloud.google.com/go/apikeys v0.5.0/go.mod h1:5aQfwY4D+ewMMWScd3hm2en3hCj+BROlyrt3ytS7KLI= cloud.google.com/go/apikeys v0.6.0/go.mod h1:kbpXu5upyiAlGkKrJgQl8A0rKNNJ7dQ377pdroRSSi8= @@ -88,11 +112,17 @@ cloud.google.com/go/appengine v1.6.0/go.mod h1:hg6i0J/BD2cKmDJbaFSYHFyZkgBEfQrDg cloud.google.com/go/appengine v1.7.0/go.mod h1:eZqpbHFCqRGa2aCdope7eC0SWLV1j0neb/QnMJVWx6A= cloud.google.com/go/appengine v1.7.1/go.mod h1:IHLToyb/3fKutRysUlFO0BPt5j7RiQ45nrzEJmKTo6E= cloud.google.com/go/appengine v1.8.1/go.mod h1:6NJXGLVhZCN9aQ/AEDvmfzKEfoYBlfB80/BHiKVputY= +cloud.google.com/go/appengine v1.8.2/go.mod h1:WMeJV9oZ51pvclqFN2PqHoGnys7rK0rz6s3Mp6yMvDo= +cloud.google.com/go/appengine v1.8.3/go.mod h1:2oUPZ1LVZ5EXi+AF1ihNAF+S8JrzQ3till5m9VQkrsk= +cloud.google.com/go/appengine v1.8.4/go.mod h1:TZ24v+wXBujtkK77CXCpjZbnuTvsFNT41MUaZ28D6vg= cloud.google.com/go/area120 v0.5.0/go.mod h1:DE/n4mp+iqVyvxHN41Vf1CR602GiHQjFPusMFW6bGR4= cloud.google.com/go/area120 v0.6.0/go.mod h1:39yFJqWVgm0UZqWTOdqkLhjoC7uFfgXRC8g/ZegeAh0= cloud.google.com/go/area120 v0.7.0/go.mod h1:a3+8EUD1SX5RUcCs3MY5YasiO1z6yLiNLRiFrykbynY= cloud.google.com/go/area120 v0.7.1/go.mod h1:j84i4E1RboTWjKtZVWXPqvK5VHQFJRF2c1Nm69pWm9k= cloud.google.com/go/area120 v0.8.1/go.mod h1:BVfZpGpB7KFVNxPiQBuHkX6Ed0rS51xIgmGyjrAfzsg= +cloud.google.com/go/area120 v0.8.2/go.mod h1:a5qfo+x77SRLXnCynFWPUZhnZGeSgvQ+Y0v1kSItkh4= +cloud.google.com/go/area120 v0.8.3/go.mod h1:5zj6pMzVTH+SVHljdSKC35sriR/CVvQZzG/Icdyriw0= +cloud.google.com/go/area120 v0.8.4/go.mod h1:jfawXjxf29wyBXr48+W+GyX/f8fflxp642D/bb9v68M= cloud.google.com/go/artifactregistry v1.6.0/go.mod h1:IYt0oBPSAGYj/kprzsBjZ/4LnG/zOcHyFHjWPCi6SAQ= cloud.google.com/go/artifactregistry v1.7.0/go.mod h1:mqTOFOnGZx8EtSqK/ZWcsm/4U8B77rbcLP6ruDU2Ixk= cloud.google.com/go/artifactregistry v1.8.0/go.mod h1:w3GQXkJX8hiKN0v+at4b0qotwijQbYUqF2GWkZzAhC0= @@ -102,6 +132,10 @@ cloud.google.com/go/artifactregistry v1.11.2/go.mod h1:nLZns771ZGAwVLzTX/7Al6R9e cloud.google.com/go/artifactregistry v1.12.0/go.mod h1:o6P3MIvtzTOnmvGagO9v/rOjjA0HmhJ+/6KAXrmYDCI= cloud.google.com/go/artifactregistry v1.13.0/go.mod h1:uy/LNfoOIivepGhooAUpL1i30Hgee3Cu0l4VTWHUC08= cloud.google.com/go/artifactregistry v1.14.1/go.mod h1:nxVdG19jTaSTu7yA7+VbWL346r3rIdkZ142BSQqhn5E= +cloud.google.com/go/artifactregistry v1.14.2/go.mod h1:Xk+QbsKEb0ElmyeMfdHAey41B+qBq3q5R5f5xD4XT3U= +cloud.google.com/go/artifactregistry v1.14.3/go.mod h1:A2/E9GXnsyXl7GUvQ/2CjHA+mVRoWAXC0brg2os+kNI= +cloud.google.com/go/artifactregistry v1.14.4/go.mod h1:SJJcZTMv6ce0LDMUnihCN7WSrI+kBSFV0KIKo8S8aYU= +cloud.google.com/go/artifactregistry v1.14.6/go.mod h1:np9LSFotNWHcjnOgh8UVK0RFPCTUGbO0ve3384xyHfE= cloud.google.com/go/asset v1.5.0/go.mod h1:5mfs8UvcM5wHhqtSv8J1CtxxaQq3AdBxxQi2jGW/K4o= cloud.google.com/go/asset v1.7.0/go.mod h1:YbENsRK4+xTiL+Ofoj5Ckf+O17kJtgp3Y3nn4uzZz5s= cloud.google.com/go/asset v1.8.0/go.mod h1:mUNGKhiqIdbr8X7KNayoYvyc4HbbFO9URsjbytpUaW0= @@ -111,6 +145,10 @@ cloud.google.com/go/asset v1.11.1/go.mod h1:fSwLhbRvC9p9CXQHJ3BgFeQNM4c9x10lqlrd cloud.google.com/go/asset v1.12.0/go.mod h1:h9/sFOa4eDIyKmH6QMpm4eUK3pDojWnUhTgJlk762Hg= cloud.google.com/go/asset v1.13.0/go.mod h1:WQAMyYek/b7NBpYq/K4KJWcRqzoalEsxz/t/dTk4THw= cloud.google.com/go/asset v1.14.1/go.mod h1:4bEJ3dnHCqWCDbWJ/6Vn7GVI9LerSi7Rfdi03hd+WTQ= +cloud.google.com/go/asset v1.15.0/go.mod h1:tpKafV6mEut3+vN9ScGvCHXHj7FALFVta+okxFECHcg= +cloud.google.com/go/asset v1.15.1/go.mod h1:yX/amTvFWRpp5rcFq6XbCxzKT8RJUam1UoboE179jU4= +cloud.google.com/go/asset v1.15.2/go.mod h1:B6H5tclkXvXz7PD22qCA2TDxSVQfasa3iDlM89O2NXs= +cloud.google.com/go/asset v1.15.3/go.mod h1:yYLfUD4wL4X589A9tYrv4rFrba0QlDeag0CMcM5ggXU= cloud.google.com/go/assuredworkloads v1.5.0/go.mod h1:n8HOZ6pff6re5KYfBXcFvSViQjDwxFkAkmUFffJRbbY= cloud.google.com/go/assuredworkloads v1.6.0/go.mod h1:yo2YOk37Yc89Rsd5QMVECvjaMKymF9OP+QXWlKXUkXw= cloud.google.com/go/assuredworkloads v1.7.0/go.mod h1:z/736/oNmtGAyU47reJgGN+KVoYoxeLBoj4XkKYscNI= @@ -118,28 +156,44 @@ cloud.google.com/go/assuredworkloads v1.8.0/go.mod h1:AsX2cqyNCOvEQC8RMPnoc0yEar cloud.google.com/go/assuredworkloads v1.9.0/go.mod h1:kFuI1P78bplYtT77Tb1hi0FMxM0vVpRC7VVoJC3ZoT0= cloud.google.com/go/assuredworkloads v1.10.0/go.mod h1:kwdUQuXcedVdsIaKgKTp9t0UJkE5+PAVNhdQm4ZVq2E= cloud.google.com/go/assuredworkloads v1.11.1/go.mod h1:+F04I52Pgn5nmPG36CWFtxmav6+7Q+c5QyJoL18Lry0= +cloud.google.com/go/assuredworkloads v1.11.2/go.mod h1:O1dfr+oZJMlE6mw0Bp0P1KZSlj5SghMBvTpZqIcUAW4= +cloud.google.com/go/assuredworkloads v1.11.3/go.mod h1:vEjfTKYyRUaIeA0bsGJceFV2JKpVRgyG2op3jfa59Zs= +cloud.google.com/go/assuredworkloads v1.11.4/go.mod h1:4pwwGNwy1RP0m+y12ef3Q/8PaiWrIDQ6nD2E8kvWI9U= cloud.google.com/go/automl v1.5.0/go.mod h1:34EjfoFGMZ5sgJ9EoLsRtdPSNZLcfflJR39VbVNS2M0= cloud.google.com/go/automl v1.6.0/go.mod h1:ugf8a6Fx+zP0D59WLhqgTDsQI9w07o64uf/Is3Nh5p8= cloud.google.com/go/automl v1.7.0/go.mod h1:RL9MYCCsJEOmt0Wf3z9uzG0a7adTT1fe+aObgSpkCt8= cloud.google.com/go/automl v1.8.0/go.mod h1:xWx7G/aPEe/NP+qzYXktoBSDfjO+vnKMGgsApGJJquM= cloud.google.com/go/automl v1.12.0/go.mod h1:tWDcHDp86aMIuHmyvjuKeeHEGq76lD7ZqfGLN6B0NuU= cloud.google.com/go/automl v1.13.1/go.mod h1:1aowgAHWYZU27MybSCFiukPO7xnyawv7pt3zK4bheQE= +cloud.google.com/go/automl v1.13.2/go.mod h1:gNY/fUmDEN40sP8amAX3MaXkxcqPIn7F1UIIPZpy4Mg= +cloud.google.com/go/automl v1.13.3/go.mod h1:Y8KwvyAZFOsMAPqUCfNu1AyclbC6ivCUF/MTwORymyY= +cloud.google.com/go/automl v1.13.4/go.mod h1:ULqwX/OLZ4hBVfKQaMtxMSTlPx0GqGbWN8uA/1EqCP8= cloud.google.com/go/baremetalsolution v0.3.0/go.mod h1:XOrocE+pvK1xFfleEnShBlNAXf+j5blPPxrhjKgnIFc= cloud.google.com/go/baremetalsolution v0.4.0/go.mod h1:BymplhAadOO/eBa7KewQ0Ppg4A4Wplbn+PsFKRLo0uI= cloud.google.com/go/baremetalsolution v0.5.0/go.mod h1:dXGxEkmR9BMwxhzBhV0AioD0ULBmuLZI8CdwalUxuss= cloud.google.com/go/baremetalsolution v1.1.1/go.mod h1:D1AV6xwOksJMV4OSlWHtWuFNZZYujJknMAP4Qa27QIA= cloud.google.com/go/baremetalsolution v1.2.0/go.mod h1:68wi9AwPYkEWIUT4SvSGS9UJwKzNpshjHsH4lzk8iOw= +cloud.google.com/go/baremetalsolution v1.2.1/go.mod h1:3qKpKIw12RPXStwQXcbhfxVj1dqQGEvcmA+SX/mUR88= +cloud.google.com/go/baremetalsolution v1.2.2/go.mod h1:O5V6Uu1vzVelYahKfwEWRMaS3AbCkeYHy3145s1FkhM= +cloud.google.com/go/baremetalsolution v1.2.3/go.mod h1:/UAQ5xG3faDdy180rCUv47e0jvpp3BFxT+Cl0PFjw5g= cloud.google.com/go/batch v0.3.0/go.mod h1:TR18ZoAekj1GuirsUsR1ZTKN3FC/4UDnScjT8NXImFE= cloud.google.com/go/batch v0.4.0/go.mod h1:WZkHnP43R/QCGQsZ+0JyG4i79ranE2u8xvjq/9+STPE= cloud.google.com/go/batch v0.7.0/go.mod h1:vLZN95s6teRUqRQ4s3RLDsH8PvboqBK+rn1oevL159g= cloud.google.com/go/batch v1.3.1/go.mod h1:VguXeQKXIYaeeIYbuozUmBR13AfL4SJP7IltNPS+A4A= cloud.google.com/go/batch v1.4.1/go.mod h1:KdBmDD61K0ovcxoRHGrN6GmOBWeAOyCgKD0Mugx4Fkk= +cloud.google.com/go/batch v1.5.0/go.mod h1:KdBmDD61K0ovcxoRHGrN6GmOBWeAOyCgKD0Mugx4Fkk= +cloud.google.com/go/batch v1.5.1/go.mod h1:RpBuIYLkQu8+CWDk3dFD/t/jOCGuUpkpX+Y0n1Xccs8= +cloud.google.com/go/batch v1.6.1/go.mod h1:urdpD13zPe6YOK+6iZs/8/x2VBRofvblLpx0t57vM98= +cloud.google.com/go/batch v1.6.3/go.mod h1:J64gD4vsNSA2O5TtDB5AAux3nJ9iV8U3ilg3JDBYejU= cloud.google.com/go/beyondcorp v0.2.0/go.mod h1:TB7Bd+EEtcw9PCPQhCJtJGjk/7TC6ckmnSFS+xwTfm4= cloud.google.com/go/beyondcorp v0.3.0/go.mod h1:E5U5lcrcXMsCuoDNyGrpyTm/hn7ne941Jz2vmksAxW8= cloud.google.com/go/beyondcorp v0.4.0/go.mod h1:3ApA0mbhHx6YImmuubf5pyW8srKnCEPON32/5hj+RmM= cloud.google.com/go/beyondcorp v0.5.0/go.mod h1:uFqj9X+dSfrheVp7ssLTaRHd2EHqSL4QZmH4e8WXGGU= cloud.google.com/go/beyondcorp v0.6.1/go.mod h1:YhxDWw946SCbmcWo3fAhw3V4XZMSpQ/VYfcKGAEU8/4= cloud.google.com/go/beyondcorp v1.0.0/go.mod h1:YhxDWw946SCbmcWo3fAhw3V4XZMSpQ/VYfcKGAEU8/4= +cloud.google.com/go/beyondcorp v1.0.1/go.mod h1:zl/rWWAFVeV+kx+X2Javly7o1EIQThU4WlkynffL/lk= +cloud.google.com/go/beyondcorp v1.0.2/go.mod h1:m8cpG7caD+5su+1eZr+TSvF6r21NdLJk4f9u4SP2Ntc= +cloud.google.com/go/beyondcorp v1.0.3/go.mod h1:HcBvnEd7eYr+HGDd5ZbuVmBYX019C6CEXBonXbCVwJo= cloud.google.com/go/bigquery v1.0.1/go.mod h1:i/xbL2UlR5RvWAURpBYZTtm/cXjCha9lbfbpx4poX+o= cloud.google.com/go/bigquery v1.3.0/go.mod h1:PjpwJnslEMmckchkHFfq+HTD2DmtT67aNFKH1/VBDHE= cloud.google.com/go/bigquery v1.4.0/go.mod h1:S8dzgnTigyfTmLBfrtrhyYhwRxG72rYxvftPBK2Dvzc= @@ -156,6 +210,8 @@ cloud.google.com/go/bigquery v1.50.0/go.mod h1:YrleYEh2pSEbgTBZYMJ5SuSr0ML3ypjRB cloud.google.com/go/bigquery v1.52.0/go.mod h1:3b/iXjRQGU4nKa87cXeg6/gogLjO8C6PmuM8i5Bi/u4= cloud.google.com/go/bigquery v1.53.0/go.mod h1:3b/iXjRQGU4nKa87cXeg6/gogLjO8C6PmuM8i5Bi/u4= cloud.google.com/go/bigquery v1.55.0/go.mod h1:9Y5I3PN9kQWuid6183JFhOGOW3GcirA5LpsKCUn+2ec= +cloud.google.com/go/bigquery v1.56.0/go.mod h1:KDcsploXTEY7XT3fDQzMUZlpQLHzE4itubHrnmhUrZA= +cloud.google.com/go/bigquery v1.57.1/go.mod h1:iYzC0tGVWt1jqSzBHqCr3lrRn0u13E8e+AqowBsDgug= cloud.google.com/go/billing v1.4.0/go.mod h1:g9IdKBEFlItS8bTtlrZdVLWSSdSyFUZKXNS02zKMOZY= cloud.google.com/go/billing v1.5.0/go.mod h1:mztb1tBc3QekhjSgmpf/CV4LzWXLzCArwpLmP2Gm88s= cloud.google.com/go/billing v1.6.0/go.mod h1:WoXzguj+BeHXPbKfNWkqVtDdzORazmCjraY+vrxcyvI= @@ -164,6 +220,10 @@ cloud.google.com/go/billing v1.12.0/go.mod h1:yKrZio/eu+okO/2McZEbch17O5CB5NpZhh cloud.google.com/go/billing v1.13.0/go.mod h1:7kB2W9Xf98hP9Sr12KfECgfGclsH3CQR0R08tnRlRbc= cloud.google.com/go/billing v1.16.0/go.mod h1:y8vx09JSSJG02k5QxbycNRrN7FGZB6F3CAcgum7jvGA= cloud.google.com/go/billing v1.17.0/go.mod h1:Z9+vZXEq+HwH7bhJkyI4OQcR6TSbeMrjlpEjO2vzY64= +cloud.google.com/go/billing v1.17.1/go.mod h1:Z9+vZXEq+HwH7bhJkyI4OQcR6TSbeMrjlpEjO2vzY64= +cloud.google.com/go/billing v1.17.2/go.mod h1:u/AdV/3wr3xoRBk5xvUzYMS1IawOAPwQMuHgHMdljDg= +cloud.google.com/go/billing v1.17.3/go.mod h1:z83AkoZ7mZwBGT3yTnt6rSGI1OOsHSIi6a5M3mJ8NaU= +cloud.google.com/go/billing v1.17.4/go.mod h1:5DOYQStCxquGprqfuid/7haD7th74kyMBHkjO/OvDtk= cloud.google.com/go/binaryauthorization v1.1.0/go.mod h1:xwnoWu3Y84jbuHa0zd526MJYmtnVXn0syOjaJgy4+dM= cloud.google.com/go/binaryauthorization v1.2.0/go.mod h1:86WKkJHtRcv5ViNABtYMhhNWRrD1Vpi//uKEy7aYEfI= cloud.google.com/go/binaryauthorization v1.3.0/go.mod h1:lRZbKgjDIIQvzYQS1p99A7/U1JqvqeZg0wiI5tp6tg0= @@ -171,16 +231,25 @@ cloud.google.com/go/binaryauthorization v1.4.0/go.mod h1:tsSPQrBd77VLplV70GUhBf/ cloud.google.com/go/binaryauthorization v1.5.0/go.mod h1:OSe4OU1nN/VswXKRBmciKpo9LulY41gch5c68htf3/Q= cloud.google.com/go/binaryauthorization v1.6.1/go.mod h1:TKt4pa8xhowwffiBmbrbcxijJRZED4zrqnwZ1lKH51U= cloud.google.com/go/binaryauthorization v1.7.0/go.mod h1:Zn+S6QqTMn6odcMU1zDZCJxPjU2tZPV1oDl45lWY154= +cloud.google.com/go/binaryauthorization v1.7.1/go.mod h1:GTAyfRWYgcbsP3NJogpV3yeunbUIjx2T9xVeYovtURE= +cloud.google.com/go/binaryauthorization v1.7.2/go.mod h1:kFK5fQtxEp97m92ziy+hbu+uKocka1qRRL8MVJIgjv0= +cloud.google.com/go/binaryauthorization v1.7.3/go.mod h1:VQ/nUGRKhrStlGr+8GMS8f6/vznYLkdK5vaKfdCIpvU= cloud.google.com/go/certificatemanager v1.3.0/go.mod h1:n6twGDvcUBFu9uBgt4eYvvf3sQ6My8jADcOVwHmzadg= cloud.google.com/go/certificatemanager v1.4.0/go.mod h1:vowpercVFyqs8ABSmrdV+GiFf2H/ch3KyudYQEMM590= cloud.google.com/go/certificatemanager v1.6.0/go.mod h1:3Hh64rCKjRAX8dXgRAyOcY5vQ/fE1sh8o+Mdd6KPgY8= cloud.google.com/go/certificatemanager v1.7.1/go.mod h1:iW8J3nG6SaRYImIa+wXQ0g8IgoofDFRp5UMzaNk1UqI= +cloud.google.com/go/certificatemanager v1.7.2/go.mod h1:15SYTDQMd00kdoW0+XY5d9e+JbOPjp24AvF48D8BbcQ= +cloud.google.com/go/certificatemanager v1.7.3/go.mod h1:T/sZYuC30PTag0TLo28VedIRIj1KPGcOQzjWAptHa00= +cloud.google.com/go/certificatemanager v1.7.4/go.mod h1:FHAylPe/6IIKuaRmHbjbdLhGhVQ+CWHSD5Jq0k4+cCE= cloud.google.com/go/channel v1.8.0/go.mod h1:W5SwCXDJsq/rg3tn3oG0LOxpAo6IMxNa09ngphpSlnk= cloud.google.com/go/channel v1.9.0/go.mod h1:jcu05W0my9Vx4mt3/rEHpfxc9eKi9XwsdDL8yBMbKUk= cloud.google.com/go/channel v1.11.0/go.mod h1:IdtI0uWGqhEeatSB62VOoJ8FSUhJ9/+iGkJVqp74CGE= cloud.google.com/go/channel v1.12.0/go.mod h1:VkxCGKASi4Cq7TbXxlaBezonAYpp1GCnKMY6tnMQnLU= cloud.google.com/go/channel v1.16.0/go.mod h1:eN/q1PFSl5gyu0dYdmxNXscY/4Fi7ABmeHCJNf/oHmc= cloud.google.com/go/channel v1.17.0/go.mod h1:RpbhJsGi/lXWAUM1eF4IbQGbsfVlg2o8Iiy2/YLfVT0= +cloud.google.com/go/channel v1.17.1/go.mod h1:xqfzcOZAcP4b/hUDH0GkGg1Sd5to6di1HOJn/pi5uBQ= +cloud.google.com/go/channel v1.17.2/go.mod h1:aT2LhnftnyfQceFql5I/mP8mIbiiJS4lWqgXA815zMk= +cloud.google.com/go/channel v1.17.3/go.mod h1:QcEBuZLGGrUMm7kNj9IbU1ZfmJq2apotsV83hbxX7eE= cloud.google.com/go/cloudbuild v1.3.0/go.mod h1:WequR4ULxlqvMsjDEEEFnOG5ZSRSgWOywXYDb1vPE6U= cloud.google.com/go/cloudbuild v1.4.0/go.mod h1:5Qwa40LHiOXmz3386FrjrYM93rM/hdRr7b53sySrTqA= cloud.google.com/go/cloudbuild v1.6.0/go.mod h1:UIbc/w9QCbH12xX+ezUsgblrWv+Cv4Tw83GiSMHOn9M= @@ -189,11 +258,17 @@ cloud.google.com/go/cloudbuild v1.9.0/go.mod h1:qK1d7s4QlO0VwfYn5YuClDGg2hfmLZEb cloud.google.com/go/cloudbuild v1.10.1/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= cloud.google.com/go/cloudbuild v1.13.0/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= cloud.google.com/go/cloudbuild v1.14.0/go.mod h1:lyJg7v97SUIPq4RC2sGsz/9tNczhyv2AjML/ci4ulzU= +cloud.google.com/go/cloudbuild v1.14.1/go.mod h1:K7wGc/3zfvmYWOWwYTgF/d/UVJhS4pu+HAy7PL7mCsU= +cloud.google.com/go/cloudbuild v1.14.2/go.mod h1:Bn6RO0mBYk8Vlrt+8NLrru7WXlQ9/RDWz2uo5KG1/sg= +cloud.google.com/go/cloudbuild v1.14.3/go.mod h1:eIXYWmRt3UtggLnFGx4JvXcMj4kShhVzGndL1LwleEM= cloud.google.com/go/clouddms v1.3.0/go.mod h1:oK6XsCDdW4Ib3jCCBugx+gVjevp2TMXFtgxvPSee3OM= cloud.google.com/go/clouddms v1.4.0/go.mod h1:Eh7sUGCC+aKry14O1NRljhjyrr0NFC0G2cjwX0cByRk= cloud.google.com/go/clouddms v1.5.0/go.mod h1:QSxQnhikCLUw13iAbffF2CZxAER3xDGNHjsTAkQJcQA= cloud.google.com/go/clouddms v1.6.1/go.mod h1:Ygo1vL52Ov4TBZQquhz5fiw2CQ58gvu+PlS6PVXCpZI= cloud.google.com/go/clouddms v1.7.0/go.mod h1:MW1dC6SOtI/tPNCciTsXtsGNEM0i0OccykPvv3hiYeM= +cloud.google.com/go/clouddms v1.7.1/go.mod h1:o4SR8U95+P7gZ/TX+YbJxehOCsM+fe6/brlrFquiszk= +cloud.google.com/go/clouddms v1.7.2/go.mod h1:Rk32TmWmHo64XqDvW7jgkFQet1tUKNVzs7oajtJT3jU= +cloud.google.com/go/clouddms v1.7.3/go.mod h1:fkN2HQQNUYInAU3NQ3vRLkV2iWs8lIdmBKOx4nrL6Hc= cloud.google.com/go/cloudtasks v1.5.0/go.mod h1:fD92REy1x5woxkKEkLdvavGnPJGEn8Uic9nWuLzqCpY= cloud.google.com/go/cloudtasks v1.6.0/go.mod h1:C6Io+sxuke9/KNRkbQpihnW93SWDU3uXt92nu85HkYI= cloud.google.com/go/cloudtasks v1.7.0/go.mod h1:ImsfdYWwlWNJbdgPIIGJWC+gemEGTBK/SunNQQNCAb4= @@ -202,6 +277,9 @@ cloud.google.com/go/cloudtasks v1.9.0/go.mod h1:w+EyLsVkLWHcOaqNEyvcKAsWp9p29dL6 cloud.google.com/go/cloudtasks v1.10.0/go.mod h1:NDSoTLkZ3+vExFEWu2UJV1arUyzVDAiZtdWcsUyNwBs= cloud.google.com/go/cloudtasks v1.11.1/go.mod h1:a9udmnou9KO2iulGscKR0qBYjreuX8oHwpmFsKspEvM= cloud.google.com/go/cloudtasks v1.12.1/go.mod h1:a9udmnou9KO2iulGscKR0qBYjreuX8oHwpmFsKspEvM= +cloud.google.com/go/cloudtasks v1.12.2/go.mod h1:A7nYkjNlW2gUoROg1kvJrQGhJP/38UaWwsnuBDOBVUk= +cloud.google.com/go/cloudtasks v1.12.3/go.mod h1:GPVXhIOSGEaR+3xT4Fp72ScI+HjHffSS4B8+BaBB5Ys= +cloud.google.com/go/cloudtasks v1.12.4/go.mod h1:BEPu0Gtt2dU6FxZHNqqNdGqIG86qyWKBPGnsb7udGY0= cloud.google.com/go/compute v0.1.0/go.mod h1:GAesmwr110a34z04OlxYkATPBEfVhkymfTBXtfbBFow= cloud.google.com/go/compute v1.3.0/go.mod h1:cCZiE1NHEtai4wiufUhW8I8S1JKkAnhnQJWM7YD99wM= cloud.google.com/go/compute v1.5.0/go.mod h1:9SMHyhJlzhlkJqrPAc839t2BZFTSk6Jdj6mkzQJeu0M= @@ -221,6 +299,9 @@ cloud.google.com/go/compute v1.19.3/go.mod h1:qxvISKp/gYnXkSAD1ppcSOveRAmzxicEv/ cloud.google.com/go/compute v1.20.1/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= cloud.google.com/go/compute v1.21.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= cloud.google.com/go/compute v1.23.0/go.mod h1:4tCnrn48xsqlwSAiLf1HXMQk8CONslYbdiEZc9FEIbM= +cloud.google.com/go/compute v1.23.1/go.mod h1:CqB3xpmPKKt3OJpW2ndFIXnA9A4xAy/F3Xp1ixncW78= +cloud.google.com/go/compute v1.23.2/go.mod h1:JJ0atRC0J/oWYiiVBmsSsrRnh92DhZPG4hFDcR04Rns= +cloud.google.com/go/compute v1.23.3/go.mod h1:VCgBUoMnIVIR0CscqQiPJLAG25E3ZRZMzcFZeQ+h8CI= cloud.google.com/go/compute/metadata v0.1.0/go.mod h1:Z1VN+bulIf6bt4P/C37K4DyZYZEXYonfTBHHFPO/4UU= cloud.google.com/go/compute/metadata v0.2.0/go.mod h1:zFmK7XCadkQkj6TtorcaGlCW1hT1fIilQDwofLpJ20k= cloud.google.com/go/compute/metadata v0.2.1/go.mod h1:jgHgmJd2RKBGzXqF5LR2EZMGxBkeanZ9wwa75XHJgOM= @@ -230,6 +311,10 @@ cloud.google.com/go/contactcenterinsights v1.4.0/go.mod h1:L2YzkGbPsv+vMQMCADxJo cloud.google.com/go/contactcenterinsights v1.6.0/go.mod h1:IIDlT6CLcDoyv79kDv8iWxMSTZhLxSCofVV5W6YFM/w= cloud.google.com/go/contactcenterinsights v1.9.1/go.mod h1:bsg/R7zGLYMVxFFzfh9ooLTruLRCG9fnzhH9KznHhbM= cloud.google.com/go/contactcenterinsights v1.10.0/go.mod h1:bsg/R7zGLYMVxFFzfh9ooLTruLRCG9fnzhH9KznHhbM= +cloud.google.com/go/contactcenterinsights v1.11.0/go.mod h1:hutBdImE4XNZ1NV4vbPJKSFOnQruhC5Lj9bZqWMTKiU= +cloud.google.com/go/contactcenterinsights v1.11.1/go.mod h1:FeNP3Kg8iteKM80lMwSk3zZZKVxr+PGnAId6soKuXwE= +cloud.google.com/go/contactcenterinsights v1.11.2/go.mod h1:A9PIR5ov5cRcd28KlDbmmXE8Aay+Gccer2h4wzkYFso= +cloud.google.com/go/contactcenterinsights v1.11.3/go.mod h1:HHX5wrz5LHVAwfI2smIotQG9x8Qd6gYilaHcLLLmNis= cloud.google.com/go/container v1.6.0/go.mod h1:Xazp7GjJSeUYo688S+6J5V+n/t+G5sKBTFkKNudGRxg= cloud.google.com/go/container v1.7.0/go.mod h1:Dp5AHtmothHGX3DwwIHPgq45Y8KmNsgN3amoYfxVkLo= cloud.google.com/go/container v1.13.1/go.mod h1:6wgbMPeQRw9rSnKBCAJXnds3Pzj03C4JHamr8asWKy4= @@ -238,12 +323,18 @@ cloud.google.com/go/container v1.15.0/go.mod h1:ft+9S0WGjAyjDggg5S06DXj+fHJICWg8 cloud.google.com/go/container v1.22.1/go.mod h1:lTNExE2R7f+DLbAN+rJiKTisauFCaoDq6NURZ83eVH4= cloud.google.com/go/container v1.24.0/go.mod h1:lTNExE2R7f+DLbAN+rJiKTisauFCaoDq6NURZ83eVH4= cloud.google.com/go/container v1.26.0/go.mod h1:YJCmRet6+6jnYYRS000T6k0D0xUXQgBSaJ7VwI8FBj4= +cloud.google.com/go/container v1.26.1/go.mod h1:5smONjPRUxeEpDG7bMKWfDL4sauswqEtnBK1/KKpR04= +cloud.google.com/go/container v1.26.2/go.mod h1:YlO84xCt5xupVbLaMY4s3XNE79MUJ+49VmkInr6HvF4= +cloud.google.com/go/container v1.27.1/go.mod h1:b1A1gJeTBXVLQ6GGw9/9M4FG94BEGsqJ5+t4d/3N7O4= cloud.google.com/go/containeranalysis v0.5.1/go.mod h1:1D92jd8gRR/c0fGMlymRgxWD3Qw9C1ff6/T7mLgVL8I= cloud.google.com/go/containeranalysis v0.6.0/go.mod h1:HEJoiEIu+lEXM+k7+qLCci0h33lX3ZqoYFdmPcoO7s4= cloud.google.com/go/containeranalysis v0.7.0/go.mod h1:9aUL+/vZ55P2CXfuZjS4UjQ9AgXoSw8Ts6lemfmxBxI= cloud.google.com/go/containeranalysis v0.9.0/go.mod h1:orbOANbwk5Ejoom+s+DUCTTJ7IBdBQJDcSylAx/on9s= cloud.google.com/go/containeranalysis v0.10.1/go.mod h1:Ya2jiILITMY68ZLPaogjmOMNkwsDrWBSTyBubGXO7j0= cloud.google.com/go/containeranalysis v0.11.0/go.mod h1:4n2e99ZwpGxpNcz+YsFT1dfOHPQFGcAC8FN2M2/ne/U= +cloud.google.com/go/containeranalysis v0.11.1/go.mod h1:rYlUOM7nem1OJMKwE1SadufX0JP3wnXj844EtZAwWLY= +cloud.google.com/go/containeranalysis v0.11.2/go.mod h1:xibioGBC1MD2j4reTyV1xY1/MvKaz+fyM9ENWhmIeP8= +cloud.google.com/go/containeranalysis v0.11.3/go.mod h1:kMeST7yWFQMGjiG9K7Eov+fPNQcGhb8mXj/UcTiWw9U= cloud.google.com/go/datacatalog v1.3.0/go.mod h1:g9svFY6tuR+j+hrTw3J2dNcmI0dzmSiyOzm8kpLq0a0= cloud.google.com/go/datacatalog v1.5.0/go.mod h1:M7GPLNQeLfWqeIm3iuiruhPzkt65+Bx8dAKvScX8jvs= cloud.google.com/go/datacatalog v1.6.0/go.mod h1:+aEyF8JKg+uXcIdAmmaMUmZ3q1b/lKLtXCmXdnc0lbc= @@ -256,24 +347,40 @@ cloud.google.com/go/datacatalog v1.14.0/go.mod h1:h0PrGtlihoutNMp/uvwhawLQ9+c63K cloud.google.com/go/datacatalog v1.14.1/go.mod h1:d2CevwTG4yedZilwe+v3E3ZBDRMobQfSG/a6cCCN5R4= cloud.google.com/go/datacatalog v1.16.0/go.mod h1:d2CevwTG4yedZilwe+v3E3ZBDRMobQfSG/a6cCCN5R4= cloud.google.com/go/datacatalog v1.17.1/go.mod h1:nCSYFHgtxh2MiEktWIz71s/X+7ds/UT9kp0PC7waCzE= +cloud.google.com/go/datacatalog v1.18.0/go.mod h1:nCSYFHgtxh2MiEktWIz71s/X+7ds/UT9kp0PC7waCzE= +cloud.google.com/go/datacatalog v1.18.1/go.mod h1:TzAWaz+ON1tkNr4MOcak8EBHX7wIRX/gZKM+yTVsv+A= +cloud.google.com/go/datacatalog v1.18.2/go.mod h1:SPVgWW2WEMuWHA+fHodYjmxPiMqcOiWfhc9OD5msigk= +cloud.google.com/go/datacatalog v1.18.3/go.mod h1:5FR6ZIF8RZrtml0VUao22FxhdjkoG+a0866rEnObryM= cloud.google.com/go/dataflow v0.6.0/go.mod h1:9QwV89cGoxjjSR9/r7eFDqqjtvbKxAK2BaYU6PVk9UM= cloud.google.com/go/dataflow v0.7.0/go.mod h1:PX526vb4ijFMesO1o202EaUmouZKBpjHsTlCtB4parQ= cloud.google.com/go/dataflow v0.8.0/go.mod h1:Rcf5YgTKPtQyYz8bLYhFoIV/vP39eL7fWNcSOyFfLJE= cloud.google.com/go/dataflow v0.9.1/go.mod h1:Wp7s32QjYuQDWqJPFFlnBKhkAtiFpMTdg00qGbnIHVw= +cloud.google.com/go/dataflow v0.9.2/go.mod h1:vBfdBZ/ejlTaYIGB3zB4T08UshH70vbtZeMD+urnUSo= +cloud.google.com/go/dataflow v0.9.3/go.mod h1:HI4kMVjcHGTs3jTHW/kv3501YW+eloiJSLxkJa/vqFE= +cloud.google.com/go/dataflow v0.9.4/go.mod h1:4G8vAkHYCSzU8b/kmsoR2lWyHJD85oMJPHMtan40K8w= cloud.google.com/go/dataform v0.3.0/go.mod h1:cj8uNliRlHpa6L3yVhDOBrUXH+BPAO1+KFMQQNSThKo= cloud.google.com/go/dataform v0.4.0/go.mod h1:fwV6Y4Ty2yIFL89huYlEkwUPtS7YZinZbzzj5S9FzCE= cloud.google.com/go/dataform v0.5.0/go.mod h1:GFUYRe8IBa2hcomWplodVmUx/iTL0FrsauObOM3Ipr0= cloud.google.com/go/dataform v0.6.0/go.mod h1:QPflImQy33e29VuapFdf19oPbE4aYTJxr31OAPV+ulA= cloud.google.com/go/dataform v0.7.0/go.mod h1:7NulqnVozfHvWUBpMDfKMUESr+85aJsC/2O0o3jWPDE= cloud.google.com/go/dataform v0.8.1/go.mod h1:3BhPSiw8xmppbgzeBbmDvmSWlwouuJkXsXsb8UBih9M= +cloud.google.com/go/dataform v0.8.2/go.mod h1:X9RIqDs6NbGPLR80tnYoPNiO1w0wenKTb8PxxlhTMKM= +cloud.google.com/go/dataform v0.8.3/go.mod h1:8nI/tvv5Fso0drO3pEjtowz58lodx8MVkdV2q0aPlqg= +cloud.google.com/go/dataform v0.9.1/go.mod h1:pWTg+zGQ7i16pyn0bS1ruqIE91SdL2FDMvEYu/8oQxs= cloud.google.com/go/datafusion v1.4.0/go.mod h1:1Zb6VN+W6ALo85cXnM1IKiPw+yQMKMhB9TsTSRDo/38= cloud.google.com/go/datafusion v1.5.0/go.mod h1:Kz+l1FGHB0J+4XF2fud96WMmRiq/wj8N9u007vyXZ2w= cloud.google.com/go/datafusion v1.6.0/go.mod h1:WBsMF8F1RhSXvVM8rCV3AeyWVxcC2xY6vith3iw3S+8= cloud.google.com/go/datafusion v1.7.1/go.mod h1:KpoTBbFmoToDExJUso/fcCiguGDk7MEzOWXUsJo0wsI= +cloud.google.com/go/datafusion v1.7.2/go.mod h1:62K2NEC6DRlpNmI43WHMWf9Vg/YvN6QVi8EVwifElI0= +cloud.google.com/go/datafusion v1.7.3/go.mod h1:eoLt1uFXKGBq48jy9LZ+Is8EAVLnmn50lNncLzwYokE= +cloud.google.com/go/datafusion v1.7.4/go.mod h1:BBs78WTOLYkT4GVZIXQCZT3GFpkpDN4aBY4NDX/jVlM= cloud.google.com/go/datalabeling v0.5.0/go.mod h1:TGcJ0G2NzcsXSE/97yWjIZO0bXj0KbVlINXMG9ud42I= cloud.google.com/go/datalabeling v0.6.0/go.mod h1:WqdISuk/+WIGeMkpw/1q7bK/tFEZxsrFJOJdY2bXvTQ= cloud.google.com/go/datalabeling v0.7.0/go.mod h1:WPQb1y08RJbmpM3ww0CSUAGweL0SxByuW2E+FU+wXcM= cloud.google.com/go/datalabeling v0.8.1/go.mod h1:XS62LBSVPbYR54GfYQsPXZjTW8UxCK2fkDciSrpRFdY= +cloud.google.com/go/datalabeling v0.8.2/go.mod h1:cyDvGHuJWu9U/cLDA7d8sb9a0tWLEletStu2sTmg3BE= +cloud.google.com/go/datalabeling v0.8.3/go.mod h1:tvPhpGyS/V7lqjmb3V0TaDdGvhzgR1JoW7G2bpi2UTI= +cloud.google.com/go/datalabeling v0.8.4/go.mod h1:Z1z3E6LHtffBGrNUkKwbwbDxTiXEApLzIgmymj8A3S8= cloud.google.com/go/dataplex v1.3.0/go.mod h1:hQuRtDg+fCiFgC8j0zV222HvzFQdRd+SVX8gdmFcZzA= cloud.google.com/go/dataplex v1.4.0/go.mod h1:X51GfLXEMVJ6UN47ESVqvlsRplbLhcsAt0kZCCKsU0A= cloud.google.com/go/dataplex v1.5.2/go.mod h1:cVMgQHsmfRoI5KFYq4JtIBEUbYwc3c7tXmIDhRmNNVQ= @@ -281,15 +388,24 @@ cloud.google.com/go/dataplex v1.6.0/go.mod h1:bMsomC/aEJOSpHXdFKFGQ1b0TDPIeL28nJ cloud.google.com/go/dataplex v1.8.1/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= cloud.google.com/go/dataplex v1.9.0/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= cloud.google.com/go/dataplex v1.9.1/go.mod h1:7TyrDT6BCdI8/38Uvp0/ZxBslOslP2X2MPDucliyvSE= +cloud.google.com/go/dataplex v1.10.1/go.mod h1:1MzmBv8FvjYfc7vDdxhnLFNskikkB+3vl475/XdCDhs= +cloud.google.com/go/dataplex v1.10.2/go.mod h1:xdC8URdTrCrZMW6keY779ZT1cTOfV8KEPNsw+LTRT1Y= +cloud.google.com/go/dataplex v1.11.1/go.mod h1:mHJYQQ2VEJHsyoC0OdNyy988DvEbPhqFs5OOLffLX0c= cloud.google.com/go/dataproc v1.7.0/go.mod h1:CKAlMjII9H90RXaMpSxQ8EU6dQx6iAYNPcYPOkSbi8s= cloud.google.com/go/dataproc v1.8.0/go.mod h1:5OW+zNAH0pMpw14JVrPONsxMQYMBqJuzORhIBfBn9uI= cloud.google.com/go/dataproc v1.12.0/go.mod h1:zrF3aX0uV3ikkMz6z4uBbIKyhRITnxvr4i3IjKsKrw4= cloud.google.com/go/dataproc/v2 v2.0.1/go.mod h1:7Ez3KRHdFGcfY7GcevBbvozX+zyWGcwLJvvAMwCaoZ4= cloud.google.com/go/dataproc/v2 v2.2.0/go.mod h1:lZR7AQtwZPvmINx5J87DSOOpTfof9LVZju6/Qo4lmcY= +cloud.google.com/go/dataproc/v2 v2.2.1/go.mod h1:QdAJLaBjh+l4PVlVZcmrmhGccosY/omC1qwfQ61Zv/o= +cloud.google.com/go/dataproc/v2 v2.2.2/go.mod h1:aocQywVmQVF4i8CL740rNI/ZRpsaaC1Wh2++BJ7HEJ4= +cloud.google.com/go/dataproc/v2 v2.2.3/go.mod h1:G5R6GBc9r36SXv/RtZIVfB8SipI+xVn0bX5SxUzVYbY= cloud.google.com/go/dataqna v0.5.0/go.mod h1:90Hyk596ft3zUQ8NkFfvICSIfHFh1Bc7C4cK3vbhkeo= cloud.google.com/go/dataqna v0.6.0/go.mod h1:1lqNpM7rqNLVgWBJyk5NF6Uen2PHym0jtVJonplVsDA= cloud.google.com/go/dataqna v0.7.0/go.mod h1:Lx9OcIIeqCrw1a6KdO3/5KMP1wAmTc0slZWwP12Qq3c= cloud.google.com/go/dataqna v0.8.1/go.mod h1:zxZM0Bl6liMePWsHA8RMGAfmTG34vJMapbHAxQ5+WA8= +cloud.google.com/go/dataqna v0.8.2/go.mod h1:KNEqgx8TTmUipnQsScOoDpq/VlXVptUqVMZnt30WAPs= +cloud.google.com/go/dataqna v0.8.3/go.mod h1:wXNBW2uvc9e7Gl5k8adyAMnLush1KVV6lZUhB+rqNu4= +cloud.google.com/go/dataqna v0.8.4/go.mod h1:mySRKjKg5Lz784P6sCov3p1QD+RZQONRMRjzGNcFd0c= cloud.google.com/go/datastore v1.0.0/go.mod h1:LXYbyblFSglQ5pkeyhO+Qmw7ukd3C+pD7TKLgZqpHYE= cloud.google.com/go/datastore v1.1.0/go.mod h1:umbIZjpQpHh4hmRpGhH4tLFup+FVzqBi1b3c64qFpCk= cloud.google.com/go/datastore v1.10.0/go.mod h1:PC5UzAmDEkAmkfaknstTYbNpgE49HAgW2J1gcgUfmdM= @@ -298,6 +414,7 @@ cloud.google.com/go/datastore v1.12.0/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1 cloud.google.com/go/datastore v1.12.1/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1EoLgSp6/N70= cloud.google.com/go/datastore v1.13.0/go.mod h1:KjdB88W897MRITkvWWJrg2OUtrR5XVj1EoLgSp6/N70= cloud.google.com/go/datastore v1.14.0/go.mod h1:GAeStMBIt9bPS7jMJA85kgkpsMkvseWWXiaHya9Jes8= +cloud.google.com/go/datastore v1.15.0/go.mod h1:GAeStMBIt9bPS7jMJA85kgkpsMkvseWWXiaHya9Jes8= cloud.google.com/go/datastream v1.2.0/go.mod h1:i/uTP8/fZwgATHS/XFu0TcNUhuA0twZxxQ3EyCUQMwo= cloud.google.com/go/datastream v1.3.0/go.mod h1:cqlOX8xlyYF/uxhiKn6Hbv6WjwPPuI9W2M9SAXwaLLQ= cloud.google.com/go/datastream v1.4.0/go.mod h1:h9dpzScPhDTs5noEMQVWP8Wx8AFBRyS0s8KWPx/9r0g= @@ -306,12 +423,18 @@ cloud.google.com/go/datastream v1.6.0/go.mod h1:6LQSuswqLa7S4rPAOZFVjHIG3wJIjZcZ cloud.google.com/go/datastream v1.7.0/go.mod h1:uxVRMm2elUSPuh65IbZpzJNMbuzkcvu5CjMqVIUHrww= cloud.google.com/go/datastream v1.9.1/go.mod h1:hqnmr8kdUBmrnk65k5wNRoHSCYksvpdZIcZIEl8h43Q= cloud.google.com/go/datastream v1.10.0/go.mod h1:hqnmr8kdUBmrnk65k5wNRoHSCYksvpdZIcZIEl8h43Q= +cloud.google.com/go/datastream v1.10.1/go.mod h1:7ngSYwnw95YFyTd5tOGBxHlOZiL+OtpjheqU7t2/s/c= +cloud.google.com/go/datastream v1.10.2/go.mod h1:W42TFgKAs/om6x/CdXX5E4oiAsKlH+e8MTGy81zdYt0= +cloud.google.com/go/datastream v1.10.3/go.mod h1:YR0USzgjhqA/Id0Ycu1VvZe8hEWwrkjuXrGbzeDOSEA= cloud.google.com/go/deploy v1.4.0/go.mod h1:5Xghikd4VrmMLNaF6FiRFDlHb59VM59YoDQnOUdsH/c= cloud.google.com/go/deploy v1.5.0/go.mod h1:ffgdD0B89tToyW/U/D2eL0jN2+IEV/3EMuXHA0l4r+s= cloud.google.com/go/deploy v1.6.0/go.mod h1:f9PTHehG/DjCom3QH0cntOVRm93uGBDt2vKzAPwpXQI= cloud.google.com/go/deploy v1.8.0/go.mod h1:z3myEJnA/2wnB4sgjqdMfgxCA0EqC3RBTNcVPs93mtQ= cloud.google.com/go/deploy v1.11.0/go.mod h1:tKuSUV5pXbn67KiubiUNUejqLs4f5cxxiCNCeyl0F2g= cloud.google.com/go/deploy v1.13.0/go.mod h1:tKuSUV5pXbn67KiubiUNUejqLs4f5cxxiCNCeyl0F2g= +cloud.google.com/go/deploy v1.13.1/go.mod h1:8jeadyLkH9qu9xgO3hVWw8jVr29N1mnW42gRJT8GY6g= +cloud.google.com/go/deploy v1.14.1/go.mod h1:N8S0b+aIHSEeSr5ORVoC0+/mOPUysVt8ae4QkZYolAw= +cloud.google.com/go/deploy v1.14.2/go.mod h1:e5XOUI5D+YGldyLNZ21wbp9S8otJbBE4i88PtO9x/2g= cloud.google.com/go/dialogflow v1.15.0/go.mod h1:HbHDWs33WOGJgn6rfzBW1Kv807BE3O1+xGbn59zZWI4= cloud.google.com/go/dialogflow v1.16.1/go.mod h1:po6LlzGfK+smoSmTBnbkIZY2w8ffjz/RcGSS+sh1el0= cloud.google.com/go/dialogflow v1.17.0/go.mod h1:YNP09C/kXA1aZdBgC/VtXX74G/TKn7XVCcVumTflA+8= @@ -323,10 +446,17 @@ cloud.google.com/go/dialogflow v1.32.0/go.mod h1:jG9TRJl8CKrDhMEcvfcfFkkpp8ZhgPz cloud.google.com/go/dialogflow v1.38.0/go.mod h1:L7jnH+JL2mtmdChzAIcXQHXMvQkE3U4hTaNltEuxXn4= cloud.google.com/go/dialogflow v1.40.0/go.mod h1:L7jnH+JL2mtmdChzAIcXQHXMvQkE3U4hTaNltEuxXn4= cloud.google.com/go/dialogflow v1.43.0/go.mod h1:pDUJdi4elL0MFmt1REMvFkdsUTYSHq+rTCS8wg0S3+M= +cloud.google.com/go/dialogflow v1.44.0/go.mod h1:pDUJdi4elL0MFmt1REMvFkdsUTYSHq+rTCS8wg0S3+M= +cloud.google.com/go/dialogflow v1.44.1/go.mod h1:n/h+/N2ouKOO+rbe/ZnI186xImpqvCVj2DdsWS/0EAk= +cloud.google.com/go/dialogflow v1.44.2/go.mod h1:QzFYndeJhpVPElnFkUXxdlptx0wPnBWLCBT9BvtC3/c= +cloud.google.com/go/dialogflow v1.44.3/go.mod h1:mHly4vU7cPXVweuB5R0zsYKPMzy240aQdAu06SqBbAQ= cloud.google.com/go/dlp v1.6.0/go.mod h1:9eyB2xIhpU0sVwUixfBubDoRwP+GjeUoxxeueZmqvmM= cloud.google.com/go/dlp v1.7.0/go.mod h1:68ak9vCiMBjbasxeVD17hVPxDEck+ExiHavX8kiHG+Q= cloud.google.com/go/dlp v1.9.0/go.mod h1:qdgmqgTyReTz5/YNSSuueR8pl7hO0o9bQ39ZhtgkWp4= cloud.google.com/go/dlp v1.10.1/go.mod h1:IM8BWz1iJd8njcNcG0+Kyd9OPnqnRNkDV8j42VT5KOI= +cloud.google.com/go/dlp v1.10.2/go.mod h1:ZbdKIhcnyhILgccwVDzkwqybthh7+MplGC3kZVZsIOQ= +cloud.google.com/go/dlp v1.10.3/go.mod h1:iUaTc/ln8I+QT6Ai5vmuwfw8fqTk2kaz0FvCwhLCom0= +cloud.google.com/go/dlp v1.11.1/go.mod h1:/PA2EnioBeXTL/0hInwgj0rfsQb3lpE3R8XUJxqUNKI= cloud.google.com/go/documentai v1.7.0/go.mod h1:lJvftZB5NRiFSX4moiye1SMxHx0Bc3x1+p9e/RfXYiU= cloud.google.com/go/documentai v1.8.0/go.mod h1:xGHNEB7CtsnySCNrCFdCyyMz44RhFEEX2Q7UD0c5IhU= cloud.google.com/go/documentai v1.9.0/go.mod h1:FS5485S8R00U10GhgBC0aNGrJxBP8ZVpEeJ7PQDZd6k= @@ -336,35 +466,55 @@ cloud.google.com/go/documentai v1.18.0/go.mod h1:F6CK6iUH8J81FehpskRmhLq/3VlwQvb cloud.google.com/go/documentai v1.20.0/go.mod h1:yJkInoMcK0qNAEdRnqY/D5asy73tnPe88I1YTZT+a8E= cloud.google.com/go/documentai v1.22.0/go.mod h1:yJkInoMcK0qNAEdRnqY/D5asy73tnPe88I1YTZT+a8E= cloud.google.com/go/documentai v1.22.1/go.mod h1:LKs22aDHbJv7ufXuPypzRO7rG3ALLJxzdCXDPutw4Qc= +cloud.google.com/go/documentai v1.23.0/go.mod h1:LKs22aDHbJv7ufXuPypzRO7rG3ALLJxzdCXDPutw4Qc= +cloud.google.com/go/documentai v1.23.2/go.mod h1:Q/wcRT+qnuXOpjAkvOV4A+IeQl04q2/ReT7SSbytLSo= +cloud.google.com/go/documentai v1.23.4/go.mod h1:4MYAaEMnADPN1LPN5xboDR5QVB6AgsaxgFdJhitlE2Y= +cloud.google.com/go/documentai v1.23.5/go.mod h1:ghzBsyVTiVdkfKaUCum/9bGBEyBjDO4GfooEcYKhN+g= cloud.google.com/go/domains v0.6.0/go.mod h1:T9Rz3GasrpYk6mEGHh4rymIhjlnIuB4ofT1wTxDeT4Y= cloud.google.com/go/domains v0.7.0/go.mod h1:PtZeqS1xjnXuRPKE/88Iru/LdfoRyEHYA9nFQf4UKpg= cloud.google.com/go/domains v0.8.0/go.mod h1:M9i3MMDzGFXsydri9/vW+EWz9sWb4I6WyHqdlAk0idE= cloud.google.com/go/domains v0.9.1/go.mod h1:aOp1c0MbejQQ2Pjf1iJvnVyT+z6R6s8pX66KaCSDYfE= +cloud.google.com/go/domains v0.9.2/go.mod h1:3YvXGYzZG1Temjbk7EyGCuGGiXHJwVNmwIf+E/cUp5I= +cloud.google.com/go/domains v0.9.3/go.mod h1:29k66YNDLDY9LCFKpGFeh6Nj9r62ZKm5EsUJxAl84KU= +cloud.google.com/go/domains v0.9.4/go.mod h1:27jmJGShuXYdUNjyDG0SodTfT5RwLi7xmH334Gvi3fY= cloud.google.com/go/edgecontainer v0.1.0/go.mod h1:WgkZ9tp10bFxqO8BLPqv2LlfmQF1X8lZqwW4r1BTajk= cloud.google.com/go/edgecontainer v0.2.0/go.mod h1:RTmLijy+lGpQ7BXuTDa4C4ssxyXT34NIuHIgKuP4s5w= cloud.google.com/go/edgecontainer v0.3.0/go.mod h1:FLDpP4nykgwwIfcLt6zInhprzw0lEi2P1fjO6Ie0qbc= cloud.google.com/go/edgecontainer v1.0.0/go.mod h1:cttArqZpBB2q58W/upSG++ooo6EsblxDIolxa3jSjbY= cloud.google.com/go/edgecontainer v1.1.1/go.mod h1:O5bYcS//7MELQZs3+7mabRqoWQhXCzenBu0R8bz2rwk= +cloud.google.com/go/edgecontainer v1.1.2/go.mod h1:wQRjIzqxEs9e9wrtle4hQPSR1Y51kqN75dgF7UllZZ4= +cloud.google.com/go/edgecontainer v1.1.3/go.mod h1:Ll2DtIABzEfaxaVSbwj3QHFaOOovlDFiWVDu349jSsA= +cloud.google.com/go/edgecontainer v1.1.4/go.mod h1:AvFdVuZuVGdgaE5YvlL1faAoa1ndRR/5XhXZvPBHbsE= cloud.google.com/go/errorreporting v0.3.0/go.mod h1:xsP2yaAp+OAW4OIm60An2bbLpqIhKXdWR/tawvl7QzU= cloud.google.com/go/essentialcontacts v1.3.0/go.mod h1:r+OnHa5jfj90qIfZDO/VztSFqbQan7HV75p8sA+mdGI= cloud.google.com/go/essentialcontacts v1.4.0/go.mod h1:8tRldvHYsmnBCHdFpvU+GL75oWiBKl80BiqlFh9tp+8= cloud.google.com/go/essentialcontacts v1.5.0/go.mod h1:ay29Z4zODTuwliK7SnX8E86aUF2CTzdNtvv42niCX0M= cloud.google.com/go/essentialcontacts v1.6.2/go.mod h1:T2tB6tX+TRak7i88Fb2N9Ok3PvY3UNbUsMag9/BARh4= +cloud.google.com/go/essentialcontacts v1.6.3/go.mod h1:yiPCD7f2TkP82oJEFXFTou8Jl8L6LBRPeBEkTaO0Ggo= +cloud.google.com/go/essentialcontacts v1.6.4/go.mod h1:iju5Vy3d9tJUg0PYMd1nHhjV7xoCXaOAVabrwLaPBEM= +cloud.google.com/go/essentialcontacts v1.6.5/go.mod h1:jjYbPzw0x+yglXC890l6ECJWdYeZ5dlYACTFL0U/VuM= cloud.google.com/go/eventarc v1.7.0/go.mod h1:6ctpF3zTnaQCxUjHUdcfgcA1A2T309+omHZth7gDfmc= cloud.google.com/go/eventarc v1.8.0/go.mod h1:imbzxkyAU4ubfsaKYdQg04WS1NvncblHEup4kvF+4gw= cloud.google.com/go/eventarc v1.10.0/go.mod h1:u3R35tmZ9HvswGRBnF48IlYgYeBcPUCjkr4BTdem2Kw= cloud.google.com/go/eventarc v1.11.0/go.mod h1:PyUjsUKPWoRBCHeOxZd/lbOOjahV41icXyUY5kSTvVY= cloud.google.com/go/eventarc v1.12.1/go.mod h1:mAFCW6lukH5+IZjkvrEss+jmt2kOdYlN8aMx3sRJiAI= cloud.google.com/go/eventarc v1.13.0/go.mod h1:mAFCW6lukH5+IZjkvrEss+jmt2kOdYlN8aMx3sRJiAI= +cloud.google.com/go/eventarc v1.13.1/go.mod h1:EqBxmGHFrruIara4FUQ3RHlgfCn7yo1HYsu2Hpt/C3Y= +cloud.google.com/go/eventarc v1.13.2/go.mod h1:X9A80ShVu19fb4e5sc/OLV7mpFUKZMwfJFeeWhcIObM= +cloud.google.com/go/eventarc v1.13.3/go.mod h1:RWH10IAZIRcj1s/vClXkBgMHwh59ts7hSWcqD3kaclg= cloud.google.com/go/filestore v1.3.0/go.mod h1:+qbvHGvXU1HaKX2nD0WEPo92TP/8AQuCVEBXNY9z0+w= cloud.google.com/go/filestore v1.4.0/go.mod h1:PaG5oDfo9r224f8OYXURtAsY+Fbyq/bLYoINEK8XQAI= cloud.google.com/go/filestore v1.5.0/go.mod h1:FqBXDWBp4YLHqRnVGveOkHDf8svj9r5+mUDLupOWEDs= cloud.google.com/go/filestore v1.6.0/go.mod h1:di5unNuss/qfZTw2U9nhFqo8/ZDSc466dre85Kydllg= cloud.google.com/go/filestore v1.7.1/go.mod h1:y10jsorq40JJnjR/lQ8AfFbbcGlw3g+Dp8oN7i7FjV4= +cloud.google.com/go/filestore v1.7.2/go.mod h1:TYOlyJs25f/omgj+vY7/tIG/E7BX369triSPzE4LdgE= +cloud.google.com/go/filestore v1.7.3/go.mod h1:Qp8WaEERR3cSkxToxFPHh/b8AACkSut+4qlCjAmKTV0= +cloud.google.com/go/filestore v1.7.4/go.mod h1:S5JCxIbFjeBhWMTfIYH2Jx24J6BqjwpkkPl+nBA5DlI= cloud.google.com/go/firestore v1.9.0/go.mod h1:HMkjKHNTtRyZNiMzu7YAsLr9K3X2udY2AMwDaMEQiiE= cloud.google.com/go/firestore v1.11.0/go.mod h1:b38dKhgzlmNNGTNZZwe7ZRFEuRab1Hay3/DBsIGKKy4= cloud.google.com/go/firestore v1.12.0/go.mod h1:b38dKhgzlmNNGTNZZwe7ZRFEuRab1Hay3/DBsIGKKy4= cloud.google.com/go/firestore v1.13.0/go.mod h1:QojqqOh8IntInDUSTAh0c8ZsPYAr68Ma8c5DWOy8xb8= +cloud.google.com/go/firestore v1.14.0/go.mod h1:96MVaHLsEhbvkBEdZgfN+AS/GIkco1LRpH9Xp9YZfzQ= cloud.google.com/go/functions v1.6.0/go.mod h1:3H1UA3qiIPRWD7PeZKLvHZ9SaQhR26XIJcC0A5GbvAk= cloud.google.com/go/functions v1.7.0/go.mod h1:+d+QBcWM+RsrgZfV9xo6KfA1GlzJfxcfZcRPEhDDfzg= cloud.google.com/go/functions v1.8.0/go.mod h1:RTZ4/HsQjIqIYP9a9YPbU+QFoQsAlYgrwOXJWHn1POY= @@ -373,6 +523,9 @@ cloud.google.com/go/functions v1.10.0/go.mod h1:0D3hEOe3DbEvCXtYOZHQZmD+SzYsi1Yb cloud.google.com/go/functions v1.12.0/go.mod h1:AXWGrF3e2C/5ehvwYo/GH6O5s09tOPksiKhz+hH8WkA= cloud.google.com/go/functions v1.13.0/go.mod h1:EU4O007sQm6Ef/PwRsI8N2umygGqPBS/IZQKBQBcJ3c= cloud.google.com/go/functions v1.15.1/go.mod h1:P5yNWUTkyU+LvW/S9O6V+V423VZooALQlqoXdoPz5AE= +cloud.google.com/go/functions v1.15.2/go.mod h1:CHAjtcR6OU4XF2HuiVeriEdELNcnvRZSk1Q8RMqy4lE= +cloud.google.com/go/functions v1.15.3/go.mod h1:r/AMHwBheapkkySEhiZYLDBwVJCdlRwsm4ieJu35/Ug= +cloud.google.com/go/functions v1.15.4/go.mod h1:CAsTc3VlRMVvx+XqXxKqVevguqJpnVip4DdonFsX28I= cloud.google.com/go/gaming v1.5.0/go.mod h1:ol7rGcxP/qHTRQE/RO4bxkXq+Fix0j6D4LFPzYTIrDM= cloud.google.com/go/gaming v1.6.0/go.mod h1:YMU1GEvA39Qt3zWGyAVA9bpYz/yAhTvaQ1t2sK4KPUA= cloud.google.com/go/gaming v1.7.0/go.mod h1:LrB8U7MHdGgFG851iHAfqUdLcKBdQ55hzXy9xBJz0+w= @@ -384,26 +537,41 @@ cloud.google.com/go/gkebackup v0.3.0/go.mod h1:n/E671i1aOQvUxT541aTkCwExO/bTer2H cloud.google.com/go/gkebackup v0.4.0/go.mod h1:byAyBGUwYGEEww7xsbnUTBHIYcOPy/PgUWUtOeRm9Vg= cloud.google.com/go/gkebackup v1.3.0/go.mod h1:vUDOu++N0U5qs4IhG1pcOnD1Mac79xWy6GoBFlWCWBU= cloud.google.com/go/gkebackup v1.3.1/go.mod h1:vUDOu++N0U5qs4IhG1pcOnD1Mac79xWy6GoBFlWCWBU= +cloud.google.com/go/gkebackup v1.3.2/go.mod h1:OMZbXzEJloyXMC7gqdSB+EOEQ1AKcpGYvO3s1ec5ixk= +cloud.google.com/go/gkebackup v1.3.3/go.mod h1:eMk7/wVV5P22KBakhQnJxWSVftL1p4VBFLpv0kIft7I= +cloud.google.com/go/gkebackup v1.3.4/go.mod h1:gLVlbM8h/nHIs09ns1qx3q3eaXcGSELgNu1DWXYz1HI= cloud.google.com/go/gkeconnect v0.5.0/go.mod h1:c5lsNAg5EwAy7fkqX/+goqFsU1Da/jQFqArp+wGNr/o= cloud.google.com/go/gkeconnect v0.6.0/go.mod h1:Mln67KyU/sHJEBY8kFZ0xTeyPtzbq9StAVvEULYK16A= cloud.google.com/go/gkeconnect v0.7.0/go.mod h1:SNfmVqPkaEi3bF/B3CNZOAYPYdg7sU+obZ+QTky2Myw= cloud.google.com/go/gkeconnect v0.8.1/go.mod h1:KWiK1g9sDLZqhxB2xEuPV8V9NYzrqTUmQR9shJHpOZw= +cloud.google.com/go/gkeconnect v0.8.2/go.mod h1:6nAVhwchBJYgQCXD2pHBFQNiJNyAd/wyxljpaa6ZPrY= +cloud.google.com/go/gkeconnect v0.8.3/go.mod h1:i9GDTrfzBSUZGCe98qSu1B8YB8qfapT57PenIb820Jo= +cloud.google.com/go/gkeconnect v0.8.4/go.mod h1:84hZz4UMlDCKl8ifVW8layK4WHlMAFeq8vbzjU0yJkw= cloud.google.com/go/gkehub v0.9.0/go.mod h1:WYHN6WG8w9bXU0hqNxt8rm5uxnk8IH+lPY9J2TV7BK0= cloud.google.com/go/gkehub v0.10.0/go.mod h1:UIPwxI0DsrpsVoWpLB0stwKCP+WFVG9+y977wO+hBH0= cloud.google.com/go/gkehub v0.11.0/go.mod h1:JOWHlmN+GHyIbuWQPl47/C2RFhnFKH38jH9Ascu3n0E= cloud.google.com/go/gkehub v0.12.0/go.mod h1:djiIwwzTTBrF5NaXCGv3mf7klpEMcST17VBTVVDcuaw= cloud.google.com/go/gkehub v0.14.1/go.mod h1:VEXKIJZ2avzrbd7u+zeMtW00Y8ddk/4V9511C9CQGTY= +cloud.google.com/go/gkehub v0.14.2/go.mod h1:iyjYH23XzAxSdhrbmfoQdePnlMj2EWcvnR+tHdBQsCY= +cloud.google.com/go/gkehub v0.14.3/go.mod h1:jAl6WafkHHW18qgq7kqcrXYzN08hXeK/Va3utN8VKg8= +cloud.google.com/go/gkehub v0.14.4/go.mod h1:Xispfu2MqnnFt8rV/2/3o73SK1snL8s9dYJ9G2oQMfc= cloud.google.com/go/gkemulticloud v0.3.0/go.mod h1:7orzy7O0S+5kq95e4Hpn7RysVA7dPs8W/GgfUtsPbrA= cloud.google.com/go/gkemulticloud v0.4.0/go.mod h1:E9gxVBnseLWCk24ch+P9+B2CoDFJZTyIgLKSalC7tuI= cloud.google.com/go/gkemulticloud v0.5.0/go.mod h1:W0JDkiyi3Tqh0TJr//y19wyb1yf8llHVto2Htf2Ja3Y= cloud.google.com/go/gkemulticloud v0.6.1/go.mod h1:kbZ3HKyTsiwqKX7Yw56+wUGwwNZViRnxWK2DVknXWfw= cloud.google.com/go/gkemulticloud v1.0.0/go.mod h1:kbZ3HKyTsiwqKX7Yw56+wUGwwNZViRnxWK2DVknXWfw= +cloud.google.com/go/gkemulticloud v1.0.1/go.mod h1:AcrGoin6VLKT/fwZEYuqvVominLriQBCKmbjtnbMjG8= +cloud.google.com/go/gkemulticloud v1.0.2/go.mod h1:+ee5VXxKb3H1l4LZAcgWB/rvI16VTNTrInWxDjAGsGo= +cloud.google.com/go/gkemulticloud v1.0.3/go.mod h1:7NpJBN94U6DY1xHIbsDqB2+TFZUfjLUKLjUX8NGLor0= cloud.google.com/go/grafeas v0.2.0/go.mod h1:KhxgtF2hb0P191HlY5besjYm6MqTSTj3LSI+M+ByZHc= cloud.google.com/go/grafeas v0.3.0/go.mod h1:P7hgN24EyONOTMyeJH6DxG4zD7fwiYa5Q6GUgyFSOU8= cloud.google.com/go/gsuiteaddons v1.3.0/go.mod h1:EUNK/J1lZEZO8yPtykKxLXI6JSVN2rg9bN8SXOa0bgM= cloud.google.com/go/gsuiteaddons v1.4.0/go.mod h1:rZK5I8hht7u7HxFQcFei0+AtfS9uSushomRlg+3ua1o= cloud.google.com/go/gsuiteaddons v1.5.0/go.mod h1:TFCClYLd64Eaa12sFVmUyG62tk4mdIsI7pAnSXRkcFo= cloud.google.com/go/gsuiteaddons v1.6.1/go.mod h1:CodrdOqRZcLp5WOwejHWYBjZvfY0kOphkAKpF/3qdZY= +cloud.google.com/go/gsuiteaddons v1.6.2/go.mod h1:K65m9XSgs8hTF3X9nNTPi8IQueljSdYo9F+Mi+s4MyU= +cloud.google.com/go/gsuiteaddons v1.6.3/go.mod h1:sCFJkZoMrLZT3JTb8uJqgKPNshH2tfXeCwTFRebTq48= +cloud.google.com/go/gsuiteaddons v1.6.4/go.mod h1:rxtstw7Fx22uLOXBpsvb9DUbC+fiXs7rF4U29KHM/pE= cloud.google.com/go/iam v0.1.0/go.mod h1:vcUNEa0pEm0qRVpmWepWaFMIAI8/hjB9mO8rNCJtF6c= cloud.google.com/go/iam v0.3.0/go.mod h1:XzJPvDayI+9zsASAFO68Hk07u3z+f+JrT2xXNdp4bnY= cloud.google.com/go/iam v0.5.0/go.mod h1:wPU9Vt0P4UmCux7mqtRu6jcpPAb74cP1fh50J3QpkUc= @@ -417,6 +585,9 @@ cloud.google.com/go/iam v1.0.1/go.mod h1:yR3tmSL8BcZB4bxByRv2jkSIahVmCtfKZwLYGBa cloud.google.com/go/iam v1.1.0/go.mod h1:nxdHjaKfCr7fNYx/HJMM8LgiMugmveWlkatear5gVyk= cloud.google.com/go/iam v1.1.1/go.mod h1:A5avdyVL2tCppe4unb0951eI9jreack+RJ0/d+KUZOU= cloud.google.com/go/iam v1.1.2/go.mod h1:A5avdyVL2tCppe4unb0951eI9jreack+RJ0/d+KUZOU= +cloud.google.com/go/iam v1.1.3/go.mod h1:3khUlaBXfPKKe7huYgEpDn6FtgRyMEqbkvBxrQyY5SE= +cloud.google.com/go/iam v1.1.4/go.mod h1:l/rg8l1AaA+VFMho/HYx2Vv6xinPSLMF8qfhRPIZ0L8= +cloud.google.com/go/iam v1.1.5/go.mod h1:rB6P/Ic3mykPbFio+vo7403drjlgvoWfYpJhMXEbzv8= cloud.google.com/go/iap v1.4.0/go.mod h1:RGFwRJdihTINIe4wZ2iCP0zF/qu18ZwyKxrhMhygBEc= cloud.google.com/go/iap v1.5.0/go.mod h1:UH/CGgKd4KyohZL5Pt0jSKE4m3FR51qg6FKQ/z/Ix9A= cloud.google.com/go/iap v1.6.0/go.mod h1:NSuvI9C/j7UdjGjIde7t7HBz+QTwBcapPE07+sSRcLk= @@ -424,15 +595,24 @@ cloud.google.com/go/iap v1.7.0/go.mod h1:beqQx56T9O1G1yNPph+spKpNibDlYIiIixiqsQX cloud.google.com/go/iap v1.7.1/go.mod h1:WapEwPc7ZxGt2jFGB/C/bm+hP0Y6NXzOYGjpPnmMS74= cloud.google.com/go/iap v1.8.1/go.mod h1:sJCbeqg3mvWLqjZNsI6dfAtbbV1DL2Rl7e1mTyXYREQ= cloud.google.com/go/iap v1.9.0/go.mod h1:01OFxd1R+NFrg78S+hoPV5PxEzv22HXaNqUUlmNHFuY= +cloud.google.com/go/iap v1.9.1/go.mod h1:SIAkY7cGMLohLSdBR25BuIxO+I4fXJiL06IBL7cy/5Q= +cloud.google.com/go/iap v1.9.2/go.mod h1:GwDTOs047PPSnwRD0Us5FKf4WDRcVvHg1q9WVkKBhdI= +cloud.google.com/go/iap v1.9.3/go.mod h1:DTdutSZBqkkOm2HEOTBzhZxh2mwwxshfD/h3yofAiCw= cloud.google.com/go/ids v1.1.0/go.mod h1:WIuwCaYVOzHIj2OhN9HAwvW+DBdmUAdcWlFxRl+KubM= cloud.google.com/go/ids v1.2.0/go.mod h1:5WXvp4n25S0rA/mQWAg1YEEBBq6/s+7ml1RDCW1IrcY= cloud.google.com/go/ids v1.3.0/go.mod h1:JBdTYwANikFKaDP6LtW5JAi4gubs57SVNQjemdt6xV4= cloud.google.com/go/ids v1.4.1/go.mod h1:np41ed8YMU8zOgv53MMMoCntLTn2lF+SUzlM+O3u/jw= +cloud.google.com/go/ids v1.4.2/go.mod h1:3vw8DX6YddRu9BncxuzMyWn0g8+ooUjI2gslJ7FH3vk= +cloud.google.com/go/ids v1.4.3/go.mod h1:9CXPqI3GedjmkjbMWCUhMZ2P2N7TUMzAkVXYEH2orYU= +cloud.google.com/go/ids v1.4.4/go.mod h1:z+WUc2eEl6S/1aZWzwtVNWoSZslgzPxAboS0lZX0HjI= cloud.google.com/go/iot v1.3.0/go.mod h1:r7RGh2B61+B8oz0AGE+J72AhA0G7tdXItODWsaA2oLs= cloud.google.com/go/iot v1.4.0/go.mod h1:dIDxPOn0UvNDUMD8Ger7FIaTuvMkj+aGk94RPP0iV+g= cloud.google.com/go/iot v1.5.0/go.mod h1:mpz5259PDl3XJthEmh9+ap0affn/MqNSP4My77Qql9o= cloud.google.com/go/iot v1.6.0/go.mod h1:IqdAsmE2cTYYNO1Fvjfzo9po179rAtJeVGUvkLN3rLE= cloud.google.com/go/iot v1.7.1/go.mod h1:46Mgw7ev1k9KqK1ao0ayW9h0lI+3hxeanz+L1zmbbbk= +cloud.google.com/go/iot v1.7.2/go.mod h1:q+0P5zr1wRFpw7/MOgDXrG/HVA+l+cSwdObffkrpnSg= +cloud.google.com/go/iot v1.7.3/go.mod h1:t8itFchkol4VgNbHnIq9lXoOOtHNR3uAACQMYbN9N4I= +cloud.google.com/go/iot v1.7.4/go.mod h1:3TWqDVvsddYBG++nHSZmluoCAVGr1hAcabbWZNKEZLk= cloud.google.com/go/kms v1.4.0/go.mod h1:fajBHndQ+6ubNw6Ss2sSd+SWvjL26RNo/dr7uxsnnOA= cloud.google.com/go/kms v1.5.0/go.mod h1:QJS2YY0eJGBg3mnDfuaCyLauWwBJiHRboYxJ++1xJNg= cloud.google.com/go/kms v1.6.0/go.mod h1:Jjy850yySiasBUDi6KFUwUv2n1+o7QZFyuUJg6OgjA0= @@ -444,6 +624,9 @@ cloud.google.com/go/kms v1.11.0/go.mod h1:hwdiYC0xjnWsKQQCQQmIQnS9asjYVSK6jtXm+z cloud.google.com/go/kms v1.12.1/go.mod h1:c9J991h5DTl+kg7gi3MYomh12YEENGrf48ee/N/2CDM= cloud.google.com/go/kms v1.15.0/go.mod h1:c9J991h5DTl+kg7gi3MYomh12YEENGrf48ee/N/2CDM= cloud.google.com/go/kms v1.15.2/go.mod h1:3hopT4+7ooWRCjc2DxgnpESFxhIraaI2IpAVUEhbT/w= +cloud.google.com/go/kms v1.15.3/go.mod h1:AJdXqHxS2GlPyduM99s9iGqi2nwbviBbhV/hdmt4iOQ= +cloud.google.com/go/kms v1.15.4/go.mod h1:L3Sdj6QTHK8dfwK5D1JLsAyELsNMnd3tAIwGS4ltKpc= +cloud.google.com/go/kms v1.15.5/go.mod h1:cU2H5jnp6G2TDpUGZyqTCoy1n16fbubHZjmVXSMtwDI= cloud.google.com/go/language v1.4.0/go.mod h1:F9dRpNFQmJbkaop6g0JhSBXCNlO90e1KWx5iDdxbWic= cloud.google.com/go/language v1.6.0/go.mod h1:6dJ8t3B+lUYfStgls25GusK04NLh3eDLQnWM3mdEbhI= cloud.google.com/go/language v1.7.0/go.mod h1:DJ6dYN/W+SQOjF8e1hLQXMF21AkH2w9wiPzPCJa2MIE= @@ -451,10 +634,16 @@ cloud.google.com/go/language v1.8.0/go.mod h1:qYPVHf7SPoNNiCL2Dr0FfEFNil1qi3pQEy cloud.google.com/go/language v1.9.0/go.mod h1:Ns15WooPM5Ad/5no/0n81yUetis74g3zrbeJBE+ptUY= cloud.google.com/go/language v1.10.1/go.mod h1:CPp94nsdVNiQEt1CNjF5WkTcisLiHPyIbMhvR8H2AW0= cloud.google.com/go/language v1.11.0/go.mod h1:uDx+pFDdAKTY8ehpWbiXyQdz8tDSYLJbQcXsCkjYyvQ= +cloud.google.com/go/language v1.11.1/go.mod h1:Xyid9MG9WOX3utvDbpX7j3tXDmmDooMyMDqgUVpH17U= +cloud.google.com/go/language v1.12.1/go.mod h1:zQhalE2QlQIxbKIZt54IASBzmZpN/aDASea5zl1l+J4= +cloud.google.com/go/language v1.12.2/go.mod h1:9idWapzr/JKXBBQ4lWqVX/hcadxB194ry20m/bTrhWc= cloud.google.com/go/lifesciences v0.5.0/go.mod h1:3oIKy8ycWGPUyZDR/8RNnTOYevhaMLqh5vLUXs9zvT8= cloud.google.com/go/lifesciences v0.6.0/go.mod h1:ddj6tSX/7BOnhxCSd3ZcETvtNr8NZ6t/iPhY2Tyfu08= cloud.google.com/go/lifesciences v0.8.0/go.mod h1:lFxiEOMqII6XggGbOnKiyZ7IBwoIqA84ClvoezaA/bo= cloud.google.com/go/lifesciences v0.9.1/go.mod h1:hACAOd1fFbCGLr/+weUKRAJas82Y4vrL3O5326N//Wc= +cloud.google.com/go/lifesciences v0.9.2/go.mod h1:QHEOO4tDzcSAzeJg7s2qwnLM2ji8IRpQl4p6m5Z9yTA= +cloud.google.com/go/lifesciences v0.9.3/go.mod h1:gNGBOJV80IWZdkd+xz4GQj4mbqaz737SCLHn2aRhQKM= +cloud.google.com/go/lifesciences v0.9.4/go.mod h1:bhm64duKhMi7s9jR9WYJYvjAFJwRqNj+Nia7hF0Z7JA= cloud.google.com/go/logging v1.6.1/go.mod h1:5ZO0mHHbvm8gEmeEUHrmDlTDSu5imF6MUP9OfilNXBw= cloud.google.com/go/logging v1.7.0/go.mod h1:3xjP2CjkM3ZkO73aj4ASA5wRPGGCRrPIAeNqVNkzY8M= cloud.google.com/go/logging v1.8.1/go.mod h1:TJjR+SimHwuC8MZ9cjByQulAMgni+RkXeI3wwctHJEI= @@ -464,25 +653,40 @@ cloud.google.com/go/longrunning v0.4.1/go.mod h1:4iWDqhBZ70CvZ6BfETbvam3T8FMvLK+ cloud.google.com/go/longrunning v0.4.2/go.mod h1:OHrnaYyLUV6oqwh0xiS7e5sLQhP1m0QU9R+WhGDMgIQ= cloud.google.com/go/longrunning v0.5.0/go.mod h1:0JNuqRShmscVAhIACGtskSAWtqtOoPkwP0YF1oVEchc= cloud.google.com/go/longrunning v0.5.1/go.mod h1:spvimkwdz6SPWKEt/XBij79E9fiTkHSQl/fRUUQJYJc= +cloud.google.com/go/longrunning v0.5.2/go.mod h1:nqo6DQbNV2pXhGDbDMoN2bWz68MjZUzqv2YttZiveCs= +cloud.google.com/go/longrunning v0.5.3/go.mod h1:y/0ga59EYu58J6SHmmQOvekvND2qODbu8ywBBW7EK7Y= +cloud.google.com/go/longrunning v0.5.4/go.mod h1:zqNVncI0BOP8ST6XQD1+VcvuShMmq7+xFSzOL++V0dI= cloud.google.com/go/managedidentities v1.3.0/go.mod h1:UzlW3cBOiPrzucO5qWkNkh0w33KFtBJU281hacNvsdE= cloud.google.com/go/managedidentities v1.4.0/go.mod h1:NWSBYbEMgqmbZsLIyKvxrYbtqOsxY1ZrGM+9RgDqInM= cloud.google.com/go/managedidentities v1.5.0/go.mod h1:+dWcZ0JlUmpuxpIDfyP5pP5y0bLdRwOS4Lp7gMni/LA= cloud.google.com/go/managedidentities v1.6.1/go.mod h1:h/irGhTN2SkZ64F43tfGPMbHnypMbu4RB3yl8YcuEak= +cloud.google.com/go/managedidentities v1.6.2/go.mod h1:5c2VG66eCa0WIq6IylRk3TBW83l161zkFvCj28X7jn8= +cloud.google.com/go/managedidentities v1.6.3/go.mod h1:tewiat9WLyFN0Fi7q1fDD5+0N4VUoL0SCX0OTCthZq4= +cloud.google.com/go/managedidentities v1.6.4/go.mod h1:WgyaECfHmF00t/1Uk8Oun3CQ2PGUtjc3e9Alh79wyiM= cloud.google.com/go/maps v0.1.0/go.mod h1:BQM97WGyfw9FWEmQMpZ5T6cpovXXSd1cGmFma94eubI= cloud.google.com/go/maps v0.6.0/go.mod h1:o6DAMMfb+aINHz/p/jbcY+mYeXBoZoxTfdSQ8VAJaCw= cloud.google.com/go/maps v0.7.0/go.mod h1:3GnvVl3cqeSvgMcpRlQidXsPYuDGQ8naBis7MVzpXsY= cloud.google.com/go/maps v1.3.0/go.mod h1:6mWTUv+WhnOwAgjVsSW2QPPECmW+s3PcRyOa9vgG/5s= cloud.google.com/go/maps v1.4.0/go.mod h1:6mWTUv+WhnOwAgjVsSW2QPPECmW+s3PcRyOa9vgG/5s= +cloud.google.com/go/maps v1.4.1/go.mod h1:BxSa0BnW1g2U2gNdbq5zikLlHUuHW0GFWh7sgML2kIY= +cloud.google.com/go/maps v1.5.1/go.mod h1:NPMZw1LJwQZYCfz4y+EIw+SI+24A4bpdFJqdKVr0lt4= +cloud.google.com/go/maps v1.6.1/go.mod h1:4+buOHhYXFBp58Zj/K+Lc1rCmJssxxF4pJ5CJnhdz18= cloud.google.com/go/mediatranslation v0.5.0/go.mod h1:jGPUhGTybqsPQn91pNXw0xVHfuJ3leR1wj37oU3y1f4= cloud.google.com/go/mediatranslation v0.6.0/go.mod h1:hHdBCTYNigsBxshbznuIMFNe5QXEowAuNmmC7h8pu5w= cloud.google.com/go/mediatranslation v0.7.0/go.mod h1:LCnB/gZr90ONOIQLgSXagp8XUW1ODs2UmUMvcgMfI2I= cloud.google.com/go/mediatranslation v0.8.1/go.mod h1:L/7hBdEYbYHQJhX2sldtTO5SZZ1C1vkapubj0T2aGig= +cloud.google.com/go/mediatranslation v0.8.2/go.mod h1:c9pUaDRLkgHRx3irYE5ZC8tfXGrMYwNZdmDqKMSfFp8= +cloud.google.com/go/mediatranslation v0.8.3/go.mod h1:F9OnXTy336rteOEywtY7FOqCk+J43o2RF638hkOQl4Y= +cloud.google.com/go/mediatranslation v0.8.4/go.mod h1:9WstgtNVAdN53m6TQa5GjIjLqKQPXe74hwSCxUP6nj4= cloud.google.com/go/memcache v1.4.0/go.mod h1:rTOfiGZtJX1AaFUrOgsMHX5kAzaTQ8azHiuDoTPzNsE= cloud.google.com/go/memcache v1.5.0/go.mod h1:dk3fCK7dVo0cUU2c36jKb4VqKPS22BTkf81Xq617aWM= cloud.google.com/go/memcache v1.6.0/go.mod h1:XS5xB0eQZdHtTuTF9Hf8eJkKtR3pVRCcvJwtm68T3rA= cloud.google.com/go/memcache v1.7.0/go.mod h1:ywMKfjWhNtkQTxrWxCkCFkoPjLHPW6A7WOTVI8xy3LY= cloud.google.com/go/memcache v1.9.0/go.mod h1:8oEyzXCu+zo9RzlEaEjHl4KkgjlNDaXbCQeQWlzNFJM= cloud.google.com/go/memcache v1.10.1/go.mod h1:47YRQIarv4I3QS5+hoETgKO40InqzLP6kpNLvyXuyaA= +cloud.google.com/go/memcache v1.10.2/go.mod h1:f9ZzJHLBrmd4BkguIAa/l/Vle6uTHzHokdnzSWOdQ6A= +cloud.google.com/go/memcache v1.10.3/go.mod h1:6z89A41MT2DVAW0P4iIRdu5cmRTsbsFn4cyiIx8gbwo= +cloud.google.com/go/memcache v1.10.4/go.mod h1:v/d8PuC8d1gD6Yn5+I3INzLR01IDn0N4Ym56RgikSI0= cloud.google.com/go/metastore v1.5.0/go.mod h1:2ZNrDcQwghfdtCwJ33nM0+GrBGlVuh8rakL3vdPY3XY= cloud.google.com/go/metastore v1.6.0/go.mod h1:6cyQTls8CWXzk45G55x57DVQ9gWg7RiH65+YgPsNh9s= cloud.google.com/go/metastore v1.7.0/go.mod h1:s45D0B4IlsINu87/AsWiEVYbLaIMeUSoxlKKDqBGFS8= @@ -490,12 +694,19 @@ cloud.google.com/go/metastore v1.8.0/go.mod h1:zHiMc4ZUpBiM7twCIFQmJ9JMEkDSyZS9U cloud.google.com/go/metastore v1.10.0/go.mod h1:fPEnH3g4JJAk+gMRnrAnoqyv2lpUCqJPWOodSaf45Eo= cloud.google.com/go/metastore v1.11.1/go.mod h1:uZuSo80U3Wd4zi6C22ZZliOUJ3XeM/MlYi/z5OAOWRA= cloud.google.com/go/metastore v1.12.0/go.mod h1:uZuSo80U3Wd4zi6C22ZZliOUJ3XeM/MlYi/z5OAOWRA= +cloud.google.com/go/metastore v1.13.0/go.mod h1:URDhpG6XLeh5K+Glq0NOt74OfrPKTwS62gEPZzb5SOk= +cloud.google.com/go/metastore v1.13.1/go.mod h1:IbF62JLxuZmhItCppcIfzBBfUFq0DIB9HPDoLgWrVOU= +cloud.google.com/go/metastore v1.13.2/go.mod h1:KS59dD+unBji/kFebVp8XU/quNSyo8b6N6tPGspKszA= +cloud.google.com/go/metastore v1.13.3/go.mod h1:K+wdjXdtkdk7AQg4+sXS8bRrQa9gcOr+foOMF2tqINE= cloud.google.com/go/monitoring v1.7.0/go.mod h1:HpYse6kkGo//7p6sT0wsIC6IBDET0RhIsnmlA53dvEk= cloud.google.com/go/monitoring v1.8.0/go.mod h1:E7PtoMJ1kQXWxPjB6mv2fhC5/15jInuulFdYYtlcvT4= cloud.google.com/go/monitoring v1.12.0/go.mod h1:yx8Jj2fZNEkL/GYZyTLS4ZtZEZN8WtDEiEqG4kLK50w= cloud.google.com/go/monitoring v1.13.0/go.mod h1:k2yMBAB1H9JT/QETjNkgdCGD9bPF712XiLTVr+cBrpw= cloud.google.com/go/monitoring v1.15.1/go.mod h1:lADlSAlFdbqQuwwpaImhsJXu1QSdd3ojypXrFSMr2rM= cloud.google.com/go/monitoring v1.16.0/go.mod h1:Ptp15HgAyM1fNICAojDMoNc/wUmn67mLHQfyqbw+poY= +cloud.google.com/go/monitoring v1.16.1/go.mod h1:6HsxddR+3y9j+o/cMJH6q/KJ/CBTvM/38L/1m7bTRJ4= +cloud.google.com/go/monitoring v1.16.2/go.mod h1:B44KGwi4ZCF8Rk/5n+FWeispDXoKSk9oss2QNlXJBgc= +cloud.google.com/go/monitoring v1.16.3/go.mod h1:KwSsX5+8PnXv5NJnICZzW2R8pWTis8ypC4zmdRD63Tw= cloud.google.com/go/networkconnectivity v1.4.0/go.mod h1:nOl7YL8odKyAOtzNX73/M5/mGZgqqMeryi6UPZTk/rA= cloud.google.com/go/networkconnectivity v1.5.0/go.mod h1:3GzqJx7uhtlM3kln0+x5wyFvuVH1pIBJjhCpjzSt75o= cloud.google.com/go/networkconnectivity v1.6.0/go.mod h1:OJOoEXW+0LAxHh89nXd64uGG+FbQoeH8DtxCHVOMlaM= @@ -504,16 +715,26 @@ cloud.google.com/go/networkconnectivity v1.10.0/go.mod h1:UP4O4sWXJG13AqrTdQCD9T cloud.google.com/go/networkconnectivity v1.11.0/go.mod h1:iWmDD4QF16VCDLXUqvyspJjIEtBR/4zq5hwnY2X3scM= cloud.google.com/go/networkconnectivity v1.12.1/go.mod h1:PelxSWYM7Sh9/guf8CFhi6vIqf19Ir/sbfZRUwXh92E= cloud.google.com/go/networkconnectivity v1.13.0/go.mod h1:SAnGPes88pl7QRLUen2HmcBSE9AowVAcdug8c0RSBFk= +cloud.google.com/go/networkconnectivity v1.14.0/go.mod h1:SAnGPes88pl7QRLUen2HmcBSE9AowVAcdug8c0RSBFk= +cloud.google.com/go/networkconnectivity v1.14.1/go.mod h1:LyGPXR742uQcDxZ/wv4EI0Vu5N6NKJ77ZYVnDe69Zug= +cloud.google.com/go/networkconnectivity v1.14.2/go.mod h1:5UFlwIisZylSkGG1AdwK/WZUaoz12PKu6wODwIbFzJo= +cloud.google.com/go/networkconnectivity v1.14.3/go.mod h1:4aoeFdrJpYEXNvrnfyD5kIzs8YtHg945Og4koAjHQek= cloud.google.com/go/networkmanagement v1.4.0/go.mod h1:Q9mdLLRn60AsOrPc8rs8iNV6OHXaGcDdsIQe1ohekq8= cloud.google.com/go/networkmanagement v1.5.0/go.mod h1:ZnOeZ/evzUdUsnvRt792H0uYEnHQEMaz+REhhzJRcf4= cloud.google.com/go/networkmanagement v1.6.0/go.mod h1:5pKPqyXjB/sgtvB5xqOemumoQNB7y95Q7S+4rjSOPYY= cloud.google.com/go/networkmanagement v1.8.0/go.mod h1:Ho/BUGmtyEqrttTgWEe7m+8vDdK74ibQc+Be0q7Fof0= cloud.google.com/go/networkmanagement v1.9.0/go.mod h1:UTUaEU9YwbCAhhz3jEOHr+2/K/MrBk2XxOLS89LQzFw= +cloud.google.com/go/networkmanagement v1.9.1/go.mod h1:CCSYgrQQvW73EJawO2QamemYcOb57LvrDdDU51F0mcI= +cloud.google.com/go/networkmanagement v1.9.2/go.mod h1:iDGvGzAoYRghhp4j2Cji7sF899GnfGQcQRQwgVOWnDw= +cloud.google.com/go/networkmanagement v1.9.3/go.mod h1:y7WMO1bRLaP5h3Obm4tey+NquUvB93Co1oh4wpL+XcU= cloud.google.com/go/networksecurity v0.5.0/go.mod h1:xS6fOCoqpVC5zx15Z/MqkfDwH4+m/61A3ODiDV1xmiQ= cloud.google.com/go/networksecurity v0.6.0/go.mod h1:Q5fjhTr9WMI5mbpRYEbiexTzROf7ZbDzvzCrNl14nyU= cloud.google.com/go/networksecurity v0.7.0/go.mod h1:mAnzoxx/8TBSyXEeESMy9OOYwo1v+gZ5eMRnsT5bC8k= cloud.google.com/go/networksecurity v0.8.0/go.mod h1:B78DkqsxFG5zRSVuwYFRZ9Xz8IcQ5iECsNrPn74hKHU= cloud.google.com/go/networksecurity v0.9.1/go.mod h1:MCMdxOKQ30wsBI1eI659f9kEp4wuuAueoC9AJKSPWZQ= +cloud.google.com/go/networksecurity v0.9.2/go.mod h1:jG0SeAttWzPMUILEHDUvFYdQTl8L/E/KC8iZDj85lEI= +cloud.google.com/go/networksecurity v0.9.3/go.mod h1:l+C0ynM6P+KV9YjOnx+kk5IZqMSLccdBqW6GUoF4p/0= +cloud.google.com/go/networksecurity v0.9.4/go.mod h1:E9CeMZ2zDsNBkr8axKSYm8XyTqNhiCHf1JO/Vb8mD1w= cloud.google.com/go/notebooks v1.2.0/go.mod h1:9+wtppMfVPUeJ8fIWPOq1UnATHISkGXGqTkxeieQ6UY= cloud.google.com/go/notebooks v1.3.0/go.mod h1:bFR5lj07DtCPC7YAAJ//vHskFBxA5JzYlH68kXVdk34= cloud.google.com/go/notebooks v1.4.0/go.mod h1:4QPMngcwmgb6uw7Po99B2xv5ufVoIQ7nOGDyL4P8AgA= @@ -522,20 +743,32 @@ cloud.google.com/go/notebooks v1.7.0/go.mod h1:PVlaDGfJgj1fl1S3dUwhFMXFgfYGhYQt2 cloud.google.com/go/notebooks v1.8.0/go.mod h1:Lq6dYKOYOWUCTvw5t2q1gp1lAp0zxAxRycayS0iJcqQ= cloud.google.com/go/notebooks v1.9.1/go.mod h1:zqG9/gk05JrzgBt4ghLzEepPHNwE5jgPcHZRKhlC1A8= cloud.google.com/go/notebooks v1.10.0/go.mod h1:SOPYMZnttHxqot0SGSFSkRrwE29eqnKPBJFqgWmiK2k= +cloud.google.com/go/notebooks v1.10.1/go.mod h1:5PdJc2SgAybE76kFQCWrTfJolCOUQXF97e+gteUUA6A= +cloud.google.com/go/notebooks v1.11.1/go.mod h1:V2Zkv8wX9kDCGRJqYoI+bQAaoVeE5kSiz4yYHd2yJwQ= +cloud.google.com/go/notebooks v1.11.2/go.mod h1:z0tlHI/lREXC8BS2mIsUeR3agM1AkgLiS+Isov3SS70= cloud.google.com/go/optimization v1.1.0/go.mod h1:5po+wfvX5AQlPznyVEZjGJTMr4+CAkJf2XSTQOOl9l4= cloud.google.com/go/optimization v1.2.0/go.mod h1:Lr7SOHdRDENsh+WXVmQhQTrzdu9ybg0NecjHidBq6xs= cloud.google.com/go/optimization v1.3.1/go.mod h1:IvUSefKiwd1a5p0RgHDbWCIbDFgKuEdB+fPPuP0IDLI= cloud.google.com/go/optimization v1.4.1/go.mod h1:j64vZQP7h9bO49m2rVaTVoNM0vEBEN5eKPUPbZyXOrk= cloud.google.com/go/optimization v1.5.0/go.mod h1:evo1OvTxeBRBu6ydPlrIRizKY/LJKo/drDMMRKqGEUU= +cloud.google.com/go/optimization v1.5.1/go.mod h1:NC0gnUD5MWVAF7XLdoYVPmYYVth93Q6BUzqAq3ZwtV8= +cloud.google.com/go/optimization v1.6.1/go.mod h1:hH2RYPTTM9e9zOiTaYPTiGPcGdNZVnBSBxjIAJzUkqo= +cloud.google.com/go/optimization v1.6.2/go.mod h1:mWNZ7B9/EyMCcwNl1frUGEuY6CPijSkz88Fz2vwKPOY= cloud.google.com/go/orchestration v1.3.0/go.mod h1:Sj5tq/JpWiB//X/q3Ngwdl5K7B7Y0KZ7bfv0wL6fqVA= cloud.google.com/go/orchestration v1.4.0/go.mod h1:6W5NLFWs2TlniBphAViZEVhrXRSMgUGDfW7vrWKvsBk= cloud.google.com/go/orchestration v1.6.0/go.mod h1:M62Bevp7pkxStDfFfTuCOaXgaaqRAga1yKyoMtEoWPQ= cloud.google.com/go/orchestration v1.8.1/go.mod h1:4sluRF3wgbYVRqz7zJ1/EUNc90TTprliq9477fGobD8= +cloud.google.com/go/orchestration v1.8.2/go.mod h1:T1cP+6WyTmh6LSZzeUhvGf0uZVmJyTx7t8z7Vg87+A0= +cloud.google.com/go/orchestration v1.8.3/go.mod h1:xhgWAYqlbYjlz2ftbFghdyqENYW+JXuhBx9KsjMoGHs= +cloud.google.com/go/orchestration v1.8.4/go.mod h1:d0lywZSVYtIoSZXb0iFjv9SaL13PGyVOKDxqGxEf/qI= cloud.google.com/go/orgpolicy v1.4.0/go.mod h1:xrSLIV4RePWmP9P3tBl8S93lTmlAxjm06NSm2UTmKvE= cloud.google.com/go/orgpolicy v1.5.0/go.mod h1:hZEc5q3wzwXJaKrsx5+Ewg0u1LxJ51nNFlext7Tanwc= cloud.google.com/go/orgpolicy v1.10.0/go.mod h1:w1fo8b7rRqlXlIJbVhOMPrwVljyuW5mqssvBtU18ONc= cloud.google.com/go/orgpolicy v1.11.0/go.mod h1:2RK748+FtVvnfuynxBzdnyu7sygtoZa1za/0ZfpOs1M= cloud.google.com/go/orgpolicy v1.11.1/go.mod h1:8+E3jQcpZJQliP+zaFfayC2Pg5bmhuLK755wKhIIUCE= +cloud.google.com/go/orgpolicy v1.11.2/go.mod h1:biRDpNwfyytYnmCRWZWxrKF22Nkz9eNVj9zyaBdpm1o= +cloud.google.com/go/orgpolicy v1.11.3/go.mod h1:oKAtJ/gkMjum5icv2aujkP4CxROxPXsBbYGCDbPO8MM= +cloud.google.com/go/orgpolicy v1.11.4/go.mod h1:0+aNV/nrfoTQ4Mytv+Aw+stBDBjNf4d8fYRA9herfJI= cloud.google.com/go/osconfig v1.7.0/go.mod h1:oVHeCeZELfJP7XLxcBGTMBvRO+1nQ5tFG9VQTmYS2Fs= cloud.google.com/go/osconfig v1.8.0/go.mod h1:EQqZLu5w5XA7eKizepumcvWx+m8mJUhEwiPqWiZeEdg= cloud.google.com/go/osconfig v1.9.0/go.mod h1:Yx+IeIZJ3bdWmzbQU4fxNl8xsZ4amB+dygAwFPlvnNo= @@ -543,16 +776,26 @@ cloud.google.com/go/osconfig v1.10.0/go.mod h1:uMhCzqC5I8zfD9zDEAfvgVhDS8oIjySWh cloud.google.com/go/osconfig v1.11.0/go.mod h1:aDICxrur2ogRd9zY5ytBLV89KEgT2MKB2L/n6x1ooPw= cloud.google.com/go/osconfig v1.12.0/go.mod h1:8f/PaYzoS3JMVfdfTubkowZYGmAhUCjjwnjqWI7NVBc= cloud.google.com/go/osconfig v1.12.1/go.mod h1:4CjBxND0gswz2gfYRCUoUzCm9zCABp91EeTtWXyz0tE= +cloud.google.com/go/osconfig v1.12.2/go.mod h1:eh9GPaMZpI6mEJEuhEjUJmaxvQ3gav+fFEJon1Y8Iw0= +cloud.google.com/go/osconfig v1.12.3/go.mod h1:L/fPS8LL6bEYUi1au832WtMnPeQNT94Zo3FwwV1/xGM= +cloud.google.com/go/osconfig v1.12.4/go.mod h1:B1qEwJ/jzqSRslvdOCI8Kdnp0gSng0xW4LOnIebQomA= cloud.google.com/go/oslogin v1.4.0/go.mod h1:YdgMXWRaElXz/lDk1Na6Fh5orF7gvmJ0FGLIs9LId4E= cloud.google.com/go/oslogin v1.5.0/go.mod h1:D260Qj11W2qx/HVF29zBg+0fd6YCSjSqLUkY/qEenQU= cloud.google.com/go/oslogin v1.6.0/go.mod h1:zOJ1O3+dTU8WPlGEkFSh7qeHPPSoxrcMbbK1Nm2iX70= cloud.google.com/go/oslogin v1.7.0/go.mod h1:e04SN0xO1UNJ1M5GP0vzVBFicIe4O53FOfcixIqTyXo= cloud.google.com/go/oslogin v1.9.0/go.mod h1:HNavntnH8nzrn8JCTT5fj18FuJLFJc4NaZJtBnQtKFs= cloud.google.com/go/oslogin v1.10.1/go.mod h1:x692z7yAue5nE7CsSnoG0aaMbNoRJRXO4sn73R+ZqAs= +cloud.google.com/go/oslogin v1.11.0/go.mod h1:8GMTJs4X2nOAUVJiPGqIWVcDaF0eniEto3xlOxaboXE= +cloud.google.com/go/oslogin v1.11.1/go.mod h1:OhD2icArCVNUxKqtK0mcSmKL7lgr0LVlQz+v9s1ujTg= +cloud.google.com/go/oslogin v1.12.1/go.mod h1:VfwTeFJGbnakxAY236eN8fsnglLiVXndlbcNomY4iZU= +cloud.google.com/go/oslogin v1.12.2/go.mod h1:CQ3V8Jvw4Qo4WRhNPF0o+HAM4DiLuE27Ul9CX9g2QdY= cloud.google.com/go/phishingprotection v0.5.0/go.mod h1:Y3HZknsK9bc9dMi+oE8Bim0lczMU6hrX0UpADuMefr0= cloud.google.com/go/phishingprotection v0.6.0/go.mod h1:9Y3LBLgy0kDTcYET8ZH3bq/7qni15yVUoAxiFxnlSUA= cloud.google.com/go/phishingprotection v0.7.0/go.mod h1:8qJI4QKHoda/sb/7/YmMQ2omRLSLYSu9bU0EKCNI+Lk= cloud.google.com/go/phishingprotection v0.8.1/go.mod h1:AxonW7GovcA8qdEk13NfHq9hNx5KPtfxXNeUxTDxB6I= +cloud.google.com/go/phishingprotection v0.8.2/go.mod h1:LhJ91uyVHEYKSKcMGhOa14zMMWfbEdxG032oT6ECbC8= +cloud.google.com/go/phishingprotection v0.8.3/go.mod h1:3B01yO7T2Ra/TMojifn8EoGd4G9jts/6cIO0DgDY9J8= +cloud.google.com/go/phishingprotection v0.8.4/go.mod h1:6b3kNPAc2AQ6jZfFHioZKg9MQNybDg4ixFd4RPZZ2nE= cloud.google.com/go/policytroubleshooter v1.3.0/go.mod h1:qy0+VwANja+kKrjlQuOzmlvscn4RNsAc0e15GGqfMxg= cloud.google.com/go/policytroubleshooter v1.4.0/go.mod h1:DZT4BcRw3QoO8ota9xw/LKtPa8lKeCByYeKTIf/vxdE= cloud.google.com/go/policytroubleshooter v1.5.0/go.mod h1:Rz1WfV+1oIpPdN2VvvuboLVRsB1Hclg3CKQ53j9l8vw= @@ -560,11 +803,17 @@ cloud.google.com/go/policytroubleshooter v1.6.0/go.mod h1:zYqaPTsmfvpjm5ULxAyD/l cloud.google.com/go/policytroubleshooter v1.7.1/go.mod h1:0NaT5v3Ag1M7U5r0GfDCpUFkWd9YqpubBWsQlhanRv0= cloud.google.com/go/policytroubleshooter v1.8.0/go.mod h1:tmn5Ir5EToWe384EuboTcVQT7nTag2+DuH3uHmKd1HU= cloud.google.com/go/policytroubleshooter v1.9.0/go.mod h1:+E2Lga7TycpeSTj2FsH4oXxTnrbHJGRlKhVZBLGgU64= +cloud.google.com/go/policytroubleshooter v1.9.1/go.mod h1:MYI8i0bCrL8cW+VHN1PoiBTyNZTstCg2WUw2eVC4c4U= +cloud.google.com/go/policytroubleshooter v1.10.1/go.mod h1:5C0rhT3TDZVxAu8813bwmTvd57Phbl8mr9F4ipOsxEs= +cloud.google.com/go/policytroubleshooter v1.10.2/go.mod h1:m4uF3f6LseVEnMV6nknlN2vYGRb+75ylQwJdnOXfnv0= cloud.google.com/go/privatecatalog v0.5.0/go.mod h1:XgosMUvvPyxDjAVNDYxJ7wBW8//hLDDYmnsNcMGq1K0= cloud.google.com/go/privatecatalog v0.6.0/go.mod h1:i/fbkZR0hLN29eEWiiwue8Pb+GforiEIBnV9yrRUOKI= cloud.google.com/go/privatecatalog v0.7.0/go.mod h1:2s5ssIFO69F5csTXcwBP7NPFTZvps26xGzvQ2PQaBYg= cloud.google.com/go/privatecatalog v0.8.0/go.mod h1:nQ6pfaegeDAq/Q5lrfCQzQLhubPiZhSaNhIgfJlnIXs= cloud.google.com/go/privatecatalog v0.9.1/go.mod h1:0XlDXW2unJXdf9zFz968Hp35gl/bhF4twwpXZAW50JA= +cloud.google.com/go/privatecatalog v0.9.2/go.mod h1:RMA4ATa8IXfzvjrhhK8J6H4wwcztab+oZph3c6WmtFc= +cloud.google.com/go/privatecatalog v0.9.3/go.mod h1:K5pn2GrVmOPjXz3T26mzwXLcKivfIJ9R5N79AFCF9UE= +cloud.google.com/go/privatecatalog v0.9.4/go.mod h1:SOjm93f+5hp/U3PqMZAHTtBtluqLygrDrVO8X8tYtG0= cloud.google.com/go/pubsub v1.0.1/go.mod h1:R0Gpsv3s54REJCy4fxDixWD93lHJMoZTyQ2kNxGRt3I= cloud.google.com/go/pubsub v1.1.0/go.mod h1:EwwdRX2sKPjnvnqCa270oGRyludottCI76h+R3AArQw= cloud.google.com/go/pubsub v1.2.0/go.mod h1:jhfEVHT8odbXTkndysNHCcx0awwzvfOlguIAii9o8iA= @@ -588,10 +837,17 @@ cloud.google.com/go/recaptchaenterprise/v2 v2.5.0/go.mod h1:O8LzcHXN3rz0j+LBC91j cloud.google.com/go/recaptchaenterprise/v2 v2.6.0/go.mod h1:RPauz9jeLtB3JVzg6nCbe12qNoaa8pXc4d/YukAmcnA= cloud.google.com/go/recaptchaenterprise/v2 v2.7.0/go.mod h1:19wVj/fs5RtYtynAPJdDTb69oW0vNHYDBTbB4NvMD9c= cloud.google.com/go/recaptchaenterprise/v2 v2.7.2/go.mod h1:kR0KjsJS7Jt1YSyWFkseQ756D45kaYNTlDPPaRAvDBU= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.0/go.mod h1:QuE8EdU9dEnesG8/kG3XuJyNsjEqMlMzg3v3scCJ46c= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.1/go.mod h1:JZYZJOeZjgSSTGP4uz7NlQ4/d1w5hGmksVgM0lbEij0= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.2/go.mod h1:kpaDBOpkwD4G0GVMzG1W6Doy1tFFC97XAV3xy+Rd/pw= +cloud.google.com/go/recaptchaenterprise/v2 v2.8.3/go.mod h1:Dak54rw6lC2gBY8FBznpOCAR58wKf+R+ZSJRoeJok4w= cloud.google.com/go/recommendationengine v0.5.0/go.mod h1:E5756pJcVFeVgaQv3WNpImkFP8a+RptV6dDLGPILjvg= cloud.google.com/go/recommendationengine v0.6.0/go.mod h1:08mq2umu9oIqc7tDy8sx+MNJdLG0fUi3vaSVbztHgJ4= cloud.google.com/go/recommendationengine v0.7.0/go.mod h1:1reUcE3GIu6MeBz/h5xZJqNLuuVjNg1lmWMPyjatzac= cloud.google.com/go/recommendationengine v0.8.1/go.mod h1:MrZihWwtFYWDzE6Hz5nKcNz3gLizXVIDI/o3G1DLcrE= +cloud.google.com/go/recommendationengine v0.8.2/go.mod h1:QIybYHPK58qir9CV2ix/re/M//Ty10OxjnnhWdaKS1Y= +cloud.google.com/go/recommendationengine v0.8.3/go.mod h1:m3b0RZV02BnODE9FeSvGv1qibFo8g0OnmB/RMwYy4V8= +cloud.google.com/go/recommendationengine v0.8.4/go.mod h1:GEteCf1PATl5v5ZsQ60sTClUE0phbWmo3rQ1Js8louU= cloud.google.com/go/recommender v1.5.0/go.mod h1:jdoeiBIVrJe9gQjwd759ecLJbxCDED4A6p+mqoqDvTg= cloud.google.com/go/recommender v1.6.0/go.mod h1:+yETpm25mcoiECKh9DEScGzIRyDKpZ0cEhWGo+8bo+c= cloud.google.com/go/recommender v1.7.0/go.mod h1:XLHs/W+T8olwlGOgfQenXBTbIseGclClff6lhFVe9Bs= @@ -599,33 +855,52 @@ cloud.google.com/go/recommender v1.8.0/go.mod h1:PkjXrTT05BFKwxaUxQmtIlrtj0kph10 cloud.google.com/go/recommender v1.9.0/go.mod h1:PnSsnZY7q+VL1uax2JWkt/UegHssxjUVVCrX52CuEmQ= cloud.google.com/go/recommender v1.10.1/go.mod h1:XFvrE4Suqn5Cq0Lf+mCP6oBHD/yRMA8XxP5sb7Q7gpA= cloud.google.com/go/recommender v1.11.0/go.mod h1:kPiRQhPyTJ9kyXPCG6u/dlPLbYfFlkwHNRwdzPVAoII= +cloud.google.com/go/recommender v1.11.1/go.mod h1:sGwFFAyI57v2Hc5LbIj+lTwXipGu9NW015rkaEM5B18= +cloud.google.com/go/recommender v1.11.2/go.mod h1:AeoJuzOvFR/emIcXdVFkspVXVTYpliRCmKNYDnyBv6Y= +cloud.google.com/go/recommender v1.11.3/go.mod h1:+FJosKKJSId1MBFeJ/TTyoGQZiEelQQIZMKYYD8ruK4= cloud.google.com/go/redis v1.7.0/go.mod h1:V3x5Jq1jzUcg+UNsRvdmsfuFnit1cfe3Z/PGyq/lm4Y= cloud.google.com/go/redis v1.8.0/go.mod h1:Fm2szCDavWzBk2cDKxrkmWBqoCiL1+Ctwq7EyqBCA/A= cloud.google.com/go/redis v1.9.0/go.mod h1:HMYQuajvb2D0LvMgZmLDZW8V5aOC/WxstZHiy4g8OiA= cloud.google.com/go/redis v1.10.0/go.mod h1:ThJf3mMBQtW18JzGgh41/Wld6vnDDc/F/F35UolRZPM= cloud.google.com/go/redis v1.11.0/go.mod h1:/X6eicana+BWcUda5PpwZC48o37SiFVTFSs0fWAJ7uQ= cloud.google.com/go/redis v1.13.1/go.mod h1:VP7DGLpE91M6bcsDdMuyCm2hIpB6Vp2hI090Mfd1tcg= +cloud.google.com/go/redis v1.13.2/go.mod h1:0Hg7pCMXS9uz02q+LoEVl5dNHUkIQv+C/3L76fandSA= +cloud.google.com/go/redis v1.13.3/go.mod h1:vbUpCKUAZSYzFcWKmICnYgRAhTFg9r+djWqFxDYXi4U= +cloud.google.com/go/redis v1.14.1/go.mod h1:MbmBxN8bEnQI4doZPC1BzADU4HGocHBk2de3SbgOkqs= cloud.google.com/go/resourcemanager v1.3.0/go.mod h1:bAtrTjZQFJkiWTPDb1WBjzvc6/kifjj4QBYuKCCoqKA= cloud.google.com/go/resourcemanager v1.4.0/go.mod h1:MwxuzkumyTX7/a3n37gmsT3py7LIXwrShilPh3P1tR0= cloud.google.com/go/resourcemanager v1.5.0/go.mod h1:eQoXNAiAvCf5PXxWxXjhKQoTMaUSNrEfg+6qdf/wots= cloud.google.com/go/resourcemanager v1.6.0/go.mod h1:YcpXGRs8fDzcUl1Xw8uOVmI8JEadvhRIkoXXUNVYcVo= cloud.google.com/go/resourcemanager v1.7.0/go.mod h1:HlD3m6+bwhzj9XCouqmeiGuni95NTrExfhoSrkC/3EI= cloud.google.com/go/resourcemanager v1.9.1/go.mod h1:dVCuosgrh1tINZ/RwBufr8lULmWGOkPS8gL5gqyjdT8= +cloud.google.com/go/resourcemanager v1.9.2/go.mod h1:OujkBg1UZg5lX2yIyMo5Vz9O5hf7XQOSV7WxqxxMtQE= +cloud.google.com/go/resourcemanager v1.9.3/go.mod h1:IqrY+g0ZgLsihcfcmqSe+RKp1hzjXwG904B92AwBz6U= +cloud.google.com/go/resourcemanager v1.9.4/go.mod h1:N1dhP9RFvo3lUfwtfLWVxfUWq8+KUQ+XLlHLH3BoFJ0= cloud.google.com/go/resourcesettings v1.3.0/go.mod h1:lzew8VfESA5DQ8gdlHwMrqZs1S9V87v3oCnKCWoOuQU= cloud.google.com/go/resourcesettings v1.4.0/go.mod h1:ldiH9IJpcrlC3VSuCGvjR5of/ezRrOxFtpJoJo5SmXg= cloud.google.com/go/resourcesettings v1.5.0/go.mod h1:+xJF7QSG6undsQDfsCJyqWXyBwUoJLhetkRMDRnIoXA= cloud.google.com/go/resourcesettings v1.6.1/go.mod h1:M7mk9PIZrC5Fgsu1kZJci6mpgN8o0IUzVx3eJU3y4Jw= +cloud.google.com/go/resourcesettings v1.6.2/go.mod h1:mJIEDd9MobzunWMeniaMp6tzg4I2GvD3TTmPkc8vBXk= +cloud.google.com/go/resourcesettings v1.6.3/go.mod h1:pno5D+7oDYkMWZ5BpPsb4SO0ewg3IXcmmrUZaMJrFic= +cloud.google.com/go/resourcesettings v1.6.4/go.mod h1:pYTTkWdv2lmQcjsthbZLNBP4QW140cs7wqA3DuqErVI= cloud.google.com/go/retail v1.8.0/go.mod h1:QblKS8waDmNUhghY2TI9O3JLlFk8jybHeV4BF19FrE4= cloud.google.com/go/retail v1.9.0/go.mod h1:g6jb6mKuCS1QKnH/dpu7isX253absFl6iE92nHwlBUY= cloud.google.com/go/retail v1.10.0/go.mod h1:2gDk9HsL4HMS4oZwz6daui2/jmKvqShXKQuB2RZ+cCc= cloud.google.com/go/retail v1.11.0/go.mod h1:MBLk1NaWPmh6iVFSz9MeKG/Psyd7TAgm6y/9L2B4x9Y= cloud.google.com/go/retail v1.12.0/go.mod h1:UMkelN/0Z8XvKymXFbD4EhFJlYKRx1FGhQkVPU5kF14= cloud.google.com/go/retail v1.14.1/go.mod h1:y3Wv3Vr2k54dLNIrCzenyKG8g8dhvhncT2NcNjb/6gE= +cloud.google.com/go/retail v1.14.2/go.mod h1:W7rrNRChAEChX336QF7bnMxbsjugcOCPU44i5kbLiL8= +cloud.google.com/go/retail v1.14.3/go.mod h1:Omz2akDHeSlfCq8ArPKiBxlnRpKEBjUH386JYFLUvXo= +cloud.google.com/go/retail v1.14.4/go.mod h1:l/N7cMtY78yRnJqp5JW8emy7MB1nz8E4t2yfOmklYfg= cloud.google.com/go/run v0.2.0/go.mod h1:CNtKsTA1sDcnqqIFR3Pb5Tq0usWxJJvsWOCPldRU3Do= cloud.google.com/go/run v0.3.0/go.mod h1:TuyY1+taHxTjrD0ZFk2iAR+xyOXEA0ztb7U3UNA0zBo= cloud.google.com/go/run v0.8.0/go.mod h1:VniEnuBwqjigv0A7ONfQUaEItaiCRVujlMqerPPiktM= cloud.google.com/go/run v0.9.0/go.mod h1:Wwu+/vvg8Y+JUApMwEDfVfhetv30hCG4ZwDR/IXl2Qg= cloud.google.com/go/run v1.2.0/go.mod h1:36V1IlDzQ0XxbQjUx6IYbw8H3TJnWvhii963WW3B/bo= +cloud.google.com/go/run v1.3.0/go.mod h1:S/osX/4jIPZGg+ssuqh6GNgg7syixKe3YnprwehzHKU= +cloud.google.com/go/run v1.3.1/go.mod h1:cymddtZOzdwLIAsmS6s+Asl4JoXIDm/K1cpZTxV4Q5s= +cloud.google.com/go/run v1.3.2/go.mod h1:SIhmqArbjdU/D9M6JoHaAqnAMKLFtXaVdNeq04NjnVE= +cloud.google.com/go/run v1.3.3/go.mod h1:WSM5pGyJ7cfYyYbONVQBN4buz42zFqwG67Q3ch07iK4= cloud.google.com/go/scheduler v1.4.0/go.mod h1:drcJBmxF3aqZJRhmkHQ9b3uSSpQoltBPGPxGAWROx6s= cloud.google.com/go/scheduler v1.5.0/go.mod h1:ri073ym49NW3AfT6DZi21vLZrG07GXr5p3H1KxN5QlI= cloud.google.com/go/scheduler v1.6.0/go.mod h1:SgeKVM7MIwPn3BqtcBntpLyrIJftQISRrYB5ZtT+KOk= @@ -633,11 +908,17 @@ cloud.google.com/go/scheduler v1.7.0/go.mod h1:jyCiBqWW956uBjjPMMuX09n3x37mtyPJe cloud.google.com/go/scheduler v1.8.0/go.mod h1:TCET+Y5Gp1YgHT8py4nlg2Sew8nUHMqcpousDgXJVQc= cloud.google.com/go/scheduler v1.9.0/go.mod h1:yexg5t+KSmqu+njTIh3b7oYPheFtBWGcbVUYF1GGMIc= cloud.google.com/go/scheduler v1.10.1/go.mod h1:R63Ldltd47Bs4gnhQkmNDse5w8gBRrhObZ54PxgR2Oo= +cloud.google.com/go/scheduler v1.10.2/go.mod h1:O3jX6HRH5eKCA3FutMw375XHZJudNIKVonSCHv7ropY= +cloud.google.com/go/scheduler v1.10.3/go.mod h1:8ANskEM33+sIbpJ+R4xRfw/jzOG+ZFE8WVLy7/yGvbc= +cloud.google.com/go/scheduler v1.10.4/go.mod h1:MTuXcrJC9tqOHhixdbHDFSIuh7xZF2IysiINDuiq6NI= cloud.google.com/go/secretmanager v1.6.0/go.mod h1:awVa/OXF6IiyaU1wQ34inzQNc4ISIDIrId8qE5QGgKA= cloud.google.com/go/secretmanager v1.8.0/go.mod h1:hnVgi/bN5MYHd3Gt0SPuTPPp5ENina1/LxM+2W9U9J4= cloud.google.com/go/secretmanager v1.9.0/go.mod h1:b71qH2l1yHmWQHt9LC80akm86mX8AL6X1MA01dW8ht4= cloud.google.com/go/secretmanager v1.10.0/go.mod h1:MfnrdvKMPNra9aZtQFvBcvRU54hbPD8/HayQdlUgJpU= cloud.google.com/go/secretmanager v1.11.1/go.mod h1:znq9JlXgTNdBeQk9TBW/FnR/W4uChEKGeqQWAJ8SXFw= +cloud.google.com/go/secretmanager v1.11.2/go.mod h1:MQm4t3deoSub7+WNwiC4/tRYgDBHJgJPvswqQVB1Vss= +cloud.google.com/go/secretmanager v1.11.3/go.mod h1:0bA2o6FabmShrEy328i67aV+65XoUFFSmVeLBn/51jI= +cloud.google.com/go/secretmanager v1.11.4/go.mod h1:wreJlbS9Zdq21lMzWmJ0XhWW2ZxgPeahsqeV/vZoJ3w= cloud.google.com/go/security v1.5.0/go.mod h1:lgxGdyOKKjHL4YG3/YwIL2zLqMFCKs0UbQwgyZmfJl4= cloud.google.com/go/security v1.7.0/go.mod h1:mZklORHl6Bg7CNnnjLH//0UlAlaXqiG7Lb9PsPXLfD0= cloud.google.com/go/security v1.8.0/go.mod h1:hAQOwgmaHhztFhiQ41CjDODdWP0+AE1B3sX4OFlq+GU= @@ -646,6 +927,9 @@ cloud.google.com/go/security v1.10.0/go.mod h1:QtOMZByJVlibUT2h9afNDWRZ1G96gVywH cloud.google.com/go/security v1.12.0/go.mod h1:rV6EhrpbNHrrxqlvW0BWAIawFWq3X90SduMJdFwtLB8= cloud.google.com/go/security v1.13.0/go.mod h1:Q1Nvxl1PAgmeW0y3HTt54JYIvUdtcpYKVfIB8AOMZ+0= cloud.google.com/go/security v1.15.1/go.mod h1:MvTnnbsWnehoizHi09zoiZob0iCHVcL4AUBj76h9fXA= +cloud.google.com/go/security v1.15.2/go.mod h1:2GVE/v1oixIRHDaClVbHuPcZwAqFM28mXuAKCfMgYIg= +cloud.google.com/go/security v1.15.3/go.mod h1:gQ/7Q2JYUZZgOzqKtw9McShH+MjNvtDpL40J1cT+vBs= +cloud.google.com/go/security v1.15.4/go.mod h1:oN7C2uIZKhxCLiAAijKUCuHLZbIt/ghYEo8MqwD/Ty4= cloud.google.com/go/securitycenter v1.13.0/go.mod h1:cv5qNAqjY84FCN6Y9z28WlkKXyWsgLO832YiWwkCWcU= cloud.google.com/go/securitycenter v1.14.0/go.mod h1:gZLAhtyKv85n52XYWt6RmeBdydyxfPeTrpToDPw4Auc= cloud.google.com/go/securitycenter v1.15.0/go.mod h1:PeKJ0t8MoFmmXLXWm41JidyzI3PJjd8sXWaVqg43WWk= @@ -653,6 +937,9 @@ cloud.google.com/go/securitycenter v1.16.0/go.mod h1:Q9GMaLQFUD+5ZTabrbujNWLtSLZ cloud.google.com/go/securitycenter v1.18.1/go.mod h1:0/25gAzCM/9OL9vVx4ChPeM/+DlfGQJDwBy/UC8AKK0= cloud.google.com/go/securitycenter v1.19.0/go.mod h1:LVLmSg8ZkkyaNy4u7HCIshAngSQ8EcIRREP3xBnyfag= cloud.google.com/go/securitycenter v1.23.0/go.mod h1:8pwQ4n+Y9WCWM278R8W3nF65QtY172h4S8aXyI9/hsQ= +cloud.google.com/go/securitycenter v1.23.1/go.mod h1:w2HV3Mv/yKhbXKwOCu2i8bCuLtNP1IMHuiYQn4HJq5s= +cloud.google.com/go/securitycenter v1.24.1/go.mod h1:3h9IdjjHhVMXdQnmqzVnM7b0wMn/1O/U20eWVpMpZjI= +cloud.google.com/go/securitycenter v1.24.2/go.mod h1:l1XejOngggzqwr4Fa2Cn+iWZGf+aBLTXtB/vXjy5vXM= cloud.google.com/go/servicecontrol v1.4.0/go.mod h1:o0hUSJ1TXJAmi/7fLJAedOovnujSEvjKCAFNXPQ1RaU= cloud.google.com/go/servicecontrol v1.5.0/go.mod h1:qM0CnXHhyqKVuiZnGKrIurvVImCs8gmqWsDoqe9sU1s= cloud.google.com/go/servicecontrol v1.10.0/go.mod h1:pQvyvSRh7YzUF2efw7H87V92mxU8FnFDawMClGCNuAA= @@ -666,6 +953,9 @@ cloud.google.com/go/servicedirectory v1.8.0/go.mod h1:srXodfhY1GFIPvltunswqXpVxF cloud.google.com/go/servicedirectory v1.9.0/go.mod h1:29je5JjiygNYlmsGz8k6o+OZ8vd4f//bQLtvzkPPT/s= cloud.google.com/go/servicedirectory v1.10.1/go.mod h1:Xv0YVH8s4pVOwfM/1eMTl0XJ6bzIOSLDt8f8eLaGOxQ= cloud.google.com/go/servicedirectory v1.11.0/go.mod h1:Xv0YVH8s4pVOwfM/1eMTl0XJ6bzIOSLDt8f8eLaGOxQ= +cloud.google.com/go/servicedirectory v1.11.1/go.mod h1:tJywXimEWzNzw9FvtNjsQxxJ3/41jseeILgwU/QLrGI= +cloud.google.com/go/servicedirectory v1.11.2/go.mod h1:KD9hCLhncWRV5jJphwIpugKwM5bn1x0GyVVD4NO8mGg= +cloud.google.com/go/servicedirectory v1.11.3/go.mod h1:LV+cHkomRLr67YoQy3Xq2tUXBGOs5z5bPofdq7qtiAw= cloud.google.com/go/servicemanagement v1.4.0/go.mod h1:d8t8MDbezI7Z2R1O/wu8oTggo3BI2GKYbdG4y/SJTco= cloud.google.com/go/servicemanagement v1.5.0/go.mod h1:XGaCRe57kfqu4+lRxaFEAuqmjzF0r+gWHjWqKqBvKFo= cloud.google.com/go/servicemanagement v1.6.0/go.mod h1:aWns7EeeCOtGEX4OvZUWCCJONRZeFKiptqKf1D0l/Jc= @@ -678,11 +968,16 @@ cloud.google.com/go/shell v1.3.0/go.mod h1:VZ9HmRjZBsjLGXusm7K5Q5lzzByZmJHf1d0IW cloud.google.com/go/shell v1.4.0/go.mod h1:HDxPzZf3GkDdhExzD/gs8Grqk+dmYcEjGShZgYa9URw= cloud.google.com/go/shell v1.6.0/go.mod h1:oHO8QACS90luWgxP3N9iZVuEiSF84zNyLytb+qE2f9A= cloud.google.com/go/shell v1.7.1/go.mod h1:u1RaM+huXFaTojTbW4g9P5emOrrmLE69KrxqQahKn4g= +cloud.google.com/go/shell v1.7.2/go.mod h1:KqRPKwBV0UyLickMn0+BY1qIyE98kKyI216sH/TuHmc= +cloud.google.com/go/shell v1.7.3/go.mod h1:cTTEz/JdaBsQAeTQ3B6HHldZudFoYBOqjteev07FbIc= +cloud.google.com/go/shell v1.7.4/go.mod h1:yLeXB8eKLxw0dpEmXQ/FjriYrBijNsONpwnWsdPqlKM= cloud.google.com/go/spanner v1.41.0/go.mod h1:MLYDBJR/dY4Wt7ZaMIQ7rXOTLjYrmxLE/5ve9vFfWos= cloud.google.com/go/spanner v1.44.0/go.mod h1:G8XIgYdOK+Fbcpbs7p2fiprDw4CaZX63whnSMLVBxjk= cloud.google.com/go/spanner v1.45.0/go.mod h1:FIws5LowYz8YAE1J8fOS7DJup8ff7xJeetWEo5REA2M= cloud.google.com/go/spanner v1.47.0/go.mod h1:IXsJwVW2j4UKs0eYDqodab6HgGuA1bViSqW4uH9lfUI= cloud.google.com/go/spanner v1.49.0/go.mod h1:eGj9mQGK8+hkgSVbHNQ06pQ4oS+cyc4tXXd6Dif1KoM= +cloud.google.com/go/spanner v1.50.0/go.mod h1:eGj9mQGK8+hkgSVbHNQ06pQ4oS+cyc4tXXd6Dif1KoM= +cloud.google.com/go/spanner v1.51.0/go.mod h1:c5KNo5LQ1X5tJwma9rSQZsXNBDNvj4/n8BVc3LNahq0= cloud.google.com/go/speech v1.6.0/go.mod h1:79tcr4FHCimOp56lwC01xnt/WPJZc4v3gzyT7FoBkCM= cloud.google.com/go/speech v1.7.0/go.mod h1:KptqL+BAQIhMsj1kOP2la5DSEEerPDuOP/2mmkhHhZQ= cloud.google.com/go/speech v1.8.0/go.mod h1:9bYIl1/tjsAnMgKGHKmBZzXKEkGgtU+MpdDPTE9f7y0= @@ -691,6 +986,9 @@ cloud.google.com/go/speech v1.14.1/go.mod h1:gEosVRPJ9waG7zqqnsHpYTOoAS4KouMRLDF cloud.google.com/go/speech v1.15.0/go.mod h1:y6oH7GhqCaZANH7+Oe0BhgIogsNInLlz542tg3VqeYI= cloud.google.com/go/speech v1.17.1/go.mod h1:8rVNzU43tQvxDaGvqOhpDqgkJTFowBpDvCJ14kGlJYo= cloud.google.com/go/speech v1.19.0/go.mod h1:8rVNzU43tQvxDaGvqOhpDqgkJTFowBpDvCJ14kGlJYo= +cloud.google.com/go/speech v1.19.1/go.mod h1:WcuaWz/3hOlzPFOVo9DUsblMIHwxP589y6ZMtaG+iAA= +cloud.google.com/go/speech v1.19.2/go.mod h1:2OYFfj+Ch5LWjsaSINuCZsre/789zlcCI3SY4oAi2oI= +cloud.google.com/go/speech v1.20.1/go.mod h1:wwolycgONvfz2EDU8rKuHRW3+wc9ILPsAWoikBEWavY= cloud.google.com/go/storage v1.0.0/go.mod h1:IhtSnM/ZTZV8YYJWCY8RULGVqBDmpoyjwiyrjsg+URw= cloud.google.com/go/storage v1.5.0/go.mod h1:tpKbwo567HUNpVclU5sGELwQWBDZ8gh0ZeosJ0Rtdos= cloud.google.com/go/storage v1.6.0/go.mod h1:N7U0C8pVQ/+NIKOBQyamJIeKQKkZ+mxpohlUTyfDhBk= @@ -708,25 +1006,40 @@ cloud.google.com/go/storagetransfer v1.6.0/go.mod h1:y77xm4CQV/ZhFZH75PLEXY0ROiS cloud.google.com/go/storagetransfer v1.7.0/go.mod h1:8Giuj1QNb1kfLAiWM1bN6dHzfdlDAVC9rv9abHot2W4= cloud.google.com/go/storagetransfer v1.8.0/go.mod h1:JpegsHHU1eXg7lMHkvf+KE5XDJ7EQu0GwNJbbVGanEw= cloud.google.com/go/storagetransfer v1.10.0/go.mod h1:DM4sTlSmGiNczmV6iZyceIh2dbs+7z2Ayg6YAiQlYfA= +cloud.google.com/go/storagetransfer v1.10.1/go.mod h1:rS7Sy0BtPviWYTTJVWCSV4QrbBitgPeuK4/FKa4IdLs= +cloud.google.com/go/storagetransfer v1.10.2/go.mod h1:meIhYQup5rg9juQJdyppnA/WLQCOguxtk1pr3/vBWzA= +cloud.google.com/go/storagetransfer v1.10.3/go.mod h1:Up8LY2p6X68SZ+WToswpQbQHnJpOty/ACcMafuey8gc= cloud.google.com/go/talent v1.1.0/go.mod h1:Vl4pt9jiHKvOgF9KoZo6Kob9oV4lwd/ZD5Cto54zDRw= cloud.google.com/go/talent v1.2.0/go.mod h1:MoNF9bhFQbiJ6eFD3uSsg0uBALw4n4gaCaEjBw9zo8g= cloud.google.com/go/talent v1.3.0/go.mod h1:CmcxwJ/PKfRgd1pBjQgU6W3YBwiewmUzQYH5HHmSCmM= cloud.google.com/go/talent v1.4.0/go.mod h1:ezFtAgVuRf8jRsvyE6EwmbTK5LKciD4KVnHuDEFmOOA= cloud.google.com/go/talent v1.5.0/go.mod h1:G+ODMj9bsasAEJkQSzO2uHQWXHHXUomArjWQQYkqK6c= cloud.google.com/go/talent v1.6.2/go.mod h1:CbGvmKCG61mkdjcqTcLOkb2ZN1SrQI8MDyma2l7VD24= +cloud.google.com/go/talent v1.6.3/go.mod h1:xoDO97Qd4AK43rGjJvyBHMskiEf3KulgYzcH6YWOVoo= +cloud.google.com/go/talent v1.6.4/go.mod h1:QsWvi5eKeh6gG2DlBkpMaFYZYrYUnIpo34f6/V5QykY= +cloud.google.com/go/talent v1.6.5/go.mod h1:Mf5cma696HmE+P2BWJ/ZwYqeJXEeU0UqjHFXVLadEDI= cloud.google.com/go/texttospeech v1.4.0/go.mod h1:FX8HQHA6sEpJ7rCMSfXuzBcysDAuWusNNNvN9FELDd8= cloud.google.com/go/texttospeech v1.5.0/go.mod h1:oKPLhR4n4ZdQqWKURdwxMy0uiTS1xU161C8W57Wkea4= cloud.google.com/go/texttospeech v1.6.0/go.mod h1:YmwmFT8pj1aBblQOI3TfKmwibnsfvhIBzPXcW4EBovc= cloud.google.com/go/texttospeech v1.7.1/go.mod h1:m7QfG5IXxeneGqTapXNxv2ItxP/FS0hCZBwXYqucgSk= +cloud.google.com/go/texttospeech v1.7.2/go.mod h1:VYPT6aTOEl3herQjFHYErTlSZJ4vB00Q2ZTmuVgluD4= +cloud.google.com/go/texttospeech v1.7.3/go.mod h1:Av/zpkcgWfXlDLRYob17lqMstGZ3GqlvJXqKMp2u8so= +cloud.google.com/go/texttospeech v1.7.4/go.mod h1:vgv0002WvR4liGuSd5BJbWy4nDn5Ozco0uJymY5+U74= cloud.google.com/go/tpu v1.3.0/go.mod h1:aJIManG0o20tfDQlRIej44FcwGGl/cD0oiRyMKG19IQ= cloud.google.com/go/tpu v1.4.0/go.mod h1:mjZaX8p0VBgllCzF6wcU2ovUXN9TONFLd7iz227X2Xg= cloud.google.com/go/tpu v1.5.0/go.mod h1:8zVo1rYDFuW2l4yZVY0R0fb/v44xLh3llq7RuV61fPM= cloud.google.com/go/tpu v1.6.1/go.mod h1:sOdcHVIgDEEOKuqUoi6Fq53MKHJAtOwtz0GuKsWSH3E= +cloud.google.com/go/tpu v1.6.2/go.mod h1:NXh3NDwt71TsPZdtGWgAG5ThDfGd32X1mJ2cMaRlVgU= +cloud.google.com/go/tpu v1.6.3/go.mod h1:lxiueqfVMlSToZY1151IaZqp89ELPSrk+3HIQ5HRkbY= +cloud.google.com/go/tpu v1.6.4/go.mod h1:NAm9q3Rq2wIlGnOhpYICNI7+bpBebMJbh0yyp3aNw1Y= cloud.google.com/go/trace v1.3.0/go.mod h1:FFUE83d9Ca57C+K8rDl/Ih8LwOzWIV1krKgxg6N0G28= cloud.google.com/go/trace v1.4.0/go.mod h1:UG0v8UBqzusp+z63o7FK74SdFE+AXpCLdFb1rshXG+Y= cloud.google.com/go/trace v1.8.0/go.mod h1:zH7vcsbAhklH8hWFig58HvxcxyQbaIqMarMg9hn5ECA= cloud.google.com/go/trace v1.9.0/go.mod h1:lOQqpE5IaWY0Ixg7/r2SjixMuc6lfTFeO4QGM4dQWOk= cloud.google.com/go/trace v1.10.1/go.mod h1:gbtL94KE5AJLH3y+WVpfWILmqgc6dXcqgNXdOPAQTYk= +cloud.google.com/go/trace v1.10.2/go.mod h1:NPXemMi6MToRFcSxRl2uDnu/qAlAQ3oULUphcHGh1vA= +cloud.google.com/go/trace v1.10.3/go.mod h1:Ke1bgfc73RV3wUFml+uQp7EsDw4dGaETLxB7Iq/r4CY= +cloud.google.com/go/trace v1.10.4/go.mod h1:Nso99EDIK8Mj5/zmB+iGr9dosS/bzWCJ8wGmE6TXNWY= cloud.google.com/go/translate v1.3.0/go.mod h1:gzMUwRjvOqj5i69y/LYLd8RrNQk+hOmIXTi9+nb3Djs= cloud.google.com/go/translate v1.4.0/go.mod h1:06Dn/ppvLD6WvA5Rhdp029IX2Mi3Mn7fpMRLPvXT5Wg= cloud.google.com/go/translate v1.5.0/go.mod h1:29YDSYveqqpA1CQFD7NQuP49xymq17RXNaUDdc0mNu0= @@ -735,6 +1048,9 @@ cloud.google.com/go/translate v1.7.0/go.mod h1:lMGRudH1pu7I3n3PETiOB2507gf3HnfLV cloud.google.com/go/translate v1.8.1/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= cloud.google.com/go/translate v1.8.2/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= cloud.google.com/go/translate v1.9.0/go.mod h1:d1ZH5aaOA0CNhWeXeC8ujd4tdCFw8XoNWRljklu5RHs= +cloud.google.com/go/translate v1.9.1/go.mod h1:TWIgDZknq2+JD4iRcojgeDtqGEp154HN/uL6hMvylS8= +cloud.google.com/go/translate v1.9.2/go.mod h1:E3Tc6rUTsQkVrXW6avbUhKJSr7ZE3j7zNmqzXKHqRrY= +cloud.google.com/go/translate v1.9.3/go.mod h1:Kbq9RggWsbqZ9W5YpM94Q1Xv4dshw/gr/SHfsl5yCZ0= cloud.google.com/go/video v1.8.0/go.mod h1:sTzKFc0bUSByE8Yoh8X0mn8bMymItVGPfTuUBUyRgxk= cloud.google.com/go/video v1.9.0/go.mod h1:0RhNKFRF5v92f8dQt0yhaHrEuH95m068JYOvLZYnJSw= cloud.google.com/go/video v1.12.0/go.mod h1:MLQew95eTuaNDEGriQdcYn0dTwf9oWiA4uYebxM5kdg= @@ -744,12 +1060,18 @@ cloud.google.com/go/video v1.15.0/go.mod h1:SkgaXwT+lIIAKqWAJfktHT/RbgjSuY6DobxE cloud.google.com/go/video v1.17.1/go.mod h1:9qmqPqw/Ib2tLqaeHgtakU+l5TcJxCJbhFXM7UJjVzU= cloud.google.com/go/video v1.19.0/go.mod h1:9qmqPqw/Ib2tLqaeHgtakU+l5TcJxCJbhFXM7UJjVzU= cloud.google.com/go/video v1.20.0/go.mod h1:U3G3FTnsvAGqglq9LxgqzOiBc/Nt8zis8S+850N2DUM= +cloud.google.com/go/video v1.20.1/go.mod h1:3gJS+iDprnj8SY6pe0SwLeC5BUW80NjhwX7INWEuWGU= +cloud.google.com/go/video v1.20.2/go.mod h1:lrixr5JeKNThsgfM9gqtwb6Okuqzfo4VrY2xynaViTA= +cloud.google.com/go/video v1.20.3/go.mod h1:TnH/mNZKVHeNtpamsSPygSR0iHtvrR/cW1/GDjN5+GU= cloud.google.com/go/videointelligence v1.6.0/go.mod h1:w0DIDlVRKtwPCn/C4iwZIJdvC69yInhW0cfi+p546uU= cloud.google.com/go/videointelligence v1.7.0/go.mod h1:k8pI/1wAhjznARtVT9U1llUaFNPh7muw8QyOUpavru4= cloud.google.com/go/videointelligence v1.8.0/go.mod h1:dIcCn4gVDdS7yte/w+koiXn5dWVplOZkE+xwG9FgK+M= cloud.google.com/go/videointelligence v1.9.0/go.mod h1:29lVRMPDYHikk3v8EdPSaL8Ku+eMzDljjuvRs105XoU= cloud.google.com/go/videointelligence v1.10.0/go.mod h1:LHZngX1liVtUhZvi2uNS0VQuOzNi2TkY1OakiuoUOjU= cloud.google.com/go/videointelligence v1.11.1/go.mod h1:76xn/8InyQHarjTWsBR058SmlPCwQjgcvoW0aZykOvo= +cloud.google.com/go/videointelligence v1.11.2/go.mod h1:ocfIGYtIVmIcWk1DsSGOoDiXca4vaZQII1C85qtoplc= +cloud.google.com/go/videointelligence v1.11.3/go.mod h1:tf0NUaGTjU1iS2KEkGWvO5hRHeCkFK3nPo0/cOZhZAo= +cloud.google.com/go/videointelligence v1.11.4/go.mod h1:kPBMAYsTPFiQxMLmmjpcZUMklJp3nC9+ipJJtprccD8= cloud.google.com/go/vision v1.2.0/go.mod h1:SmNwgObm5DpFBme2xpyOyasvBc1aPdjvMk2bBk0tKD0= cloud.google.com/go/vision/v2 v2.2.0/go.mod h1:uCdV4PpN1S0jyCyq8sIM42v2Y6zOLkZs+4R9LrGYwFo= cloud.google.com/go/vision/v2 v2.3.0/go.mod h1:UO61abBx9QRMFkNBbf1D8B1LXdS2cGiiCRx0vSpZoUo= @@ -758,30 +1080,48 @@ cloud.google.com/go/vision/v2 v2.5.0/go.mod h1:MmaezXOOE+IWa+cS7OhRRLK2cNv1ZL98z cloud.google.com/go/vision/v2 v2.6.0/go.mod h1:158Hes0MvOS9Z/bDMSFpjwsUrZ5fPrdwuyyvKSGAGMY= cloud.google.com/go/vision/v2 v2.7.0/go.mod h1:H89VysHy21avemp6xcf9b9JvZHVehWbET0uT/bcuY/0= cloud.google.com/go/vision/v2 v2.7.2/go.mod h1:jKa8oSYBWhYiXarHPvP4USxYANYUEdEsQrloLjrSwJU= +cloud.google.com/go/vision/v2 v2.7.3/go.mod h1:V0IcLCY7W+hpMKXK1JYE0LV5llEqVmj+UJChjvA1WsM= +cloud.google.com/go/vision/v2 v2.7.4/go.mod h1:ynDKnsDN/0RtqkKxQZ2iatv3Dm9O+HfRb5djl7l4Vvw= +cloud.google.com/go/vision/v2 v2.7.5/go.mod h1:GcviprJLFfK9OLf0z8Gm6lQb6ZFUulvpZws+mm6yPLM= cloud.google.com/go/vmmigration v1.2.0/go.mod h1:IRf0o7myyWFSmVR1ItrBSFLFD/rJkfDCUTO4vLlJvsE= cloud.google.com/go/vmmigration v1.3.0/go.mod h1:oGJ6ZgGPQOFdjHuocGcLqX4lc98YQ7Ygq8YQwHh9A7g= cloud.google.com/go/vmmigration v1.5.0/go.mod h1:E4YQ8q7/4W9gobHjQg4JJSgXXSgY21nA5r8swQV+Xxc= cloud.google.com/go/vmmigration v1.6.0/go.mod h1:bopQ/g4z+8qXzichC7GW1w2MjbErL54rk3/C843CjfY= cloud.google.com/go/vmmigration v1.7.1/go.mod h1:WD+5z7a/IpZ5bKK//YmT9E047AD+rjycCAvyMxGJbro= +cloud.google.com/go/vmmigration v1.7.2/go.mod h1:iA2hVj22sm2LLYXGPT1pB63mXHhrH1m/ruux9TwWLd8= +cloud.google.com/go/vmmigration v1.7.3/go.mod h1:ZCQC7cENwmSWlwyTrZcWivchn78YnFniEQYRWQ65tBo= +cloud.google.com/go/vmmigration v1.7.4/go.mod h1:yBXCmiLaB99hEl/G9ZooNx2GyzgsjKnw5fWcINRgD70= cloud.google.com/go/vmwareengine v0.1.0/go.mod h1:RsdNEf/8UDvKllXhMz5J40XxDrNJNN4sagiox+OI208= cloud.google.com/go/vmwareengine v0.2.2/go.mod h1:sKdctNJxb3KLZkE/6Oui94iw/xs9PRNC2wnNLXsHvH8= cloud.google.com/go/vmwareengine v0.3.0/go.mod h1:wvoyMvNWdIzxMYSpH/R7y2h5h3WFkx6d+1TIsP39WGY= cloud.google.com/go/vmwareengine v0.4.1/go.mod h1:Px64x+BvjPZwWuc4HdmVhoygcXqEkGHXoa7uyfTgSI0= cloud.google.com/go/vmwareengine v1.0.0/go.mod h1:Px64x+BvjPZwWuc4HdmVhoygcXqEkGHXoa7uyfTgSI0= +cloud.google.com/go/vmwareengine v1.0.1/go.mod h1:aT3Xsm5sNx0QShk1Jc1B8OddrxAScYLwzVoaiXfdzzk= +cloud.google.com/go/vmwareengine v1.0.2/go.mod h1:xMSNjIk8/itYrz1JA8nV3Ajg4L4n3N+ugP8JKzk3OaA= +cloud.google.com/go/vmwareengine v1.0.3/go.mod h1:QSpdZ1stlbfKtyt6Iu19M6XRxjmXO+vb5a/R6Fvy2y4= cloud.google.com/go/vpcaccess v1.4.0/go.mod h1:aQHVbTWDYUR1EbTApSVvMq1EnT57ppDmQzZ3imqIk4w= cloud.google.com/go/vpcaccess v1.5.0/go.mod h1:drmg4HLk9NkZpGfCmZ3Tz0Bwnm2+DKqViEpeEpOq0m8= cloud.google.com/go/vpcaccess v1.6.0/go.mod h1:wX2ILaNhe7TlVa4vC5xce1bCnqE3AeH27RV31lnmZes= cloud.google.com/go/vpcaccess v1.7.1/go.mod h1:FogoD46/ZU+JUBX9D606X21EnxiszYi2tArQwLY4SXs= +cloud.google.com/go/vpcaccess v1.7.2/go.mod h1:mmg/MnRHv+3e8FJUjeSibVFvQF1cCy2MsFaFqxeY1HU= +cloud.google.com/go/vpcaccess v1.7.3/go.mod h1:YX4skyfW3NC8vI3Fk+EegJnlYFatA+dXK4o236EUCUc= +cloud.google.com/go/vpcaccess v1.7.4/go.mod h1:lA0KTvhtEOb/VOdnH/gwPuOzGgM+CWsmGu6bb4IoMKk= cloud.google.com/go/webrisk v1.4.0/go.mod h1:Hn8X6Zr+ziE2aNd8SliSDWpEnSS1u4R9+xXZmFiHmGE= cloud.google.com/go/webrisk v1.5.0/go.mod h1:iPG6fr52Tv7sGk0H6qUFzmL3HHZev1htXuWDEEsqMTg= cloud.google.com/go/webrisk v1.6.0/go.mod h1:65sW9V9rOosnc9ZY7A7jsy1zoHS5W9IAXv6dGqhMQMc= cloud.google.com/go/webrisk v1.7.0/go.mod h1:mVMHgEYH0r337nmt1JyLthzMr6YxwN1aAIEc2fTcq7A= cloud.google.com/go/webrisk v1.8.0/go.mod h1:oJPDuamzHXgUc+b8SiHRcVInZQuybnvEW72PqTc7sSg= cloud.google.com/go/webrisk v1.9.1/go.mod h1:4GCmXKcOa2BZcZPn6DCEvE7HypmEJcJkr4mtM+sqYPc= +cloud.google.com/go/webrisk v1.9.2/go.mod h1:pY9kfDgAqxUpDBOrG4w8deLfhvJmejKB0qd/5uQIPBc= +cloud.google.com/go/webrisk v1.9.3/go.mod h1:RUYXe9X/wBDXhVilss7EDLW9ZNa06aowPuinUOPCXH8= +cloud.google.com/go/webrisk v1.9.4/go.mod h1:w7m4Ib4C+OseSr2GL66m0zMBywdrVNTDKsdEsfMl7X0= cloud.google.com/go/websecurityscanner v1.3.0/go.mod h1:uImdKm2wyeXQevQJXeh8Uun/Ym1VqworNDlBXQevGMo= cloud.google.com/go/websecurityscanner v1.4.0/go.mod h1:ebit/Fp0a+FWu5j4JOmJEV8S8CzdTkAS77oDsiSqYWQ= cloud.google.com/go/websecurityscanner v1.5.0/go.mod h1:Y6xdCPy81yi0SQnDY1xdNTNpfY1oAgXUlcfN3B3eSng= cloud.google.com/go/websecurityscanner v1.6.1/go.mod h1:Njgaw3rttgRHXzwCB8kgCYqv5/rGpFCsBOvPbYgszpg= +cloud.google.com/go/websecurityscanner v1.6.2/go.mod h1:7YgjuU5tun7Eg2kpKgGnDuEOXWIrh8x8lWrJT4zfmas= +cloud.google.com/go/websecurityscanner v1.6.3/go.mod h1:x9XANObUFR+83Cya3g/B9M/yoHVqzxPnFtgF8yYGAXw= +cloud.google.com/go/websecurityscanner v1.6.4/go.mod h1:mUiyMQ+dGpPPRkHgknIZeCzSHJ45+fY4F52nZFDHm2o= cloud.google.com/go/workflows v1.6.0/go.mod h1:6t9F5h/unJz41YqfBmqSASJSXccBLtD1Vwf+KmJENM0= cloud.google.com/go/workflows v1.7.0/go.mod h1:JhSrZuVZWuiDfKEFxU0/F1PQjmpnpcoISEXH2bcHC3M= cloud.google.com/go/workflows v1.8.0/go.mod h1:ysGhmEajwZxGn1OhGOGKsTXc5PyxOc0vfKf5Af+to4M= @@ -789,6 +1129,9 @@ cloud.google.com/go/workflows v1.9.0/go.mod h1:ZGkj1aFIOd9c8Gerkjjq7OW7I5+l6cSvT cloud.google.com/go/workflows v1.10.0/go.mod h1:fZ8LmRmZQWacon9UCX1r/g/DfAXx5VcPALq2CxzdePw= cloud.google.com/go/workflows v1.11.1/go.mod h1:Z+t10G1wF7h8LgdY/EmRcQY8ptBD/nvofaL6FqlET6g= cloud.google.com/go/workflows v1.12.0/go.mod h1:PYhSk2b6DhZ508tj8HXKaBh+OFe+xdl0dHF/tJdzPQM= +cloud.google.com/go/workflows v1.12.1/go.mod h1:5A95OhD/edtOhQd/O741NSfIMezNTbCwLM1P1tBRGHM= +cloud.google.com/go/workflows v1.12.2/go.mod h1:+OmBIgNqYJPVggnMo9nqmizW0qEXHhmnAzK/CnBqsHc= +cloud.google.com/go/workflows v1.12.3/go.mod h1:fmOUeeqEwPzIU81foMjTRQIdwQHADi/vEr1cx9R1m5g= dmitri.shuralyov.com/gpu/mtl v0.0.0-20190408044501-666a987793e9/go.mod h1:H6x//7gZCb22OMCxBHrMx7a5I7Hp++hsVxbQ4BYO7hU= gioui.org v0.0.0-20210308172011-57750fc8a0a6/go.mod h1:RSH6KIUZ0p2xy5zHDxgAM4zumjgTw83q2ge/PI+yyw8= git.sr.ht/~sbinet/gg v0.3.1/go.mod h1:KGYtlADtqsqANL9ueOFkWymvzUvLMQllU5Ixo+8v3pc= @@ -832,8 +1175,9 @@ github.com/cncf/xds/go v0.0.0-20220314180256-7f1daf1720fc/go.mod h1:eXthEFrGJvWH github.com/cncf/xds/go v0.0.0-20230105202645-06c439db220b/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230310173818-32f1caf87195/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/cncf/xds/go v0.0.0-20230428030218-4003588d1b74/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= -github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4 h1:/inchEIKaYC1Akx+H+gqO04wryn5h75LSazbRlnya1k= github.com/cncf/xds/go v0.0.0-20230607035331-e9ce68804cb4/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= +github.com/cncf/xds/go v0.0.0-20231109132714-523115ebc101 h1:7To3pQ+pZo0i3dsWEbinPNFs5gPSBOsJtx3wTT94VBY= +github.com/cncf/xds/go v0.0.0-20231109132714-523115ebc101/go.mod h1:eXthEFrGJvWHgFFCl3hGmgk+/aYT6PnTQLykKQRLhEs= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= @@ -935,8 +1279,11 @@ github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/ github.com/google/go-cmp v0.5.6/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= github.com/google/go-cmp v0.5.7/go.mod h1:n+brtR0CgQNWTVd5ZUFpTBC8YFBDLK/h/bpaJ8/DtOE= github.com/google/go-cmp v0.5.8/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= -github.com/google/go-cmp v0.5.9 h1:O2Tfq5qg4qc4AmwVlvv0oLiVAGB7enBSJ2x2DqQFi38= github.com/google/go-cmp v0.5.9/go.mod h1:17dUlkBOakJ0+DkrSSNjCkIjxS6bF9zb3elmeNGIjoY= +github.com/google/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-pkcs11 v0.2.0/go.mod h1:6eQoGcuNJpa7jnd5pMGdkSaQpNDYvPlXWMcjXXThLlY= +github.com/google/go-pkcs11 v0.2.1-0.20230907215043-c6f79328ddf9/go.mod h1:6eQoGcuNJpa7jnd5pMGdkSaQpNDYvPlXWMcjXXThLlY= github.com/google/martian v2.1.0+incompatible/go.mod h1:9I4somxYTbIHy5NJKHRl3wXiIaQGbYVAs8BPL6v8lEs= github.com/google/martian/v3 v3.0.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= github.com/google/martian/v3 v3.1.0/go.mod h1:y5Zk1BBys9G+gd6Jrk0W3cC1+ELVxBWuIGO+w/tUAp0= @@ -961,15 +1308,19 @@ github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm4 github.com/google/s2a-go v0.1.0/go.mod h1:OJpEgntRZo8ugHpF9hkoLJbS5dSI20XZeXJ9JVywLlM= github.com/google/s2a-go v0.1.3/go.mod h1:Ej+mSEMGRnqRzjc7VtF+jdBwYG5fuJfiZ8ELkjEwM0A= github.com/google/s2a-go v0.1.4/go.mod h1:Ej+mSEMGRnqRzjc7VtF+jdBwYG5fuJfiZ8ELkjEwM0A= +github.com/google/s2a-go v0.1.7/go.mod h1:50CgR4k1jNlWBu4UfS4AcfhVe1r6pdZPygJ3R8F0Qdw= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.4.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/enterprise-certificate-proxy v0.0.0-20220520183353-fd19c99a87aa/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.1.0/go.mod h1:17drOmN3MwGY7t0e+Ei9b45FFGA3fBs3x36SsCg1hq8= github.com/googleapis/enterprise-certificate-proxy v0.2.0/go.mod h1:8C0jb7/mgJe/9KK8Lm7X9ctZC2t60YyIpYEI16jx0Qg= github.com/googleapis/enterprise-certificate-proxy v0.2.1/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= github.com/googleapis/enterprise-certificate-proxy v0.2.3/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= github.com/googleapis/enterprise-certificate-proxy v0.2.4/go.mod h1:AwSRAtLfXpU5Nm3pW+v7rGDHp09LsPtGY9MduiEsR9k= +github.com/googleapis/enterprise-certificate-proxy v0.2.5/go.mod h1:RxW0N9901Cko1VOCW3SXCpWP+mlIEkk2tP7jnHy9a3w= +github.com/googleapis/enterprise-certificate-proxy v0.3.2/go.mod h1:VLSiSSBs/ksPL8kq3OBOQ6WRI2QnaFynd1DCjZ62+V0= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= github.com/googleapis/gax-go/v2 v2.1.0/go.mod h1:Q3nei7sK6ybPYH7twZdmQpAd1MKb7pfu6SK+H1/DsU0= @@ -1101,7 +1452,10 @@ golang.org/x/crypto v0.7.0/go.mod h1:pYwdfH91IfpZVANVyUOhSIPZaFoJGxTFbZhFTx+dXZU golang.org/x/crypto v0.9.0/go.mod h1:yrmDGqONDYtNj3tH8X9dzUun2m2lzPa9ngI6/RUPGR0= golang.org/x/crypto v0.10.0/go.mod h1:o4eNf7Ede1fv+hwOwZsTHl9EsPFO6q6ZvYR8vYfY45I= golang.org/x/crypto v0.11.0/go.mod h1:xgJhtzW8F9jGdVFWZESrid1U1bjeNy4zgy5cRr/CIio= +golang.org/x/crypto v0.12.0/go.mod h1:NF0Gs7EO5K4qLn+Ylc+fih8BSTeIjAP05siRnAh98yw= +golang.org/x/crypto v0.13.0/go.mod h1:y6Z2r+Rw4iayiXXAIxJIDAJ1zMW4yaTpebo8fPOliYc= golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4= +golang.org/x/crypto v0.15.0/go.mod h1:4ChreQoLWfG3xLDer1WdlH5NdlQ3+mwnQq1YTKY+72g= golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20180807140117-3d87b88a115f/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA= @@ -1223,9 +1577,11 @@ golang.org/x/net v0.9.0/go.mod h1:d48xBJpPfHeWQsugry2m+kC02ZBRGRgulfHnEXEuWns= golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg= golang.org/x/net v0.11.0/go.mod h1:2L/ixqYpgIVXmeoSA/4Lu7BzTG4KIyPIryS4IsOd1oQ= golang.org/x/net v0.12.0/go.mod h1:zEVYFnQC7m/vmpQFELhcD1EWkZlX69l4oqgmer6hfKA= +golang.org/x/net v0.14.0/go.mod h1:PpSgVXXLK0OxS0F31C1/tv6XNguvCrnXIDrFMspZIUI= golang.org/x/net v0.16.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= -golang.org/x/net v0.17.0 h1:pVaXccu2ozPjCXewfr1S7xza/zcXTity9cCdXQYSjIM= golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE= +golang.org/x/net v0.18.0 h1:mIYleuAkSbHh0tCv7RvjL3F6ZVbLjq4+R7zbOn3Kokg= +golang.org/x/net v0.18.0/go.mod h1:/czyP5RqHAH4odGYxBJ1qz0+CE5WZ+2j1YgoEo8F2jQ= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -1257,7 +1613,9 @@ golang.org/x/oauth2 v0.6.0/go.mod h1:ycmewcwgD4Rpr3eZJLSB4Kyyljb3qDh40vJ8STE5HKw golang.org/x/oauth2 v0.7.0/go.mod h1:hPLQkd9LyjfXTiRohC/41GhcFqxisoUQ99sCUOHO9x4= golang.org/x/oauth2 v0.8.0/go.mod h1:yr7u4HXZRm1R1kBWqr/xKNqewf0plRYoB7sla+BCIXE= golang.org/x/oauth2 v0.10.0/go.mod h1:kTpgurOux7LqtuxjuyZa4Gj2gdezIt/jQtGnNFfypQI= +golang.org/x/oauth2 v0.11.0/go.mod h1:LdF7O/8bLR/qWK9DrpXmbHLTouvRHK0SgJl0GmDBchk= golang.org/x/oauth2 v0.13.0/go.mod h1:/JMhi4ZRXAf4HG9LiNmxvk+45+96RUlVThiH8FzNBn0= +golang.org/x/oauth2 v0.14.0/go.mod h1:lAtNWgaWfL4cm7j2OV8TxGi9Qb7ECORx8DktCY74OwM= golang.org/x/sync v0.0.0-20180314180146-1d60e4601c6f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181108010431-42b317875d0f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20181221193216-37e7f081c4d4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= @@ -1277,6 +1635,7 @@ golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.2.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= golang.org/x/sync v0.4.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y= +golang.org/x/sync v0.5.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/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-20190312061237-fead79001313/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= @@ -1358,8 +1717,11 @@ golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.9.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.10.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.13.0 h1:Af8nKPmuFypiUBjVoU9V20FiaFXOcuZI21p0ycVYYGE= +golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.12.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.14.0 h1:Vz7Qs629MkJkGyHxUlRHizWJRG2j8fbQKjELVSNhy7Q= +golang.org/x/sys v0.14.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.1.0/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= @@ -1372,7 +1734,10 @@ golang.org/x/term v0.7.0/go.mod h1:P32HKFT3hSsZrRxla30E9HqToFYAQPCMs/zFMBUFqPY= golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo= golang.org/x/term v0.9.0/go.mod h1:M6DEAAIenWoTxdKrOltXcmDY3rSplQUkrvaDU5FcQyo= golang.org/x/term v0.10.0/go.mod h1:lpqdcUyK/oCiQxvxVrppt5ggO2KCZ5QblwqPnfZ6d5o= +golang.org/x/term v0.11.0/go.mod h1:zC9APTIj3jG3FdV/Ons+XE1riIZXG4aZ4GTHiPZJPIU= +golang.org/x/term v0.12.0/go.mod h1:owVbMEjm3cBLCHdkQu9b1opXd4ETQWc3BhuQGKgXgvU= golang.org/x/term v0.13.0/go.mod h1:LTmsnFJwVN6bCy1rVCoS+qHT1HhALEFxKncY3WNNh4U= +golang.org/x/term v0.14.0/go.mod h1:TySc+nGkYR6qt8km8wUhuFRTVSMIX3XPR58y2lC8vww= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/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.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -1391,8 +1756,10 @@ golang.org/x/text v0.8.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= golang.org/x/text v0.10.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.11.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= -golang.org/x/text v0.13.0 h1:ablQoSUd0tRdKxZewP80B+BaqeKJuVhuRxj/dkrun3k= +golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= +golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ= +golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -1542,6 +1909,8 @@ google.golang.org/api v0.124.0/go.mod h1:xu2HQurE5gi/3t1aFCvhPD781p0a3p11sdunTJ2 google.golang.org/api v0.125.0/go.mod h1:mBwVAtz+87bEN6CbA1GtZPDOqY2R5ONPqJeIlvyo4Aw= google.golang.org/api v0.126.0/go.mod h1:mBwVAtz+87bEN6CbA1GtZPDOqY2R5ONPqJeIlvyo4Aw= google.golang.org/api v0.128.0/go.mod h1:Y611qgqaE92On/7g65MQgxYul3c0rEB894kniWLY750= +google.golang.org/api v0.139.0/go.mod h1:CVagp6Eekz9CjGZ718Z+sloknzkDJE7Vc1Ckj9+viBk= +google.golang.org/api v0.149.0/go.mod h1:Mwn1B7JTXrzXtnvmzQE2BD6bYZQ8DShKZDZbeN9I7qI= google.golang.org/appengine v1.1.0/go.mod h1:EbEs0AVv82hx2wNQdGPgUI5lhzA/G0D9YwlJXL52JkM= google.golang.org/appengine v1.4.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= google.golang.org/appengine v1.5.0/go.mod h1:xpcJRLb0r/rnEns0DIKYYv+WjYCduHsrkT7/EB5XEv4= @@ -1693,10 +2062,15 @@ google.golang.org/genproto v0.0.0-20230711160842-782d3b101e98/go.mod h1:S7mY02Oq google.golang.org/genproto v0.0.0-20230726155614-23370e0ffb3e/go.mod h1:0ggbjUrZYpy1q+ANUS30SEoGZ53cdfwtbuG7Ptgy108= google.golang.org/genproto v0.0.0-20230803162519-f966b187b2e5/go.mod h1:oH/ZOT02u4kWEp7oYBGYFFkCdKS/uYR9Z7+0/xuuFp8= google.golang.org/genproto v0.0.0-20230821184602-ccc8af3d0e93/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= +google.golang.org/genproto v0.0.0-20230822172742-b8732ec3820d/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= google.golang.org/genproto v0.0.0-20230913181813-007df8e322eb/go.mod h1:yZTlhN0tQnXo3h00fuXNCxJdLdIdnVFVBaRJ5LWBbw4= google.golang.org/genproto v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:CCviP9RmpZ1mxVr8MUjCnSiY09IbAXZxhLE6EhHIdPU= -google.golang.org/genproto v0.0.0-20231002182017-d307bd883b97 h1:SeZZZx0cP0fqUyA+oRzP9k7cSwJlvDFiROO72uwD6i0= google.golang.org/genproto v0.0.0-20231002182017-d307bd883b97/go.mod h1:t1VqOqqvce95G3hIDCT5FeO3YUc6Q4Oe24L/+rNMxRk= +google.golang.org/genproto v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:EMfReVxb80Dq1hhioy0sOsY9jCE46YDgHlJ7fWVUWRE= +google.golang.org/genproto v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:CgAqfJo+Xmu0GwA0411Ht3OU3OntXwsGmrmjI8ioGXI= +google.golang.org/genproto v0.0.0-20231030173426-d783a09b4405/go.mod h1:3WDQMjmJk36UQhjQ89emUzb1mdaHcPeeAh4SCBKznB4= +google.golang.org/genproto v0.0.0-20231106174013-bbf56f31fb17 h1:wpZ8pe2x1Q3f2KyT5f8oP/fa9rHAKgFPr/HZdNuS+PQ= +google.golang.org/genproto v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:J7XzRzVy1+IPwWHZUzoD0IccYZIrXILAQpc+Qy9CMhY= google.golang.org/genproto/googleapis/api v0.0.0-20230525234020-1aefcd67740a/go.mod h1:ts19tUU+Z0ZShN1y3aPyq2+O3d5FUNNgT6FtOzmrNn8= google.golang.org/genproto/googleapis/api v0.0.0-20230525234035-dd9d682886f9/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= google.golang.org/genproto/googleapis/api v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:vHYtlOoi6TsQ3Uk2yxR7NI5z8uoV+3pZtR4jmHIkRig= @@ -1706,10 +2080,17 @@ google.golang.org/genproto/googleapis/api v0.0.0-20230706204954-ccb25ca9f130/go. google.golang.org/genproto/googleapis/api v0.0.0-20230711160842-782d3b101e98/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ= google.golang.org/genproto/googleapis/api v0.0.0-20230726155614-23370e0ffb3e/go.mod h1:rsr7RhLuwsDKL7RmgDDCUc6yaGr1iqceVb5Wv6f6YvQ= google.golang.org/genproto/googleapis/api v0.0.0-20230803162519-f966b187b2e5/go.mod h1:5DZzOUPCLYL3mNkQ0ms0F3EuUNZ7py1Bqeq6sxzI7/Q= +google.golang.org/genproto/googleapis/api v0.0.0-20230822172742-b8732ec3820d/go.mod h1:KjSP20unUpOx5kyQUFa7k4OJg0qeJ7DEZflGDu2p6Bk= google.golang.org/genproto/googleapis/api v0.0.0-20230913181813-007df8e322eb/go.mod h1:KjSP20unUpOx5kyQUFa7k4OJg0qeJ7DEZflGDu2p6Bk= google.golang.org/genproto/googleapis/api v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:RdyHbowztCGQySiCvQPgWQWgWhGnouTdCflKoDBt32U= google.golang.org/genproto/googleapis/api v0.0.0-20231002182017-d307bd883b97/go.mod h1:iargEX0SFPm3xcfMI0d1domjg0ZF4Aa0p2awqyxhvF0= +google.golang.org/genproto/googleapis/api v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:SUBoKXbI1Efip18FClrQVGjWcyd0QZd8KkvdP34t7ww= +google.golang.org/genproto/googleapis/api v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:IBQ646DjkDkvUIsVq/cc03FUFQ9wbZu7yE396YcL870= +google.golang.org/genproto/googleapis/api v0.0.0-20231030173426-d783a09b4405/go.mod h1:oT32Z4o8Zv2xPQTg0pbVaPr0MPOH6f14RgXt7zfIpwg= +google.golang.org/genproto/googleapis/api v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:0xJLfVdJqpAPl8tDg1ujOCGzx6LFLttXT5NhllGOXY4= google.golang.org/genproto/googleapis/bytestream v0.0.0-20230530153820-e85fd2cbaebc/go.mod h1:ylj+BE99M198VPbBh6A8d9n3w8fChvyLK3wwBOjXBFA= +google.golang.org/genproto/googleapis/bytestream v0.0.0-20230807174057-1744710a1577/go.mod h1:NjCQG/D8JandXxM57PZbAJL1DCNL6EypA0vPPwfsc7c= +google.golang.org/genproto/googleapis/bytestream v0.0.0-20231030173426-d783a09b4405/go.mod h1:GRUCuLdzVqZte8+Dl/D4N25yLzcGqqWaYkeVOwulFqw= google.golang.org/genproto/googleapis/rpc v0.0.0-20230525234015-3fc162c6f38a/go.mod h1:xURIpW9ES5+/GZhnV6beoEtxQrnkRGIfP5VQG2tCBLc= google.golang.org/genproto/googleapis/rpc v0.0.0-20230525234030-28d5490b6b19/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= google.golang.org/genproto/googleapis/rpc v0.0.0-20230526203410-71b5a4ffd15e/go.mod h1:66JfowdXAEgad5O9NnYcsNPLCPZJD++2L9X0PCMODrA= @@ -1719,10 +2100,15 @@ google.golang.org/genproto/googleapis/rpc v0.0.0-20230706204954-ccb25ca9f130/go. google.golang.org/genproto/googleapis/rpc v0.0.0-20230711160842-782d3b101e98/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM= google.golang.org/genproto/googleapis/rpc v0.0.0-20230731190214-cbb8c96f2d6d/go.mod h1:TUfxEVdsvPg18p6AslUXFoLdpED4oBnGwyqk3dV1XzM= google.golang.org/genproto/googleapis/rpc v0.0.0-20230803162519-f966b187b2e5/go.mod h1:zBEcrKX2ZOcEkHWxBPAIvYUWOKKMIhYcmNiUIu2ji3I= +google.golang.org/genproto/googleapis/rpc v0.0.0-20230822172742-b8732ec3820d/go.mod h1:+Bk1OCOj40wS2hwAMA+aCW9ypzm63QTBBHp6lQ3p+9M= google.golang.org/genproto/googleapis/rpc v0.0.0-20230920183334-c177e329c48b/go.mod h1:+Bk1OCOj40wS2hwAMA+aCW9ypzm63QTBBHp6lQ3p+9M= google.golang.org/genproto/googleapis/rpc v0.0.0-20230920204549-e6e6cdab5c13/go.mod h1:KSqppvjFjtoCI+KGd4PELB0qLNxdJHRGqRI09mB6pQA= -google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97 h1:6GQBEOdGkX6MMTLT9V+TjtIRZCw9VPD5Z+yHY9wMgS0= google.golang.org/genproto/googleapis/rpc v0.0.0-20231002182017-d307bd883b97/go.mod h1:v7nGkzlmW8P3n/bKmWBn2WpBjpOEx8Q6gMueudAmKfY= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231012201019-e917dd12ba7a/go.mod h1:4cYg8o5yUbm77w8ZX00LhMVNl/YVBFJRYWDc0uYWMs0= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231016165738-49dd2c1f3d0b/go.mod h1:swOH3j0KzcDDgGUWr+SNpyTen5YrXjS3eyPzFYKc6lc= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231030173426-d783a09b4405/go.mod h1:67X1fPuzjcrkymZzZV1vvkFeTn2Rvc6lYF9MYFGCcwE= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17 h1:Jyp0Hsi0bmHXG6k9eATXoYtjd6e2UzZ1SCn/wIupY14= +google.golang.org/genproto/googleapis/rpc v0.0.0-20231106174013-bbf56f31fb17/go.mod h1:oQ5rr10WTTMvP4A36n8JpR1OrO1BEiV4f78CneXZxkA= google.golang.org/grpc v1.19.0/go.mod h1:mqu4LbDTu4XGKhr4mRzUsmM4RtVoemTSY81AxZiDr8c= google.golang.org/grpc v1.20.1/go.mod h1:10oTOabMzJvdu6/UiuZezV6QK5dSlG84ov/aaiqXj38= google.golang.org/grpc v1.21.1/go.mod h1:oYelfM1adQP15Ek0mdvEgi9Df8B9CZIaU1084ijfRaM= @@ -1768,9 +2154,11 @@ google.golang.org/grpc v1.55.0/go.mod h1:iYEXKGkEBhg1PjZQvoYEVPTDkHo1/bjTnfwTeGO google.golang.org/grpc v1.56.1/go.mod h1:I9bI3vqKfayGqPUAwGdOSu7kt6oIJLixfffKrpXqQ9s= google.golang.org/grpc v1.56.2/go.mod h1:I9bI3vqKfayGqPUAwGdOSu7kt6oIJLixfffKrpXqQ9s= google.golang.org/grpc v1.57.0/go.mod h1:Sd+9RMTACXwmub0zcNY2c4arhtrbBYD1AUHI/dt16Mo= +google.golang.org/grpc v1.58.2/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0= google.golang.org/grpc v1.58.3/go.mod h1:tgX3ZQDlNJGU96V6yHh1T/JeoBQ2TXdr43YbYSsCJk0= -google.golang.org/grpc v1.60.1 h1:26+wFr+cNqSGFcOXcabYC0lUVJVRa2Sb2ortSK7VrEU= -google.golang.org/grpc v1.60.1/go.mod h1:OlCHIeLYqSSsLi6i49B5QGdzaMZK9+M7LXN2FKz4eGM= +google.golang.org/grpc v1.59.0/go.mod h1:aUPDwccQo6OTjy7Hct4AfBPD1GptF4fyUjIkQ9YtF98= +google.golang.org/grpc v1.61.0 h1:TOvOcuXn30kRao+gfcvsebNEa5iZIiLkisYEkf7R7o0= +google.golang.org/grpc v1.61.0/go.mod h1:VUbo7IFqmF1QtCAstipjG0GIoq49KvMe9+h1jFLBNJs= google.golang.org/grpc/cmd/protoc-gen-go-grpc v1.1.0/go.mod h1:6Kw0yEErY5E/yWrBtf03jp27GLLJujG4z/JK95pnjjw= google.golang.org/protobuf v0.0.0-20200109180630-ec00e32a8dfd/go.mod h1:DFci5gLYBciE7Vtevhsrf46CRTquxDuWsQurQQe4oz8= google.golang.org/protobuf v0.0.0-20200221191635-4d8936d0db64/go.mod h1:kwYJMbMJ01Woi6D6+Kah6886xMZcty6N08ah7+eCXa0= diff --git a/examples/local_ratelimit/Dockerfile-nginx b/examples/local_ratelimit/Dockerfile-nginx index 99d0c568606db..ebda5b942b5a4 100644 --- a/examples/local_ratelimit/Dockerfile-nginx +++ b/examples/local_ratelimit/Dockerfile-nginx @@ -1 +1 @@ -FROM nginx@sha256:4c0fdaa8b6341bfdeca5f18f7837462c80cff90527ee35ef185571e1c327beac +FROM nginx@sha256:5f44022eab9198d75939d9eaa5341bc077eca16fa51d4ef32d33f1bd4c8cbe7d diff --git a/examples/lua-cluster-specifier/docker-compose.yaml b/examples/lua-cluster-specifier/docker-compose.yaml index 904b030f84174..8faf8df65a2cc 100644 --- a/examples/lua-cluster-specifier/docker-compose.yaml +++ b/examples/lua-cluster-specifier/docker-compose.yaml @@ -5,10 +5,4 @@ services: context: . dockerfile: ../shared/envoy/Dockerfile ports: - - "${PORT_PROXY:-8000}:8000" - - web_service: - build: - context: ../shared/echo - ports: - - "${PORT_WEB:-8080}:8080" + - "${PORT_PROXY:-10000}:10000" diff --git a/examples/lua-cluster-specifier/envoy.yaml b/examples/lua-cluster-specifier/envoy.yaml index 058e281793959..178ced586715e 100644 --- a/examples/lua-cluster-specifier/envoy.yaml +++ b/examples/lua-cluster-specifier/envoy.yaml @@ -1,10 +1,9 @@ static_resources: listeners: - - name: main - address: + - address: socket_address: address: 0.0.0.0 - port_value: 8000 + port_value: 10000 filter_chains: - filters: - name: envoy.filters.network.http_connection_manager @@ -13,9 +12,9 @@ static_resources: stat_prefix: ingress_http codec_type: AUTO route_config: - name: local_route + name: example_route virtual_hosts: - - name: local_service + - name: example_hosts domains: - "*" routes: @@ -32,23 +31,22 @@ static_resources: function envoy_on_route(route_handle) local header_value = route_handle:headers():get("header_key") if header_value == "fake" then - return "fake_service" + return "fake_cluster" end - return "web_service" + return "example_cluster" end - default_cluster: web_service - + default_cluster: example_cluster http_filters: - name: envoy.filters.http.router typed_config: "@type": type.googleapis.com/envoy.extensions.filters.http.router.v3.Router clusters: - - name: web_service - type: STRICT_DNS # static + - name: example_cluster + type: STRICT_DNS lb_policy: ROUND_ROBIN load_assignment: - cluster_name: web_service + cluster_name: example_cluster_service endpoints: - lb_endpoints: - endpoint: diff --git a/examples/mysql/Dockerfile-mysql b/examples/mysql/Dockerfile-mysql index bd3ba96617372..ffaff3501c025 100644 --- a/examples/mysql/Dockerfile-mysql +++ b/examples/mysql/Dockerfile-mysql @@ -1 +1 @@ -FROM mysql:8.2.0@sha256:4ef30b2c11a3366d7bb9ad95c70c0782ae435df52d046553ed931621ea36ffa5 +FROM mysql:8.3.0@sha256:d7c20c5ba268c558f4fac62977f8c7125bde0630ff8946b08dde44135ef40df3 diff --git a/examples/opentelemetry/Dockerfile-opentelemetry b/examples/opentelemetry/Dockerfile-opentelemetry index 9153a09d7003b..1462bd33651f3 100644 --- a/examples/opentelemetry/Dockerfile-opentelemetry +++ b/examples/opentelemetry/Dockerfile-opentelemetry @@ -1,7 +1,7 @@ -FROM alpine:3.19@sha256:51b67269f354137895d43f3b3d810bfacd3945438e94dc5ac55fdac340352f48 as otelc_curl +FROM alpine:3.19@sha256:c5b1261d6d3e43071626931fc004f70149baeba2c8ec672bd4f27761f8e1ad6b as otelc_curl RUN apk --update add curl -FROM otel/opentelemetry-collector:latest@sha256:92f6e2efd014152bee26f8324e3a511980b512a36d8793d3fee708715caaa6c0 +FROM otel/opentelemetry-collector:latest@sha256:2cfa5eb469eaf226c1fd62e6e3d38f94a8550951f49136fef3c78f38c211415e COPY --from=otelc_curl / / diff --git a/examples/redis/Dockerfile-redis b/examples/redis/Dockerfile-redis index e03c15acc0ac8..9eb8e22d575cb 100644 --- a/examples/redis/Dockerfile-redis +++ b/examples/redis/Dockerfile-redis @@ -1 +1 @@ -FROM redis@sha256:b5ddcd52d425a8e354696c022f392fe45fca928f68d6289e6bb4a709c3a74668 +FROM redis@sha256:f44e91787b843612a3878d8d8fae227b9db63f471214314f5b2e73576ca633d0 diff --git a/examples/shared/golang/Dockerfile b/examples/shared/golang/Dockerfile index 6c26405d2f68c..35ea973949fff 100644 --- a/examples/shared/golang/Dockerfile +++ b/examples/shared/golang/Dockerfile @@ -1,9 +1,9 @@ -FROM debian:bookworm-slim@sha256:f4a83aa865a2b4a064ff142aa91c713180df9fcb86ce676b5de2981029379c37 as os-base +FROM debian:bookworm-slim@sha256:7802002798b0e351323ed2357ae6dc5a8c4d0a05a57e7f4d8f97136151d3d603 as os-base RUN rm -f /etc/apt/apt.conf.d/docker-clean \ && echo 'Binary::apt::APT::Keep-Downloaded-Packages "true";' | tee /etc/apt/apt.conf.d/keep-cache -FROM golang:1.21.6-bookworm@sha256:cbee5d27649be9e3a48d4d152838901c65d7f8e803f4cc46b53699dd215b555f as golang-base +FROM golang:1.21.6-bookworm@sha256:3efef61ff1d99c8a90845100e2a7e934b4a5d11b639075dc605ff53c141044fc as golang-base FROM golang-base as golang-control-plane-builder diff --git a/examples/shared/jaeger/Dockerfile b/examples/shared/jaeger/Dockerfile index 64b4e94e6dbeb..ed92ce6e60e2b 100644 --- a/examples/shared/jaeger/Dockerfile +++ b/examples/shared/jaeger/Dockerfile @@ -1,4 +1,4 @@ -FROM jaegertracing/all-in-one@sha256:040857c9c22ac25775b0213e4127b3a94521f8232c2ef3597402b812ab1ef3dd +FROM jaegertracing/all-in-one@sha256:ead304a221a110b26b54bed36129ee48eaac67f1b68b733b40dc9fde8039c513 HEALTHCHECK \ --interval=1s \ --timeout=1s \ diff --git a/examples/shared/node/Dockerfile b/examples/shared/node/Dockerfile index ff9c05d00b92a..8035e9b802781 100644 --- a/examples/shared/node/Dockerfile +++ b/examples/shared/node/Dockerfile @@ -1,4 +1,4 @@ -FROM node:21.5-bookworm-slim@sha256:9df21707e27d98ee83e079fa47c5c0c5fba6c768e566643f8944b00b00afc4a2 as node-base +FROM node:21.6-bookworm-slim@sha256:5792ef22332ab69f8149ca3f1b50519c97e220d8b0d97ca4d424963f34593fc4 as node-base FROM node-base as node-http-auth diff --git a/examples/shared/postgres/Dockerfile b/examples/shared/postgres/Dockerfile index 78aea83b1df9a..e3fd85af7e87b 100644 --- a/examples/shared/postgres/Dockerfile +++ b/examples/shared/postgres/Dockerfile @@ -1,3 +1,3 @@ -FROM postgres:latest@sha256:49c276fa02e3d61bd9b8db81dfb4784fe814f50f778dce5980a03817438293e3 +FROM postgres:latest@sha256:4d1b17af6f66b852ee3a721f6691a2ca7352f9d28f570a6a48cee4ebe646b2fd COPY docker-healthcheck.sh /usr/local/bin/ HEALTHCHECK CMD ["docker-healthcheck.sh"] diff --git a/examples/shared/python/aiohttp/requirements.txt b/examples/shared/python/aiohttp/requirements.txt index bf302ca82db1b..64181dc33b9a2 100644 --- a/examples/shared/python/aiohttp/requirements.txt +++ b/examples/shared/python/aiohttp/requirements.txt @@ -4,83 +4,83 @@ # # pip-compile --allow-unsafe --generate-hashes requirements.in # -aiohttp==3.9.1 \ - --hash=sha256:02ab6006ec3c3463b528374c4cdce86434e7b89ad355e7bf29e2f16b46c7dd6f \ - --hash=sha256:04fa38875e53eb7e354ece1607b1d2fdee2d175ea4e4d745f6ec9f751fe20c7c \ - --hash=sha256:0b0a6a36ed7e164c6df1e18ee47afbd1990ce47cb428739d6c99aaabfaf1b3af \ - --hash=sha256:0d406b01a9f5a7e232d1b0d161b40c05275ffbcbd772dc18c1d5a570961a1ca4 \ - --hash=sha256:0e49b08eafa4f5707ecfb321ab9592717a319e37938e301d462f79b4e860c32a \ - --hash=sha256:0e7ba7ff228c0d9a2cd66194e90f2bca6e0abca810b786901a569c0de082f489 \ - --hash=sha256:11cb254e397a82efb1805d12561e80124928e04e9c4483587ce7390b3866d213 \ - --hash=sha256:11ff168d752cb41e8492817e10fb4f85828f6a0142b9726a30c27c35a1835f01 \ - --hash=sha256:176df045597e674fa950bf5ae536be85699e04cea68fa3a616cf75e413737eb5 \ - --hash=sha256:219a16763dc0294842188ac8a12262b5671817042b35d45e44fd0a697d8c8361 \ - --hash=sha256:22698f01ff5653fe66d16ffb7658f582a0ac084d7da1323e39fd9eab326a1f26 \ - --hash=sha256:237533179d9747080bcaad4d02083ce295c0d2eab3e9e8ce103411a4312991a0 \ - --hash=sha256:289ba9ae8e88d0ba16062ecf02dd730b34186ea3b1e7489046fc338bdc3361c4 \ - --hash=sha256:2c59e0076ea31c08553e868cec02d22191c086f00b44610f8ab7363a11a5d9d8 \ - --hash=sha256:2c9376e2b09895c8ca8b95362283365eb5c03bdc8428ade80a864160605715f1 \ - --hash=sha256:3135713c5562731ee18f58d3ad1bf41e1d8883eb68b363f2ffde5b2ea4b84cc7 \ - --hash=sha256:3b9c7426923bb7bd66d409da46c41e3fb40f5caf679da624439b9eba92043fa6 \ - --hash=sha256:3c0266cd6f005e99f3f51e583012de2778e65af6b73860038b968a0a8888487a \ - --hash=sha256:41473de252e1797c2d2293804e389a6d6986ef37cbb4a25208de537ae32141dd \ - --hash=sha256:4831df72b053b1eed31eb00a2e1aff6896fb4485301d4ccb208cac264b648db4 \ - --hash=sha256:49f0c1b3c2842556e5de35f122fc0f0b721334ceb6e78c3719693364d4af8499 \ - --hash=sha256:4b4c452d0190c5a820d3f5c0f3cd8a28ace48c54053e24da9d6041bf81113183 \ - --hash=sha256:4ee8caa925aebc1e64e98432d78ea8de67b2272252b0a931d2ac3bd876ad5544 \ - --hash=sha256:500f1c59906cd142d452074f3811614be04819a38ae2b3239a48b82649c08821 \ - --hash=sha256:5216b6082c624b55cfe79af5d538e499cd5f5b976820eac31951fb4325974501 \ - --hash=sha256:54311eb54f3a0c45efb9ed0d0a8f43d1bc6060d773f6973efd90037a51cd0a3f \ - --hash=sha256:54631fb69a6e44b2ba522f7c22a6fb2667a02fd97d636048478db2fd8c4e98fe \ - --hash=sha256:565760d6812b8d78d416c3c7cfdf5362fbe0d0d25b82fed75d0d29e18d7fc30f \ - --hash=sha256:598db66eaf2e04aa0c8900a63b0101fdc5e6b8a7ddd805c56d86efb54eb66672 \ - --hash=sha256:5c4fa235d534b3547184831c624c0b7c1e262cd1de847d95085ec94c16fddcd5 \ - --hash=sha256:69985d50a2b6f709412d944ffb2e97d0be154ea90600b7a921f95a87d6f108a2 \ - --hash=sha256:69da0f3ed3496808e8cbc5123a866c41c12c15baaaead96d256477edf168eb57 \ - --hash=sha256:6c93b7c2e52061f0925c3382d5cb8980e40f91c989563d3d32ca280069fd6a87 \ - --hash=sha256:70907533db712f7aa791effb38efa96f044ce3d4e850e2d7691abd759f4f0ae0 \ - --hash=sha256:81b77f868814346662c96ab36b875d7814ebf82340d3284a31681085c051320f \ - --hash=sha256:82eefaf1a996060602f3cc1112d93ba8b201dbf5d8fd9611227de2003dddb3b7 \ - --hash=sha256:85c3e3c9cb1d480e0b9a64c658cd66b3cfb8e721636ab8b0e746e2d79a7a9eed \ - --hash=sha256:8a22a34bc594d9d24621091d1b91511001a7eea91d6652ea495ce06e27381f70 \ - --hash=sha256:8cef8710fb849d97c533f259103f09bac167a008d7131d7b2b0e3a33269185c0 \ - --hash=sha256:8d44e7bf06b0c0a70a20f9100af9fcfd7f6d9d3913e37754c12d424179b4e48f \ - --hash=sha256:8d7f98fde213f74561be1d6d3fa353656197f75d4edfbb3d94c9eb9b0fc47f5d \ - --hash=sha256:8d8e4450e7fe24d86e86b23cc209e0023177b6d59502e33807b732d2deb6975f \ - --hash=sha256:8fc49a87ac269d4529da45871e2ffb6874e87779c3d0e2ccd813c0899221239d \ - --hash=sha256:90ec72d231169b4b8d6085be13023ece8fa9b1bb495e4398d847e25218e0f431 \ - --hash=sha256:91c742ca59045dce7ba76cab6e223e41d2c70d79e82c284a96411f8645e2afff \ - --hash=sha256:9b05d33ff8e6b269e30a7957bd3244ffbce2a7a35a81b81c382629b80af1a8bf \ - --hash=sha256:9b05d5cbe9dafcdc733262c3a99ccf63d2f7ce02543620d2bd8db4d4f7a22f83 \ - --hash=sha256:9c5857612c9813796960c00767645cb5da815af16dafb32d70c72a8390bbf690 \ - --hash=sha256:a34086c5cc285be878622e0a6ab897a986a6e8bf5b67ecb377015f06ed316587 \ - --hash=sha256:ab221850108a4a063c5b8a70f00dd7a1975e5a1713f87f4ab26a46e5feac5a0e \ - --hash=sha256:b796b44111f0cab6bbf66214186e44734b5baab949cb5fb56154142a92989aeb \ - --hash=sha256:b8c3a67eb87394386847d188996920f33b01b32155f0a94f36ca0e0c635bf3e3 \ - --hash=sha256:bcb6532b9814ea7c5a6a3299747c49de30e84472fa72821b07f5a9818bce0f66 \ - --hash=sha256:bcc0ea8d5b74a41b621ad4a13d96c36079c81628ccc0b30cfb1603e3dfa3a014 \ - --hash=sha256:bea94403a21eb94c93386d559bce297381609153e418a3ffc7d6bf772f59cc35 \ - --hash=sha256:bff7e2811814fa2271be95ab6e84c9436d027a0e59665de60edf44e529a42c1f \ - --hash=sha256:c72444d17777865734aa1a4d167794c34b63e5883abb90356a0364a28904e6c0 \ - --hash=sha256:c7b5d5d64e2a14e35a9240b33b89389e0035e6de8dbb7ffa50d10d8b65c57449 \ - --hash=sha256:c7e939f1ae428a86e4abbb9a7c4732bf4706048818dfd979e5e2839ce0159f23 \ - --hash=sha256:c88a15f272a0ad3d7773cf3a37cc7b7d077cbfc8e331675cf1346e849d97a4e5 \ - --hash=sha256:c9110c06eaaac7e1f5562caf481f18ccf8f6fdf4c3323feab28a93d34cc646bd \ - --hash=sha256:ca7ca5abfbfe8d39e653870fbe8d7710be7a857f8a8386fc9de1aae2e02ce7e4 \ - --hash=sha256:cae4c0c2ca800c793cae07ef3d40794625471040a87e1ba392039639ad61ab5b \ - --hash=sha256:cdefe289681507187e375a5064c7599f52c40343a8701761c802c1853a504558 \ - --hash=sha256:cf2a0ac0615842b849f40c4d7f304986a242f1e68286dbf3bd7a835e4f83acfd \ - --hash=sha256:cfeadf42840c1e870dc2042a232a8748e75a36b52d78968cda6736de55582766 \ - --hash=sha256:d737e69d193dac7296365a6dcb73bbbf53bb760ab25a3727716bbd42022e8d7a \ - --hash=sha256:d7481f581251bb5558ba9f635db70908819caa221fc79ee52a7f58392778c636 \ - --hash=sha256:df9cf74b9bc03d586fc53ba470828d7b77ce51b0582d1d0b5b2fb673c0baa32d \ - --hash=sha256:e1f80197f8b0b846a8d5cf7b7ec6084493950d0882cc5537fb7b96a69e3c8590 \ - --hash=sha256:ecca113f19d5e74048c001934045a2b9368d77b0b17691d905af18bd1c21275e \ - --hash=sha256:ee2527134f95e106cc1653e9ac78846f3a2ec1004cf20ef4e02038035a74544d \ - --hash=sha256:f27fdaadce22f2ef950fc10dcdf8048407c3b42b73779e48a4e76b3c35bca26c \ - --hash=sha256:f694dc8a6a3112059258a725a4ebe9acac5fe62f11c77ac4dcf896edfa78ca28 \ - --hash=sha256:f800164276eec54e0af5c99feb9494c295118fc10a11b997bbb1348ba1a52065 \ - --hash=sha256:ffcd828e37dc219a72c9012ec44ad2e7e3066bec6ff3aaa19e7d435dbf4032ca +aiohttp==3.9.3 \ + --hash=sha256:017a21b0df49039c8f46ca0971b3a7fdc1f56741ab1240cb90ca408049766168 \ + --hash=sha256:039df344b45ae0b34ac885ab5b53940b174530d4dd8a14ed8b0e2155b9dddccb \ + --hash=sha256:055ce4f74b82551678291473f66dc9fb9048a50d8324278751926ff0ae7715e5 \ + --hash=sha256:06a9b2c8837d9a94fae16c6223acc14b4dfdff216ab9b7202e07a9a09541168f \ + --hash=sha256:07b837ef0d2f252f96009e9b8435ec1fef68ef8b1461933253d318748ec1acdc \ + --hash=sha256:0ed621426d961df79aa3b963ac7af0d40392956ffa9be022024cd16297b30c8c \ + --hash=sha256:0fa43c32d1643f518491d9d3a730f85f5bbaedcbd7fbcae27435bb8b7a061b29 \ + --hash=sha256:1f5a71d25cd8106eab05f8704cd9167b6e5187bcdf8f090a66c6d88b634802b4 \ + --hash=sha256:1f5cd333fcf7590a18334c90f8c9147c837a6ec8a178e88d90a9b96ea03194cc \ + --hash=sha256:27468897f628c627230dba07ec65dc8d0db566923c48f29e084ce382119802bc \ + --hash=sha256:298abd678033b8571995650ccee753d9458dfa0377be4dba91e4491da3f2be63 \ + --hash=sha256:2c895a656dd7e061b2fd6bb77d971cc38f2afc277229ce7dd3552de8313a483e \ + --hash=sha256:361a1026c9dd4aba0109e4040e2aecf9884f5cfe1b1b1bd3d09419c205e2e53d \ + --hash=sha256:363afe77cfcbe3a36353d8ea133e904b108feea505aa4792dad6585a8192c55a \ + --hash=sha256:38a19bc3b686ad55804ae931012f78f7a534cce165d089a2059f658f6c91fa60 \ + --hash=sha256:38f307b41e0bea3294a9a2a87833191e4bcf89bb0365e83a8be3a58b31fb7f38 \ + --hash=sha256:3e59c23c52765951b69ec45ddbbc9403a8761ee6f57253250c6e1536cacc758b \ + --hash=sha256:4b4af9f25b49a7be47c0972139e59ec0e8285c371049df1a63b6ca81fdd216a2 \ + --hash=sha256:504b6981675ace64c28bf4a05a508af5cde526e36492c98916127f5a02354d53 \ + --hash=sha256:50fca156d718f8ced687a373f9e140c1bb765ca16e3d6f4fe116e3df7c05b2c5 \ + --hash=sha256:522a11c934ea660ff8953eda090dcd2154d367dec1ae3c540aff9f8a5c109ab4 \ + --hash=sha256:52df73f14ed99cee84865b95a3d9e044f226320a87af208f068ecc33e0c35b96 \ + --hash=sha256:595f105710293e76b9dc09f52e0dd896bd064a79346234b521f6b968ffdd8e58 \ + --hash=sha256:59c26c95975f26e662ca78fdf543d4eeaef70e533a672b4113dd888bd2423caa \ + --hash=sha256:5bce0dc147ca85caa5d33debc4f4d65e8e8b5c97c7f9f660f215fa74fc49a321 \ + --hash=sha256:5eafe2c065df5401ba06821b9a054d9cb2848867f3c59801b5d07a0be3a380ae \ + --hash=sha256:5ed3e046ea7b14938112ccd53d91c1539af3e6679b222f9469981e3dac7ba1ce \ + --hash=sha256:5fe9ce6c09668063b8447f85d43b8d1c4e5d3d7e92c63173e6180b2ac5d46dd8 \ + --hash=sha256:648056db9a9fa565d3fa851880f99f45e3f9a771dd3ff3bb0c048ea83fb28194 \ + --hash=sha256:69361bfdca5468c0488d7017b9b1e5ce769d40b46a9f4a2eed26b78619e9396c \ + --hash=sha256:6b0e029353361f1746bac2e4cc19b32f972ec03f0f943b390c4ab3371840aabf \ + --hash=sha256:6b88f9386ff1ad91ace19d2a1c0225896e28815ee09fc6a8932fded8cda97c3d \ + --hash=sha256:770d015888c2a598b377bd2f663adfd947d78c0124cfe7b959e1ef39f5b13869 \ + --hash=sha256:7943c414d3a8d9235f5f15c22ace69787c140c80b718dcd57caaade95f7cd93b \ + --hash=sha256:7cf5c9458e1e90e3c390c2639f1017a0379a99a94fdfad3a1fd966a2874bba52 \ + --hash=sha256:7f46acd6a194287b7e41e87957bfe2ad1ad88318d447caf5b090012f2c5bb528 \ + --hash=sha256:82e6aa28dd46374f72093eda8bcd142f7771ee1eb9d1e223ff0fa7177a96b4a5 \ + --hash=sha256:835a55b7ca49468aaaac0b217092dfdff370e6c215c9224c52f30daaa735c1c1 \ + --hash=sha256:84871a243359bb42c12728f04d181a389718710129b36b6aad0fc4655a7647d4 \ + --hash=sha256:8aacb477dc26797ee089721536a292a664846489c49d3ef9725f992449eda5a8 \ + --hash=sha256:8e2c45c208c62e955e8256949eb225bd8b66a4c9b6865729a786f2aa79b72e9d \ + --hash=sha256:90842933e5d1ff760fae6caca4b2b3edba53ba8f4b71e95dacf2818a2aca06f7 \ + --hash=sha256:938a9653e1e0c592053f815f7028e41a3062e902095e5a7dc84617c87267ebd5 \ + --hash=sha256:939677b61f9d72a4fa2a042a5eee2a99a24001a67c13da113b2e30396567db54 \ + --hash=sha256:9d3c9b50f19704552f23b4eaea1fc082fdd82c63429a6506446cbd8737823da3 \ + --hash=sha256:a6fe5571784af92b6bc2fda8d1925cccdf24642d49546d3144948a6a1ed58ca5 \ + --hash=sha256:a78ed8a53a1221393d9637c01870248a6f4ea5b214a59a92a36f18151739452c \ + --hash=sha256:ab40e6251c3873d86ea9b30a1ac6d7478c09277b32e14745d0d3c6e76e3c7e29 \ + --hash=sha256:abf151955990d23f84205286938796c55ff11bbfb4ccfada8c9c83ae6b3c89a3 \ + --hash=sha256:acef0899fea7492145d2bbaaaec7b345c87753168589cc7faf0afec9afe9b747 \ + --hash=sha256:b40670ec7e2156d8e57f70aec34a7216407848dfe6c693ef131ddf6e76feb672 \ + --hash=sha256:b791a3143681a520c0a17e26ae7465f1b6f99461a28019d1a2f425236e6eedb5 \ + --hash=sha256:b955ed993491f1a5da7f92e98d5dad3c1e14dc175f74517c4e610b1f2456fb11 \ + --hash=sha256:ba39e9c8627edc56544c8628cc180d88605df3892beeb2b94c9bc857774848ca \ + --hash=sha256:bca77a198bb6e69795ef2f09a5f4c12758487f83f33d63acde5f0d4919815768 \ + --hash=sha256:c3452ea726c76e92f3b9fae4b34a151981a9ec0a4847a627c43d71a15ac32aa6 \ + --hash=sha256:c46956ed82961e31557b6857a5ca153c67e5476972e5f7190015018760938da2 \ + --hash=sha256:c7c8b816c2b5af5c8a436df44ca08258fc1a13b449393a91484225fcb7545533 \ + --hash=sha256:cd73265a9e5ea618014802ab01babf1940cecb90c9762d8b9e7d2cc1e1969ec6 \ + --hash=sha256:dad46e6f620574b3b4801c68255492e0159d1712271cc99d8bdf35f2043ec266 \ + --hash=sha256:dc9b311743a78043b26ffaeeb9715dc360335e5517832f5a8e339f8a43581e4d \ + --hash=sha256:df822ee7feaaeffb99c1a9e5e608800bd8eda6e5f18f5cfb0dc7eeb2eaa6bbec \ + --hash=sha256:e083c285857b78ee21a96ba1eb1b5339733c3563f72980728ca2b08b53826ca5 \ + --hash=sha256:e5e46b578c0e9db71d04c4b506a2121c0cb371dd89af17a0586ff6769d4c58c1 \ + --hash=sha256:e99abf0bba688259a496f966211c49a514e65afa9b3073a1fcee08856e04425b \ + --hash=sha256:ee43080e75fc92bf36219926c8e6de497f9b247301bbf88c5c7593d931426679 \ + --hash=sha256:f033d80bc6283092613882dfe40419c6a6a1527e04fc69350e87a9df02bbc283 \ + --hash=sha256:f1088fa100bf46e7b398ffd9904f4808a0612e1d966b4aa43baa535d1b6341eb \ + --hash=sha256:f56455b0c2c7cc3b0c584815264461d07b177f903a04481dfc33e08a89f0c26b \ + --hash=sha256:f59dfe57bb1ec82ac0698ebfcdb7bcd0e99c255bd637ff613760d5f33e7c81b3 \ + --hash=sha256:f7217af2e14da0856e082e96ff637f14ae45c10a5714b63c77f26d8884cf1051 \ + --hash=sha256:f734e38fd8666f53da904c52a23ce517f1b07722118d750405af7e4123933511 \ + --hash=sha256:f95511dd5d0e05fd9728bac4096319f80615aaef4acbecb35a990afebe953b0e \ + --hash=sha256:fdd215b7b7fd4a53994f238d0f46b7ba4ac4c0adb12452beee724ddd0743ae5d \ + --hash=sha256:feeb18a801aacb098220e2c3eea59a512362eb408d4afd0c242044c33ad6d542 \ + --hash=sha256:ff30218887e62209942f91ac1be902cc80cddb86bf00fbc6783b7a43b2bea26f # via -r requirements.in aiosignal==1.3.1 \ --hash=sha256:54cd96e15e1649b75d6c87526a6ff0b6c1b0dd3459f43d9ca11d48c339b68cfc \ diff --git a/examples/shared/websocket/Dockerfile b/examples/shared/websocket/Dockerfile index 38d788710dd23..f57af91de78fb 100644 --- a/examples/shared/websocket/Dockerfile +++ b/examples/shared/websocket/Dockerfile @@ -1,4 +1,4 @@ -FROM debian:bookworm-slim@sha256:f4a83aa865a2b4a064ff142aa91c713180df9fcb86ce676b5de2981029379c37 as websocket-base +FROM debian:bookworm-slim@sha256:7802002798b0e351323ed2357ae6dc5a8c4d0a05a57e7f4d8f97136151d3d603 as websocket-base ENV DEBIAN_FRONTEND=noninteractive RUN --mount=type=cache,target=/var/cache/apt,sharing=locked \ --mount=type=cache,target=/var/lib/apt/lists,sharing=locked \ diff --git a/examples/single-page-app/ui/yarn.lock b/examples/single-page-app/ui/yarn.lock index 5d0f48705fd94..61b629f36dfe5 100644 --- a/examples/single-page-app/ui/yarn.lock +++ b/examples/single-page-app/ui/yarn.lock @@ -143,9 +143,9 @@ integrity sha512-85ttAOMLsr53VgXkTbkx8oA6YTfT4q7/HzXSLEYmjcSTJPMPQtvq1BD79Byep5xMUYbGRzEpDsjUf3dyp54IKw== "@babel/helpers@^7.23.7": - version "7.23.7" - resolved "https://registry.yarnpkg.com/@babel/helpers/-/helpers-7.23.7.tgz#eb543c36f81da2873e47b76ee032343ac83bba60" - integrity sha512-6AMnjCoC8wjqBzDHkuqpa7jAKwvMo4dC+lr/TFBz+ucfulO1XMpDnwWPGBNwClOKZ8h6xn5N81W/R5OrcKtCbQ== + version "7.23.8" + resolved "https://registry.yarnpkg.com/@babel/helpers/-/helpers-7.23.8.tgz#fc6b2d65b16847fd50adddbd4232c76378959e34" + integrity sha512-KDqYz4PiOWvDFrdHLPhKtCThtIcKVy6avWD2oG4GEvyQ+XDZwHD4YQd+H2vNMnq2rkdxsDkU82T+Vk8U/WXHRQ== dependencies: "@babel/template" "^7.22.15" "@babel/traverse" "^7.23.7" @@ -180,9 +180,9 @@ "@babel/helper-plugin-utils" "^7.22.5" "@babel/runtime@^7.0.0", "@babel/runtime@^7.12.13", "@babel/runtime@^7.12.5", "@babel/runtime@^7.18.3": - version "7.23.7" - resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.23.7.tgz#dd7c88deeb218a0f8bd34d5db1aa242e0f203193" - integrity sha512-w06OXVOFso7LcbzMiDGt+3X7Rh7Ho8MmgPoWU3rarH+8upf+wSU/grlGbWzQyr3DkdN6ZeuMFjpdwW0Q+HxobA== + version "7.23.8" + resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.23.8.tgz#8ee6fe1ac47add7122902f257b8ddf55c898f650" + integrity sha512-Y7KbAP984rn1VGMbGqKmBLio9V7y5Je9GvU4rQPCPinCyNfUcToxIXl06d59URp/F3LwinvODxab5N/G6qggkw== dependencies: regenerator-runtime "^0.14.0" @@ -1152,120 +1152,120 @@ resolved "https://registry.yarnpkg.com/@emotion/weak-memoize/-/weak-memoize-0.3.1.tgz#d0fce5d07b0620caa282b5131c297bb60f9d87e6" integrity sha512-EsBwpc7hBUJWAsNPBmJy4hxWx12v6bshQsldrVmjxJoc3isbxhOrF2IcCpaXxfvq03NwkI7sbsOLXbYuqF/8Ww== -"@esbuild/aix-ppc64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/aix-ppc64/-/aix-ppc64-0.19.11.tgz#2acd20be6d4f0458bc8c784103495ff24f13b1d3" - integrity sha512-FnzU0LyE3ySQk7UntJO4+qIiQgI7KoODnZg5xzXIrFJlKd2P2gwHsHY4927xj9y5PJmJSzULiUCWmv7iWnNa7g== - -"@esbuild/android-arm64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/android-arm64/-/android-arm64-0.19.11.tgz#b45d000017385c9051a4f03e17078abb935be220" - integrity sha512-aiu7K/5JnLj//KOnOfEZ0D90obUkRzDMyqd/wNAUQ34m4YUPVhRZpnqKV9uqDGxT7cToSDnIHsGooyIczu9T+Q== - -"@esbuild/android-arm@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/android-arm/-/android-arm-0.19.11.tgz#f46f55414e1c3614ac682b29977792131238164c" - integrity sha512-5OVapq0ClabvKvQ58Bws8+wkLCV+Rxg7tUVbo9xu034Nm536QTII4YzhaFriQ7rMrorfnFKUsArD2lqKbFY4vw== - -"@esbuild/android-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/android-x64/-/android-x64-0.19.11.tgz#bfc01e91740b82011ef503c48f548950824922b2" - integrity sha512-eccxjlfGw43WYoY9QgB82SgGgDbibcqyDTlk3l3C0jOVHKxrjdc9CTwDUQd0vkvYg5um0OH+GpxYvp39r+IPOg== - -"@esbuild/darwin-arm64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/darwin-arm64/-/darwin-arm64-0.19.11.tgz#533fb7f5a08c37121d82c66198263dcc1bed29bf" - integrity sha512-ETp87DRWuSt9KdDVkqSoKoLFHYTrkyz2+65fj9nfXsaV3bMhTCjtQfw3y+um88vGRKRiF7erPrh/ZuIdLUIVxQ== - -"@esbuild/darwin-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/darwin-x64/-/darwin-x64-0.19.11.tgz#62f3819eff7e4ddc656b7c6815a31cf9a1e7d98e" - integrity sha512-fkFUiS6IUK9WYUO/+22omwetaSNl5/A8giXvQlcinLIjVkxwTLSktbF5f/kJMftM2MJp9+fXqZ5ezS7+SALp4g== - -"@esbuild/freebsd-arm64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/freebsd-arm64/-/freebsd-arm64-0.19.11.tgz#d478b4195aa3ca44160272dab85ef8baf4175b4a" - integrity sha512-lhoSp5K6bxKRNdXUtHoNc5HhbXVCS8V0iZmDvyWvYq9S5WSfTIHU2UGjcGt7UeS6iEYp9eeymIl5mJBn0yiuxA== - -"@esbuild/freebsd-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/freebsd-x64/-/freebsd-x64-0.19.11.tgz#7bdcc1917409178257ca6a1a27fe06e797ec18a2" - integrity sha512-JkUqn44AffGXitVI6/AbQdoYAq0TEullFdqcMY/PCUZ36xJ9ZJRtQabzMA+Vi7r78+25ZIBosLTOKnUXBSi1Kw== - -"@esbuild/linux-arm64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-arm64/-/linux-arm64-0.19.11.tgz#58ad4ff11685fcc735d7ff4ca759ab18fcfe4545" - integrity sha512-LneLg3ypEeveBSMuoa0kwMpCGmpu8XQUh+mL8XXwoYZ6Be2qBnVtcDI5azSvh7vioMDhoJFZzp9GWp9IWpYoUg== - -"@esbuild/linux-arm@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-arm/-/linux-arm-0.19.11.tgz#ce82246d873b5534d34de1e5c1b33026f35e60e3" - integrity sha512-3CRkr9+vCV2XJbjwgzjPtO8T0SZUmRZla+UL1jw+XqHZPkPgZiyWvbDvl9rqAN8Zl7qJF0O/9ycMtjU67HN9/Q== - -"@esbuild/linux-ia32@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-ia32/-/linux-ia32-0.19.11.tgz#cbae1f313209affc74b80f4390c4c35c6ab83fa4" - integrity sha512-caHy++CsD8Bgq2V5CodbJjFPEiDPq8JJmBdeyZ8GWVQMjRD0sU548nNdwPNvKjVpamYYVL40AORekgfIubwHoA== - -"@esbuild/linux-loong64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-loong64/-/linux-loong64-0.19.11.tgz#5f32aead1c3ec8f4cccdb7ed08b166224d4e9121" - integrity sha512-ppZSSLVpPrwHccvC6nQVZaSHlFsvCQyjnvirnVjbKSHuE5N24Yl8F3UwYUUR1UEPaFObGD2tSvVKbvR+uT1Nrg== - -"@esbuild/linux-mips64el@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-mips64el/-/linux-mips64el-0.19.11.tgz#38eecf1cbb8c36a616261de858b3c10d03419af9" - integrity sha512-B5x9j0OgjG+v1dF2DkH34lr+7Gmv0kzX6/V0afF41FkPMMqaQ77pH7CrhWeR22aEeHKaeZVtZ6yFwlxOKPVFyg== - -"@esbuild/linux-ppc64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-ppc64/-/linux-ppc64-0.19.11.tgz#9c5725a94e6ec15b93195e5a6afb821628afd912" - integrity sha512-MHrZYLeCG8vXblMetWyttkdVRjQlQUb/oMgBNurVEnhj4YWOr4G5lmBfZjHYQHHN0g6yDmCAQRR8MUHldvvRDA== - -"@esbuild/linux-riscv64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-riscv64/-/linux-riscv64-0.19.11.tgz#2dc4486d474a2a62bbe5870522a9a600e2acb916" - integrity sha512-f3DY++t94uVg141dozDu4CCUkYW+09rWtaWfnb3bqe4w5NqmZd6nPVBm+qbz7WaHZCoqXqHz5p6CM6qv3qnSSQ== - -"@esbuild/linux-s390x@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-s390x/-/linux-s390x-0.19.11.tgz#4ad8567df48f7dd4c71ec5b1753b6f37561a65a8" - integrity sha512-A5xdUoyWJHMMlcSMcPGVLzYzpcY8QP1RtYzX5/bS4dvjBGVxdhuiYyFwp7z74ocV7WDc0n1harxmpq2ePOjI0Q== - -"@esbuild/linux-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/linux-x64/-/linux-x64-0.19.11.tgz#b7390c4d5184f203ebe7ddaedf073df82a658766" - integrity sha512-grbyMlVCvJSfxFQUndw5mCtWs5LO1gUlwP4CDi4iJBbVpZcqLVT29FxgGuBJGSzyOxotFG4LoO5X+M1350zmPA== - -"@esbuild/netbsd-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/netbsd-x64/-/netbsd-x64-0.19.11.tgz#d633c09492a1721377f3bccedb2d821b911e813d" - integrity sha512-13jvrQZJc3P230OhU8xgwUnDeuC/9egsjTkXN49b3GcS5BKvJqZn86aGM8W9pd14Kd+u7HuFBMVtrNGhh6fHEQ== - -"@esbuild/openbsd-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/openbsd-x64/-/openbsd-x64-0.19.11.tgz#17388c76e2f01125bf831a68c03a7ffccb65d1a2" - integrity sha512-ysyOGZuTp6SNKPE11INDUeFVVQFrhcNDVUgSQVDzqsqX38DjhPEPATpid04LCoUr2WXhQTEZ8ct/EgJCUDpyNw== - -"@esbuild/sunos-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/sunos-x64/-/sunos-x64-0.19.11.tgz#e320636f00bb9f4fdf3a80e548cb743370d41767" - integrity sha512-Hf+Sad9nVwvtxy4DXCZQqLpgmRTQqyFyhT3bZ4F2XlJCjxGmRFF0Shwn9rzhOYRB61w9VMXUkxlBy56dk9JJiQ== - -"@esbuild/win32-arm64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/win32-arm64/-/win32-arm64-0.19.11.tgz#c778b45a496e90b6fc373e2a2bb072f1441fe0ee" - integrity sha512-0P58Sbi0LctOMOQbpEOvOL44Ne0sqbS0XWHMvvrg6NE5jQ1xguCSSw9jQeUk2lfrXYsKDdOe6K+oZiwKPilYPQ== - -"@esbuild/win32-ia32@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/win32-ia32/-/win32-ia32-0.19.11.tgz#481a65fee2e5cce74ec44823e6b09ecedcc5194c" - integrity sha512-6YOrWS+sDJDmshdBIQU+Uoyh7pQKrdykdefC1avn76ss5c+RN6gut3LZA4E2cH5xUEp5/cA0+YxRaVtRAb0xBg== - -"@esbuild/win32-x64@0.19.11": - version "0.19.11" - resolved "https://registry.yarnpkg.com/@esbuild/win32-x64/-/win32-x64-0.19.11.tgz#a5d300008960bb39677c46bf16f53ec70d8dee04" - integrity sha512-vfkhltrjCAb603XaFhqhAF4LGDi2M4OrCRrFusyQ+iTLQ/o60QQXxc9cZC/FFpihBI9N1Grn6SMKVJ4KP7Fuiw== +"@esbuild/aix-ppc64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/aix-ppc64/-/aix-ppc64-0.19.12.tgz#d1bc06aedb6936b3b6d313bf809a5a40387d2b7f" + integrity sha512-bmoCYyWdEL3wDQIVbcyzRyeKLgk2WtWLTWz1ZIAZF/EGbNOwSA6ew3PftJ1PqMiOOGu0OyFMzG53L0zqIpPeNA== + +"@esbuild/android-arm64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/android-arm64/-/android-arm64-0.19.12.tgz#7ad65a36cfdb7e0d429c353e00f680d737c2aed4" + integrity sha512-P0UVNGIienjZv3f5zq0DP3Nt2IE/3plFzuaS96vihvD0Hd6H/q4WXUGpCxD/E8YrSXfNyRPbpTq+T8ZQioSuPA== + +"@esbuild/android-arm@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/android-arm/-/android-arm-0.19.12.tgz#b0c26536f37776162ca8bde25e42040c203f2824" + integrity sha512-qg/Lj1mu3CdQlDEEiWrlC4eaPZ1KztwGJ9B6J+/6G+/4ewxJg7gqj8eVYWvao1bXrqGiW2rsBZFSX3q2lcW05w== + +"@esbuild/android-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/android-x64/-/android-x64-0.19.12.tgz#cb13e2211282012194d89bf3bfe7721273473b3d" + integrity sha512-3k7ZoUW6Q6YqhdhIaq/WZ7HwBpnFBlW905Fa4s4qWJyiNOgT1dOqDiVAQFwBH7gBRZr17gLrlFCRzF6jFh7Kew== + +"@esbuild/darwin-arm64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/darwin-arm64/-/darwin-arm64-0.19.12.tgz#cbee41e988020d4b516e9d9e44dd29200996275e" + integrity sha512-B6IeSgZgtEzGC42jsI+YYu9Z3HKRxp8ZT3cqhvliEHovq8HSX2YX8lNocDn79gCKJXOSaEot9MVYky7AKjCs8g== + +"@esbuild/darwin-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/darwin-x64/-/darwin-x64-0.19.12.tgz#e37d9633246d52aecf491ee916ece709f9d5f4cd" + integrity sha512-hKoVkKzFiToTgn+41qGhsUJXFlIjxI/jSYeZf3ugemDYZldIXIxhvwN6erJGlX4t5h417iFuheZ7l+YVn05N3A== + +"@esbuild/freebsd-arm64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/freebsd-arm64/-/freebsd-arm64-0.19.12.tgz#1ee4d8b682ed363b08af74d1ea2b2b4dbba76487" + integrity sha512-4aRvFIXmwAcDBw9AueDQ2YnGmz5L6obe5kmPT8Vd+/+x/JMVKCgdcRwH6APrbpNXsPz+K653Qg8HB/oXvXVukA== + +"@esbuild/freebsd-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/freebsd-x64/-/freebsd-x64-0.19.12.tgz#37a693553d42ff77cd7126764b535fb6cc28a11c" + integrity sha512-EYoXZ4d8xtBoVN7CEwWY2IN4ho76xjYXqSXMNccFSx2lgqOG/1TBPW0yPx1bJZk94qu3tX0fycJeeQsKovA8gg== + +"@esbuild/linux-arm64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-arm64/-/linux-arm64-0.19.12.tgz#be9b145985ec6c57470e0e051d887b09dddb2d4b" + integrity sha512-EoTjyYyLuVPfdPLsGVVVC8a0p1BFFvtpQDB/YLEhaXyf/5bczaGeN15QkR+O4S5LeJ92Tqotve7i1jn35qwvdA== + +"@esbuild/linux-arm@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-arm/-/linux-arm-0.19.12.tgz#207ecd982a8db95f7b5279207d0ff2331acf5eef" + integrity sha512-J5jPms//KhSNv+LO1S1TX1UWp1ucM6N6XuL6ITdKWElCu8wXP72l9MM0zDTzzeikVyqFE6U8YAV9/tFyj0ti+w== + +"@esbuild/linux-ia32@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-ia32/-/linux-ia32-0.19.12.tgz#d0d86b5ca1562523dc284a6723293a52d5860601" + integrity sha512-Thsa42rrP1+UIGaWz47uydHSBOgTUnwBwNq59khgIwktK6x60Hivfbux9iNR0eHCHzOLjLMLfUMLCypBkZXMHA== + +"@esbuild/linux-loong64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-loong64/-/linux-loong64-0.19.12.tgz#9a37f87fec4b8408e682b528391fa22afd952299" + integrity sha512-LiXdXA0s3IqRRjm6rV6XaWATScKAXjI4R4LoDlvO7+yQqFdlr1Bax62sRwkVvRIrwXxvtYEHHI4dm50jAXkuAA== + +"@esbuild/linux-mips64el@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-mips64el/-/linux-mips64el-0.19.12.tgz#4ddebd4e6eeba20b509d8e74c8e30d8ace0b89ec" + integrity sha512-fEnAuj5VGTanfJ07ff0gOA6IPsvrVHLVb6Lyd1g2/ed67oU1eFzL0r9WL7ZzscD+/N6i3dWumGE1Un4f7Amf+w== + +"@esbuild/linux-ppc64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-ppc64/-/linux-ppc64-0.19.12.tgz#adb67dadb73656849f63cd522f5ecb351dd8dee8" + integrity sha512-nYJA2/QPimDQOh1rKWedNOe3Gfc8PabU7HT3iXWtNUbRzXS9+vgB0Fjaqr//XNbd82mCxHzik2qotuI89cfixg== + +"@esbuild/linux-riscv64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-riscv64/-/linux-riscv64-0.19.12.tgz#11bc0698bf0a2abf8727f1c7ace2112612c15adf" + integrity sha512-2MueBrlPQCw5dVJJpQdUYgeqIzDQgw3QtiAHUC4RBz9FXPrskyyU3VI1hw7C0BSKB9OduwSJ79FTCqtGMWqJHg== + +"@esbuild/linux-s390x@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-s390x/-/linux-s390x-0.19.12.tgz#e86fb8ffba7c5c92ba91fc3b27ed5a70196c3cc8" + integrity sha512-+Pil1Nv3Umes4m3AZKqA2anfhJiVmNCYkPchwFJNEJN5QxmTs1uzyy4TvmDrCRNT2ApwSari7ZIgrPeUx4UZDg== + +"@esbuild/linux-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/linux-x64/-/linux-x64-0.19.12.tgz#5f37cfdc705aea687dfe5dfbec086a05acfe9c78" + integrity sha512-B71g1QpxfwBvNrfyJdVDexenDIt1CiDN1TIXLbhOw0KhJzE78KIFGX6OJ9MrtC0oOqMWf+0xop4qEU8JrJTwCg== + +"@esbuild/netbsd-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/netbsd-x64/-/netbsd-x64-0.19.12.tgz#29da566a75324e0d0dd7e47519ba2f7ef168657b" + integrity sha512-3ltjQ7n1owJgFbuC61Oj++XhtzmymoCihNFgT84UAmJnxJfm4sYCiSLTXZtE00VWYpPMYc+ZQmB6xbSdVh0JWA== + +"@esbuild/openbsd-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/openbsd-x64/-/openbsd-x64-0.19.12.tgz#306c0acbdb5a99c95be98bdd1d47c916e7dc3ff0" + integrity sha512-RbrfTB9SWsr0kWmb9srfF+L933uMDdu9BIzdA7os2t0TXhCRjrQyCeOt6wVxr79CKD4c+p+YhCj31HBkYcXebw== + +"@esbuild/sunos-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/sunos-x64/-/sunos-x64-0.19.12.tgz#0933eaab9af8b9b2c930236f62aae3fc593faf30" + integrity sha512-HKjJwRrW8uWtCQnQOz9qcU3mUZhTUQvi56Q8DPTLLB+DawoiQdjsYq+j+D3s9I8VFtDr+F9CjgXKKC4ss89IeA== + +"@esbuild/win32-arm64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/win32-arm64/-/win32-arm64-0.19.12.tgz#773bdbaa1971b36db2f6560088639ccd1e6773ae" + integrity sha512-URgtR1dJnmGvX864pn1B2YUYNzjmXkuJOIqG2HdU62MVS4EHpU2946OZoTMnRUHklGtJdJZ33QfzdjGACXhn1A== + +"@esbuild/win32-ia32@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/win32-ia32/-/win32-ia32-0.19.12.tgz#000516cad06354cc84a73f0943a4aa690ef6fd67" + integrity sha512-+ZOE6pUkMOJfmxmBZElNOx72NKpIa/HFOMGzu8fqzQJ5kgf6aTGrcJaFsNiVMH4JKpMipyK+7k0n2UXN7a8YKQ== + +"@esbuild/win32-x64@0.19.12": + version "0.19.12" + resolved "https://registry.yarnpkg.com/@esbuild/win32-x64/-/win32-x64-0.19.12.tgz#c57c8afbb4054a3ab8317591a0b7320360b444ae" + integrity sha512-T1QyPSDCyMXaO3pzBkF96E8xMkiRYbUEZADd29SyPGabqxMViNoii+NcK7eWJAEoU6RZyEm5lVSIjTmcdoB9HA== "@eslint-community/eslint-utils@^4.1.2", "@eslint-community/eslint-utils@^4.2.0", "@eslint-community/eslint-utils@^4.4.0": version "4.4.0" @@ -1300,12 +1300,12 @@ integrity sha512-gMsVel9D7f2HLkBma9VbtzZRehRogVRfbr++f06nL2vnCGCNlzOD+/MUov/F4p8myyAHspEhVobgjpX64q5m6A== "@humanwhocodes/config-array@^0.11.13": - version "0.11.13" - resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.13.tgz#075dc9684f40a531d9b26b0822153c1e832ee297" - integrity sha512-JSBDMiDKSzQVngfRjOdFXgFfklaXI4K9nLF49Auh21lmBWRLIK3+xTErTWD4KU54pb6coM6ESE7Awz/FNU3zgQ== + version "0.11.14" + resolved "https://registry.yarnpkg.com/@humanwhocodes/config-array/-/config-array-0.11.14.tgz#d78e481a039f7566ecc9660b4ea7fe6b1fec442b" + integrity sha512-3T8LkOmg45BV5FICb15QQMsyUSWrQ8AygVfC7ZG32zOalnqrilm018ZVCw0eapXux8FtA33q8PSRSstjee3jSg== dependencies: - "@humanwhocodes/object-schema" "^2.0.1" - debug "^4.1.1" + "@humanwhocodes/object-schema" "^2.0.2" + debug "^4.3.1" minimatch "^3.0.5" "@humanwhocodes/module-importer@^1.0.1": @@ -1313,10 +1313,10 @@ resolved "https://registry.yarnpkg.com/@humanwhocodes/module-importer/-/module-importer-1.0.1.tgz#af5b2691a22b44be847b0ca81641c5fb6ad0172c" integrity sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA== -"@humanwhocodes/object-schema@^2.0.1": - version "2.0.1" - resolved "https://registry.yarnpkg.com/@humanwhocodes/object-schema/-/object-schema-2.0.1.tgz#e5211452df060fa8522b55c7b3c0c4d1981cb044" - integrity sha512-dvuCeX5fC9dXgJn9t+X5atfmgQAzUOWqS1254Gh0m6i8wKd10ebXkfNKiRK+1GWi/yTvvLDHpoxLr0xxxeslWw== +"@humanwhocodes/object-schema@^2.0.2": + version "2.0.2" + resolved "https://registry.yarnpkg.com/@humanwhocodes/object-schema/-/object-schema-2.0.2.tgz#d9fae00a2d5cb40f92cfe64b47ad749fbc38f917" + integrity sha512-6EwiSjwWYP7pTckG6I5eyFANjPhmPjUX9JRLUSfNPC7FX7zK9gyZAfUEaECL6ALTpGX5AjnBq3C9XmVWPitNpw== "@jridgewell/gen-mapping@^0.3.0", "@jridgewell/gen-mapping@^0.3.2": version "0.3.3" @@ -1343,9 +1343,9 @@ integrity sha512-eF2rxCRulEKXHTRiDrDy6erMYWqNw4LPdQ8UQA4huuxaQsVeRPFl2oM8oDGxMFhJUWZf9McpLtJasDDZb/Bpeg== "@jridgewell/trace-mapping@^0.3.17", "@jridgewell/trace-mapping@^0.3.9": - version "0.3.20" - resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.20.tgz#72e45707cf240fa6b081d0366f8265b0cd10197f" - integrity sha512-R8LcPeWZol2zR8mmH3JeKQ6QRCFb7XgUhV9ZlGhHLGyg4wpPiPZNQOOWhFZhxKw8u//yTbNGI42Bx/3paXEQ+Q== + version "0.3.22" + resolved "https://registry.yarnpkg.com/@jridgewell/trace-mapping/-/trace-mapping-0.3.22.tgz#72a621e5de59f5f1ef792d0793a82ee20f645e4c" + integrity sha512-Wf963MzWtA2sjrNt+g18IAln9lKnlRp+K2eH4jjIoF1wYeq3aMREpG09xhlhdzS0EjwU7qmUJYangWa+151vZw== dependencies: "@jridgewell/resolve-uri" "^3.1.0" "@jridgewell/sourcemap-codec" "^1.4.14" @@ -1376,75 +1376,75 @@ resolved "https://registry.yarnpkg.com/@popperjs/core/-/core-2.11.8.tgz#6b79032e760a0899cd4204710beede972a3a185f" integrity sha512-P1st0aksCrn9sGZhp8GMYwBnQsbvAWsZAX44oXNNvLHGqAOcoVxmjZiohstwQ7SqKnbR47akdNi+uleWD8+g6A== -"@remix-run/router@1.14.1": - version "1.14.1" - resolved "https://registry.yarnpkg.com/@remix-run/router/-/router-1.14.1.tgz#6d2dd03d52e604279c38911afc1079d58c50a755" - integrity sha512-Qg4DMQsfPNAs88rb2xkdk03N3bjK4jgX5fR24eHCTR9q6PrhZQZ4UJBPzCHJkIpTRN1UKxx2DzjZmnC+7Lj0Ow== - -"@rollup/rollup-android-arm-eabi@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.9.2.tgz#ccb02257556bacbc1e756ab9b0b973cea2c7a664" - integrity sha512-RKzxFxBHq9ysZ83fn8Iduv3A283K7zPPYuhL/z9CQuyFrjwpErJx0h4aeb/bnJ+q29GRLgJpY66ceQ/Wcsn3wA== - -"@rollup/rollup-android-arm64@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.9.2.tgz#21bd0fbafdf442c6a17645b840f6a94556b0e9bb" - integrity sha512-yZ+MUbnwf3SHNWQKJyWh88ii2HbuHCFQnAYTeeO1Nb8SyEiWASEi5dQUygt3ClHWtA9My9RQAYkjvrsZ0WK8Xg== - -"@rollup/rollup-darwin-arm64@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.9.2.tgz#9f2e5d5637677f9839dbe1622130d0592179136a" - integrity sha512-vqJ/pAUh95FLc/G/3+xPqlSBgilPnauVf2EXOQCZzhZJCXDXt/5A8mH/OzU6iWhb3CNk5hPJrh8pqJUPldN5zw== - -"@rollup/rollup-darwin-x64@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.9.2.tgz#1b06291ff1c41af94d2786cd167188c5bf7caec9" - integrity sha512-otPHsN5LlvedOprd3SdfrRNhOahhVBwJpepVKUN58L0RnC29vOAej1vMEaVU6DadnpjivVsNTM5eNt0CcwTahw== - -"@rollup/rollup-linux-arm-gnueabihf@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.9.2.tgz#147069948bba00f435122f411210624e72638ebf" - integrity sha512-ewG5yJSp+zYKBYQLbd1CUA7b1lSfIdo9zJShNTyc2ZP1rcPrqyZcNlsHgs7v1zhgfdS+kW0p5frc0aVqhZCiYQ== - -"@rollup/rollup-linux-arm64-gnu@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.9.2.tgz#3a50f0e7ae6e444d11c61fce12783196454a4efb" - integrity sha512-pL6QtV26W52aCWTG1IuFV3FMPL1m4wbsRG+qijIvgFO/VBsiXJjDPE/uiMdHBAO6YcpV4KvpKtd0v3WFbaxBtg== - -"@rollup/rollup-linux-arm64-musl@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.9.2.tgz#82b5e75484d91c25d4e649d018d9523e72d6dac2" - integrity sha512-On+cc5EpOaTwPSNetHXBuqylDW+765G/oqB9xGmWU3npEhCh8xu0xqHGUA+4xwZLqBbIZNcBlKSIYfkBm6ko7g== - -"@rollup/rollup-linux-riscv64-gnu@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.9.2.tgz#ca96f2d43a553d73aec736e991c07010561bc7a9" - integrity sha512-Wnx/IVMSZ31D/cO9HSsU46FjrPWHqtdF8+0eyZ1zIB5a6hXaZXghUKpRrC4D5DcRTZOjml2oBhXoqfGYyXKipw== - -"@rollup/rollup-linux-x64-gnu@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.9.2.tgz#db1cece244ea46706c0e1a522ec19ca0173abc55" - integrity sha512-ym5x1cj4mUAMBummxxRkI4pG5Vht1QMsJexwGP8547TZ0sox9fCLDHw9KCH9c1FO5d9GopvkaJsBIOkTKxksdw== - -"@rollup/rollup-linux-x64-musl@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.9.2.tgz#c15b26b86827f75977bf59ebd41ce5d788713936" - integrity sha512-m0hYELHGXdYx64D6IDDg/1vOJEaiV8f1G/iO+tejvRCJNSwK4jJ15e38JQy5Q6dGkn1M/9KcyEOwqmlZ2kqaZg== - -"@rollup/rollup-win32-arm64-msvc@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.9.2.tgz#60152948f9fb08e8c50c1555e334ca9f9f1f53aa" - integrity sha512-x1CWburlbN5JjG+juenuNa4KdedBdXLjZMp56nHFSHTOsb/MI2DYiGzLtRGHNMyydPGffGId+VgjOMrcltOksA== - -"@rollup/rollup-win32-ia32-msvc@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.9.2.tgz#657288cff10311f997d8dbd648590441760ae6d9" - integrity sha512-VVzCB5yXR1QlfsH1Xw1zdzQ4Pxuzv+CPr5qpElpKhVxlxD3CRdfubAG9mJROl6/dmj5gVYDDWk8sC+j9BI9/kQ== - -"@rollup/rollup-win32-x64-msvc@4.9.2": - version "4.9.2" - resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.9.2.tgz#830f3a3fba67f6216a5884368431918029045afe" - integrity sha512-SYRedJi+mweatroB+6TTnJYLts0L0bosg531xnQWtklOI6dezEagx4Q0qDyvRdK+qgdA3YZpjjGuPFtxBmddBA== +"@remix-run/router@1.14.2": + version "1.14.2" + resolved "https://registry.yarnpkg.com/@remix-run/router/-/router-1.14.2.tgz#4d58f59908d9197ba3179310077f25c88e49ed17" + integrity sha512-ACXpdMM9hmKZww21yEqWwiLws/UPLhNKvimN8RrYSqPSvB3ov7sLvAcfvaxePeLvccTQKGdkDIhLYApZVDFuKg== + +"@rollup/rollup-android-arm-eabi@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.9.6.tgz#66b8d9cb2b3a474d115500f9ebaf43e2126fe496" + integrity sha512-MVNXSSYN6QXOulbHpLMKYi60ppyO13W9my1qogeiAqtjb2yR4LSmfU2+POvDkLzhjYLXz9Rf9+9a3zFHW1Lecg== + +"@rollup/rollup-android-arm64@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.9.6.tgz#46327d5b86420d2307946bec1535fdf00356e47d" + integrity sha512-T14aNLpqJ5wzKNf5jEDpv5zgyIqcpn1MlwCrUXLrwoADr2RkWA0vOWP4XxbO9aiO3dvMCQICZdKeDrFl7UMClw== + +"@rollup/rollup-darwin-arm64@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.9.6.tgz#166987224d2f8b1e2fd28ee90c447d52271d5e90" + integrity sha512-CqNNAyhRkTbo8VVZ5R85X73H3R5NX9ONnKbXuHisGWC0qRbTTxnF1U4V9NafzJbgGM0sHZpdO83pLPzq8uOZFw== + +"@rollup/rollup-darwin-x64@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.9.6.tgz#a2e6e096f74ccea6e2f174454c26aef6bcdd1274" + integrity sha512-zRDtdJuRvA1dc9Mp6BWYqAsU5oeLixdfUvkTHuiYOHwqYuQ4YgSmi6+/lPvSsqc/I0Omw3DdICx4Tfacdzmhog== + +"@rollup/rollup-linux-arm-gnueabihf@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.9.6.tgz#09fcd4c55a2d6160c5865fec708a8e5287f30515" + integrity sha512-oNk8YXDDnNyG4qlNb6is1ojTOGL/tRhbbKeE/YuccItzerEZT68Z9gHrY3ROh7axDc974+zYAPxK5SH0j/G+QQ== + +"@rollup/rollup-linux-arm64-gnu@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.9.6.tgz#19a3c0b6315c747ca9acf86e9b710cc2440f83c9" + integrity sha512-Z3O60yxPtuCYobrtzjo0wlmvDdx2qZfeAWTyfOjEDqd08kthDKexLpV97KfAeUXPosENKd8uyJMRDfFMxcYkDQ== + +"@rollup/rollup-linux-arm64-musl@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.9.6.tgz#94aaf95fdaf2ad9335983a4552759f98e6b2e850" + integrity sha512-gpiG0qQJNdYEVad+1iAsGAbgAnZ8j07FapmnIAQgODKcOTjLEWM9sRb+MbQyVsYCnA0Im6M6QIq6ax7liws6eQ== + +"@rollup/rollup-linux-riscv64-gnu@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.9.6.tgz#160510e63f4b12618af4013bddf1761cf9fc9880" + integrity sha512-+uCOcvVmFUYvVDr27aiyun9WgZk0tXe7ThuzoUTAukZJOwS5MrGbmSlNOhx1j80GdpqbOty05XqSl5w4dQvcOA== + +"@rollup/rollup-linux-x64-gnu@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.9.6.tgz#5ac5d068ce0726bd0a96ca260d5bd93721c0cb98" + integrity sha512-HUNqM32dGzfBKuaDUBqFB7tP6VMN74eLZ33Q9Y1TBqRDn+qDonkAUyKWwF9BR9unV7QUzffLnz9GrnKvMqC/fw== + +"@rollup/rollup-linux-x64-musl@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.9.6.tgz#bafa759ab43e8eab9edf242a8259ffb4f2a57a5d" + integrity sha512-ch7M+9Tr5R4FK40FHQk8VnML0Szi2KRujUgHXd/HjuH9ifH72GUmw6lStZBo3c3GB82vHa0ZoUfjfcM7JiiMrQ== + +"@rollup/rollup-win32-arm64-msvc@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.9.6.tgz#1cc3416682e5a20d8f088f26657e6e47f8db468e" + integrity sha512-VD6qnR99dhmTQ1mJhIzXsRcTBvTjbfbGGwKAHcu+52cVl15AC/kplkhxzW/uT0Xl62Y/meBKDZvoJSJN+vTeGA== + +"@rollup/rollup-win32-ia32-msvc@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.9.6.tgz#7d2251e1aa5e8a1e47c86891fe4547a939503461" + integrity sha512-J9AFDq/xiRI58eR2NIDfyVmTYGyIZmRcvcAoJ48oDld/NTR8wyiPUu2X/v1navJ+N/FGg68LEbX3Ejd6l8B7MQ== + +"@rollup/rollup-win32-x64-msvc@4.9.6": + version "4.9.6" + resolved "https://registry.yarnpkg.com/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.9.6.tgz#2c1fb69e02a3f1506f52698cfdc3a8b6386df9a6" + integrity sha512-jqzNLhNDvIZOrt69Ce4UjGRpXJBzhUBzawMwnaDAwyHriki3XollsewxWzOzz+4yOFDkuJHtTsZFwMxhYJWmLQ== "@types/babel__core@^7.20.5": version "7.20.5" @@ -1479,6 +1479,11 @@ dependencies: "@babel/types" "^7.20.7" +"@types/estree@1.0.5": + version "1.0.5" + resolved "https://registry.yarnpkg.com/@types/estree/-/estree-1.0.5.tgz#a6ce3e556e00fd9895dd872dd172ad0d4bd687f4" + integrity sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw== + "@types/json-schema@^7.0.12": version "7.0.15" resolved "https://registry.yarnpkg.com/@types/json-schema/-/json-schema-7.0.15.tgz#596a1747233694d50f6ad8a7869fcb6f56cf5841" @@ -1519,9 +1524,9 @@ "@types/react" "*" "@types/react@*", "@types/react@^18.2.43": - version "18.2.46" - resolved "https://registry.yarnpkg.com/@types/react/-/react-18.2.46.tgz#f04d6c528f8f136ea66333bc66abcae46e2680df" - integrity sha512-nNCvVBcZlvX4NU1nRRNV/mFl1nNRuTuslAJglQsq+8ldXe5Xv0Wd2f7WTE3jOxhLH2BFfiZGC6GCp+kHQbgG+w== + version "18.2.48" + resolved "https://registry.yarnpkg.com/@types/react/-/react-18.2.48.tgz#11df5664642d0bd879c1f58bc1d37205b064e8f1" + integrity sha512-qboRCl6Ie70DQQG9hhNREz81jqC1cs9EVNcjQ1AU+jH6NFfSAhVVbrrY/+nSF+Bsk4AOwm9Qa61InvMCyV+H3w== dependencies: "@types/prop-types" "*" "@types/scheduler" "*" @@ -1538,15 +1543,15 @@ integrity sha512-dn1l8LaMea/IjDoHNd9J52uBbInB796CDffS6VdIxvqYCPSG0V0DzHp76GpaWnlhg88uYyPbXCDIowa86ybd5A== "@typescript-eslint/eslint-plugin@^6.4.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-6.17.0.tgz#dfc38f790704ba8a54a1277c51efdb489f6ecf9f" - integrity sha512-Vih/4xLXmY7V490dGwBQJTpIZxH4ZFH6eCVmQ4RFkB+wmaCTDAx4dtgoWwMNGKLkqRY1L6rPqzEbjorRnDo4rQ== + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/eslint-plugin/-/eslint-plugin-6.19.1.tgz#bb0676af940bc23bf299ca58dbdc6589c2548c2e" + integrity sha512-roQScUGFruWod9CEyoV5KlCYrubC/fvG8/1zXuT0WTcxX87GnMMmnksMwSg99lo1xiKrBzw2icsJPMAw1OtKxg== dependencies: "@eslint-community/regexpp" "^4.5.1" - "@typescript-eslint/scope-manager" "6.17.0" - "@typescript-eslint/type-utils" "6.17.0" - "@typescript-eslint/utils" "6.17.0" - "@typescript-eslint/visitor-keys" "6.17.0" + "@typescript-eslint/scope-manager" "6.19.1" + "@typescript-eslint/type-utils" "6.19.1" + "@typescript-eslint/utils" "6.19.1" + "@typescript-eslint/visitor-keys" "6.19.1" debug "^4.3.4" graphemer "^1.4.0" ignore "^5.2.4" @@ -1555,46 +1560,46 @@ ts-api-utils "^1.0.1" "@typescript-eslint/parser@^6.14.0", "@typescript-eslint/parser@^6.4.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-6.17.0.tgz#8cd7a0599888ca6056082225b2fdf9a635bf32a1" - integrity sha512-C4bBaX2orvhK+LlwrY8oWGmSl4WolCfYm513gEccdWZj0CwGadbIADb0FtVEcI+WzUyjyoBj2JRP8g25E6IB8A== - dependencies: - "@typescript-eslint/scope-manager" "6.17.0" - "@typescript-eslint/types" "6.17.0" - "@typescript-eslint/typescript-estree" "6.17.0" - "@typescript-eslint/visitor-keys" "6.17.0" + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/parser/-/parser-6.19.1.tgz#68a87bb21afaf0b1689e9cdce0e6e75bc91ada78" + integrity sha512-WEfX22ziAh6pRE9jnbkkLGp/4RhTpffr2ZK5bJ18M8mIfA8A+k97U9ZyaXCEJRlmMHh7R9MJZWXp/r73DzINVQ== + dependencies: + "@typescript-eslint/scope-manager" "6.19.1" + "@typescript-eslint/types" "6.19.1" + "@typescript-eslint/typescript-estree" "6.19.1" + "@typescript-eslint/visitor-keys" "6.19.1" debug "^4.3.4" -"@typescript-eslint/scope-manager@6.17.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-6.17.0.tgz#70e6c1334d0d76562dfa61aed9009c140a7601b4" - integrity sha512-RX7a8lwgOi7am0k17NUO0+ZmMOX4PpjLtLRgLmT1d3lBYdWH4ssBUbwdmc5pdRX8rXon8v9x8vaoOSpkHfcXGA== +"@typescript-eslint/scope-manager@6.19.1": + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/scope-manager/-/scope-manager-6.19.1.tgz#2f527ee30703a6169a52b31d42a1103d80acd51b" + integrity sha512-4CdXYjKf6/6aKNMSly/BP4iCSOpvMmqtDzRtqFyyAae3z5kkqEjKndR5vDHL8rSuMIIWP8u4Mw4VxLyxZW6D5w== dependencies: - "@typescript-eslint/types" "6.17.0" - "@typescript-eslint/visitor-keys" "6.17.0" + "@typescript-eslint/types" "6.19.1" + "@typescript-eslint/visitor-keys" "6.19.1" -"@typescript-eslint/type-utils@6.17.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-6.17.0.tgz#5febad3f523e393006614cbda28b826925b728d5" - integrity sha512-hDXcWmnbtn4P2B37ka3nil3yi3VCQO2QEB9gBiHJmQp5wmyQWqnjA85+ZcE8c4FqnaB6lBwMrPkgd4aBYz3iNg== +"@typescript-eslint/type-utils@6.19.1": + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/type-utils/-/type-utils-6.19.1.tgz#6a130e3afe605a4898e043fa9f72e96309b54935" + integrity sha512-0vdyld3ecfxJuddDjACUvlAeYNrHP/pDeQk2pWBR2ESeEzQhg52DF53AbI9QCBkYE23lgkhLCZNkHn2hEXXYIg== dependencies: - "@typescript-eslint/typescript-estree" "6.17.0" - "@typescript-eslint/utils" "6.17.0" + "@typescript-eslint/typescript-estree" "6.19.1" + "@typescript-eslint/utils" "6.19.1" debug "^4.3.4" ts-api-utils "^1.0.1" -"@typescript-eslint/types@6.17.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-6.17.0.tgz#844a92eb7c527110bf9a7d177e3f22bd5a2f40cb" - integrity sha512-qRKs9tvc3a4RBcL/9PXtKSehI/q8wuU9xYJxe97WFxnzH8NWWtcW3ffNS+EWg8uPvIerhjsEZ+rHtDqOCiH57A== +"@typescript-eslint/types@6.19.1": + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/types/-/types-6.19.1.tgz#2d4c9d492a63ede15e7ba7d129bdf7714b77f771" + integrity sha512-6+bk6FEtBhvfYvpHsDgAL3uo4BfvnTnoge5LrrCj2eJN8g3IJdLTD4B/jK3Q6vo4Ql/Hoip9I8aB6fF+6RfDqg== -"@typescript-eslint/typescript-estree@6.17.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-6.17.0.tgz#b913d19886c52d8dc3db856903a36c6c64fd62aa" - integrity sha512-gVQe+SLdNPfjlJn5VNGhlOhrXz4cajwFd5kAgWtZ9dCZf4XJf8xmgCTLIqec7aha3JwgLI2CK6GY1043FRxZwg== +"@typescript-eslint/typescript-estree@6.19.1": + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/typescript-estree/-/typescript-estree-6.19.1.tgz#796d88d88882f12e85bb33d6d82d39e1aea54ed1" + integrity sha512-aFdAxuhzBFRWhy+H20nYu19+Km+gFfwNO4TEqyszkMcgBDYQjmPJ61erHxuT2ESJXhlhrO7I5EFIlZ+qGR8oVA== dependencies: - "@typescript-eslint/types" "6.17.0" - "@typescript-eslint/visitor-keys" "6.17.0" + "@typescript-eslint/types" "6.19.1" + "@typescript-eslint/visitor-keys" "6.19.1" debug "^4.3.4" globby "^11.1.0" is-glob "^4.0.3" @@ -1602,25 +1607,25 @@ semver "^7.5.4" ts-api-utils "^1.0.1" -"@typescript-eslint/utils@6.17.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-6.17.0.tgz#f2b16d4c9984474656c420438cdede7eccd4079e" - integrity sha512-LofsSPjN/ITNkzV47hxas2JCsNCEnGhVvocfyOcLzT9c/tSZE7SfhS/iWtzP1lKNOEfLhRTZz6xqI8N2RzweSQ== +"@typescript-eslint/utils@6.19.1": + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/utils/-/utils-6.19.1.tgz#df93497f9cfddde2bcc2a591da80536e68acd151" + integrity sha512-JvjfEZuP5WoMqwh9SPAPDSHSg9FBHHGhjPugSRxu5jMfjvBpq5/sGTD+9M9aQ5sh6iJ8AY/Kk/oUYVEMAPwi7w== dependencies: "@eslint-community/eslint-utils" "^4.4.0" "@types/json-schema" "^7.0.12" "@types/semver" "^7.5.0" - "@typescript-eslint/scope-manager" "6.17.0" - "@typescript-eslint/types" "6.17.0" - "@typescript-eslint/typescript-estree" "6.17.0" + "@typescript-eslint/scope-manager" "6.19.1" + "@typescript-eslint/types" "6.19.1" + "@typescript-eslint/typescript-estree" "6.19.1" semver "^7.5.4" -"@typescript-eslint/visitor-keys@6.17.0": - version "6.17.0" - resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-6.17.0.tgz#3ed043709c39b43ec1e58694f329e0b0430c26b6" - integrity sha512-H6VwB/k3IuIeQOyYczyyKN8wH6ed8EwliaYHLxOIhyF0dYEIsN8+Bk3GE19qafeMKyZJJHP8+O1HiFhFLUNKSg== +"@typescript-eslint/visitor-keys@6.19.1": + version "6.19.1" + resolved "https://registry.yarnpkg.com/@typescript-eslint/visitor-keys/-/visitor-keys-6.19.1.tgz#2164073ed4fc34a5ff3b5e25bb5a442100454c4c" + integrity sha512-gkdtIO+xSO/SmI0W68DBg4u1KElmIUo3vXzgHyGPs6cxgB0sa3TlptRAAE0hUY1hM6FcDKEv7aIwiTGm76cXfQ== dependencies: - "@typescript-eslint/types" "6.17.0" + "@typescript-eslint/types" "6.19.1" eslint-visitor-keys "^3.4.1" "@ungap/structured-clone@^1.2.0": @@ -1871,9 +1876,9 @@ callsites@^3.0.0: integrity sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ== caniuse-lite@^1.0.30001565: - version "1.0.30001572" - resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001572.tgz#1ccf7dc92d2ee2f92ed3a54e11b7b4a3041acfa0" - integrity sha512-1Pbh5FLmn5y4+QhNyJE9j3/7dK44dGB83/ZMjv/qJk86TvDbjk0LosiZo0i0WB0Vx607qMX9jYrn1VLHCkN4rw== + version "1.0.30001579" + resolved "https://registry.yarnpkg.com/caniuse-lite/-/caniuse-lite-1.0.30001579.tgz#45c065216110f46d6274311a4b3fcf6278e0852a" + integrity sha512-u5AUVkixruKHJjw/pj9wISlcMpgFWzSrczLZbrqBSxukQixmg0SJ5sZTpvaFvxU0HoQKd4yoyAogyrAz9pzJnA== chalk@^2.4.2: version "2.4.2" @@ -1987,7 +1992,7 @@ debug@^3.2.7: dependencies: ms "^2.1.1" -debug@^4.1.0, debug@^4.1.1, debug@^4.3.1, debug@^4.3.2, debug@^4.3.4: +debug@^4.1.0, debug@^4.3.1, debug@^4.3.2, debug@^4.3.4: version "4.3.4" resolved "https://registry.yarnpkg.com/debug/-/debug-4.3.4.tgz#1319f6579357f2338d3337d2cdd4914bb5dcc865" integrity sha512-PRWFHuSU3eDtQJPvnNY7Jcket1j0t5OuOsFzPPzsekD52Zl8qUfFIPEiswXqIvHWGVHOgX+7G/vCNNhehwxfkQ== @@ -2044,9 +2049,9 @@ doctrine@^3.0.0: esutils "^2.0.2" electron-to-chromium@^1.4.601: - version "1.4.617" - resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.617.tgz#3b0dde6c54e5f0f26db75ce6c6ae751e5df4bf75" - integrity sha512-sYNE3QxcDS4ANW1k4S/wWYMXjCVcFSOX3Bg8jpuMFaXt/x8JCmp0R1Xe1ZXDX4WXnSRBf+GJ/3eGWicUuQq5cg== + version "1.4.643" + resolved "https://registry.yarnpkg.com/electron-to-chromium/-/electron-to-chromium-1.4.643.tgz#081a20c5534db91e66ef094f68624960f674768f" + integrity sha512-QHscvvS7gt155PtoRC0dR2ilhL8E9LHhfTQEq1uD5AL0524rBLAwpAREFH06f87/e45B9XkR6Ki5dbhbCsVEIg== error-ex@^1.3.1: version "1.3.2" @@ -2146,33 +2151,33 @@ es-to-primitive@^1.2.1: is-symbol "^1.0.2" esbuild@^0.19.3: - version "0.19.11" - resolved "https://registry.yarnpkg.com/esbuild/-/esbuild-0.19.11.tgz#4a02dca031e768b5556606e1b468fe72e3325d96" - integrity sha512-HJ96Hev2hX/6i5cDVwcqiJBBtuo9+FeIJOtZ9W1kA5M6AMJRHUZlpYZ1/SbEwtO0ioNAW8rUooVpC/WehY2SfA== + version "0.19.12" + resolved "https://registry.yarnpkg.com/esbuild/-/esbuild-0.19.12.tgz#dc82ee5dc79e82f5a5c3b4323a2a641827db3e04" + integrity sha512-aARqgq8roFBj054KvQr5f1sFu0D65G+miZRCuJyJ0G13Zwx7vRar5Zhn2tkQNzIXcBrNVsv/8stehpj+GAjgbg== optionalDependencies: - "@esbuild/aix-ppc64" "0.19.11" - "@esbuild/android-arm" "0.19.11" - "@esbuild/android-arm64" "0.19.11" - "@esbuild/android-x64" "0.19.11" - "@esbuild/darwin-arm64" "0.19.11" - "@esbuild/darwin-x64" "0.19.11" - "@esbuild/freebsd-arm64" "0.19.11" - "@esbuild/freebsd-x64" "0.19.11" - "@esbuild/linux-arm" "0.19.11" - "@esbuild/linux-arm64" "0.19.11" - "@esbuild/linux-ia32" "0.19.11" - "@esbuild/linux-loong64" "0.19.11" - "@esbuild/linux-mips64el" "0.19.11" - "@esbuild/linux-ppc64" "0.19.11" - "@esbuild/linux-riscv64" "0.19.11" - "@esbuild/linux-s390x" "0.19.11" - "@esbuild/linux-x64" "0.19.11" - "@esbuild/netbsd-x64" "0.19.11" - "@esbuild/openbsd-x64" "0.19.11" - "@esbuild/sunos-x64" "0.19.11" - "@esbuild/win32-arm64" "0.19.11" - "@esbuild/win32-ia32" "0.19.11" - "@esbuild/win32-x64" "0.19.11" + "@esbuild/aix-ppc64" "0.19.12" + "@esbuild/android-arm" "0.19.12" + "@esbuild/android-arm64" "0.19.12" + "@esbuild/android-x64" "0.19.12" + "@esbuild/darwin-arm64" "0.19.12" + "@esbuild/darwin-x64" "0.19.12" + "@esbuild/freebsd-arm64" "0.19.12" + "@esbuild/freebsd-x64" "0.19.12" + "@esbuild/linux-arm" "0.19.12" + "@esbuild/linux-arm64" "0.19.12" + "@esbuild/linux-ia32" "0.19.12" + "@esbuild/linux-loong64" "0.19.12" + "@esbuild/linux-mips64el" "0.19.12" + "@esbuild/linux-ppc64" "0.19.12" + "@esbuild/linux-riscv64" "0.19.12" + "@esbuild/linux-s390x" "0.19.12" + "@esbuild/linux-x64" "0.19.12" + "@esbuild/netbsd-x64" "0.19.12" + "@esbuild/openbsd-x64" "0.19.12" + "@esbuild/sunos-x64" "0.19.12" + "@esbuild/win32-arm64" "0.19.12" + "@esbuild/win32-ia32" "0.19.12" + "@esbuild/win32-x64" "0.19.12" escalade@^3.1.1: version "3.1.1" @@ -2195,9 +2200,9 @@ eslint-compat-utils@^0.1.2: integrity sha512-Jia4JDldWnFNIru1Ehx1H5s9/yxiRHY/TimCuUc0jNexew3cF1gI6CYZil1ociakfWO3rRqFjl1mskBblB3RYg== eslint-config-standard-with-typescript@^43.0.0: - version "43.0.0" - resolved "https://registry.yarnpkg.com/eslint-config-standard-with-typescript/-/eslint-config-standard-with-typescript-43.0.0.tgz#e3d336b949e621a79b9150585777cdc9808e37d7" - integrity sha512-AT0qK01M5bmsWiE3UZvaQO5da1y1n6uQckAKqGNe6zPW5IOzgMLXZxw77nnFm+C11nxAZXsCPrbsgJhSrGfX6Q== + version "43.0.1" + resolved "https://registry.yarnpkg.com/eslint-config-standard-with-typescript/-/eslint-config-standard-with-typescript-43.0.1.tgz#977862d7d41b0e1f27f399137bbf7b2e017037ff" + integrity sha512-WfZ986+qzIzX6dcr4yGUyVb/l9N3Z8wPXCc5z/70fljs3UbWhhV+WxrfgsqMToRzuuyX9MqZ974pq2UPhDTOcA== dependencies: "@typescript-eslint/parser" "^6.4.0" eslint-config-standard "17.1.0" @@ -2256,9 +2261,9 @@ eslint-plugin-import@^2.25.2: tsconfig-paths "^3.15.0" "eslint-plugin-n@^15.0.0 || ^16.0.0 ": - version "16.6.1" - resolved "https://registry.yarnpkg.com/eslint-plugin-n/-/eslint-plugin-n-16.6.1.tgz#b16e0033bc9ce592b1c3512cb1cee24f84ecb5ae" - integrity sha512-M1kE5bVQRLBMDYRZwDhWzlzbp370SRRRC1MHqq4I3L2Tatey+9/2csc5mwLDPlmhJaDvkojbrNUME5/llpRyDg== + version "16.6.2" + resolved "https://registry.yarnpkg.com/eslint-plugin-n/-/eslint-plugin-n-16.6.2.tgz#6a60a1a376870064c906742272074d5d0b412b0b" + integrity sha512-6TyDmZ1HXoFQXnhCTUjVFULReoBPOAjpuiKELMkeP40yffI/1ZRO+d9ug/VC6fqISo2WkuIBk3cvuRPALaWlOQ== dependencies: "@eslint-community/eslint-utils" "^4.4.0" builtins "^5.0.1" @@ -2488,9 +2493,9 @@ for-each@^0.3.3: is-callable "^1.1.3" framer-motion@^10.16.16: - version "10.17.0" - resolved "https://registry.yarnpkg.com/framer-motion/-/framer-motion-10.17.0.tgz#56fe93b1ce32bdfe8c39e1b0dca23b5222f73a46" - integrity sha512-92brXaYasyEwaPV7tnHnc6MKxdN84CxWE1aZ80q/mlS+wQo0rxp/pmjGt5hdAEK5RCKJsWToI+MyIcGoA91Msg== + version "10.18.0" + resolved "https://registry.yarnpkg.com/framer-motion/-/framer-motion-10.18.0.tgz#1f4fc51403996ea7170af885bd44a7079d255950" + integrity sha512-oGlDh1Q1XqYPksuTD/usb0I70hq95OUzmL9+6Zd+Hs4XV0oaISBa/UUMSjYiq6m8EUF32132mOJ8xVZS+I0S6w== dependencies: tslib "^2.4.0" optionalDependencies: @@ -2652,7 +2657,7 @@ has-flag@^4.0.0: resolved "https://registry.yarnpkg.com/has-flag/-/has-flag-4.0.0.tgz#944771fd9c81c81265c4d6941860da06bb59479b" integrity sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ== -has-property-descriptors@^1.0.0: +has-property-descriptors@^1.0.0, has-property-descriptors@^1.0.1: version "1.0.1" resolved "https://registry.yarnpkg.com/has-property-descriptors/-/has-property-descriptors-1.0.1.tgz#52ba30b6c5ec87fd89fa574bc1c39125c6f65340" integrity sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg== @@ -3269,9 +3274,9 @@ picomatch@^2.3.1: integrity sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA== postcss@^8.4.32: - version "8.4.32" - resolved "https://registry.yarnpkg.com/postcss/-/postcss-8.4.32.tgz#1dac6ac51ab19adb21b8b34fd2d93a86440ef6c9" - integrity sha512-D/kj5JNu6oo2EIy+XL/26JEDTlIbB8hw85G8StOE6L74RQAVVP5rej6wxCNqyMbR4RkPfqvezVbPw81Ngd6Kcw== + version "8.4.33" + resolved "https://registry.yarnpkg.com/postcss/-/postcss-8.4.33.tgz#1378e859c9f69bf6f638b990a0212f43e2aaa742" + integrity sha512-Kkpbhhdjw2qQs2O2DGX+8m5OVqEcbB9HRBvuYM9pgrjEFUg30A9LmXNlTAUj4S9kgtGyrMbTzVjH7E+s5Re2yg== dependencies: nanoid "^3.3.7" picocolors "^1.0.0" @@ -3322,9 +3327,9 @@ react-fast-compare@3.2.2: integrity sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ== react-focus-lock@^2.9.4: - version "2.9.6" - resolved "https://registry.yarnpkg.com/react-focus-lock/-/react-focus-lock-2.9.6.tgz#cad168a150fdd72d5ab2419ba8e62780788011b1" - integrity sha512-B7gYnCjHNrNYwY2juS71dHbf0+UpXXojt02svxybj8N5bxceAkzPChKEncHuratjUHkIFNCn06k2qj1DRlzTug== + version "2.9.7" + resolved "https://registry.yarnpkg.com/react-focus-lock/-/react-focus-lock-2.9.7.tgz#778358691b55db38a9954a989341048bd4065935" + integrity sha512-EfhX040SELLqnQ9JftqsmQCG49iByg8F5X5m19Er+n371OaETZ35dlNPZrLOOTlnnwD4c2Zv0KDgabDTc7dPHw== dependencies: "@babel/runtime" "^7.0.0" focus-lock "^1.0.0" @@ -3363,19 +3368,19 @@ react-remove-scroll@^2.5.6: use-sidecar "^1.1.2" react-router-dom@^6.21.0: - version "6.21.1" - resolved "https://registry.yarnpkg.com/react-router-dom/-/react-router-dom-6.21.1.tgz#58b459d2fe1841388c95bb068f85128c45e27349" - integrity sha512-QCNrtjtDPwHDO+AO21MJd7yIcr41UetYt5jzaB9Y1UYaPTCnVuJq6S748g1dE11OQlCFIQg+RtAA1SEZIyiBeA== + version "6.21.3" + resolved "https://registry.yarnpkg.com/react-router-dom/-/react-router-dom-6.21.3.tgz#ef3a7956a3699c7b82c21fcb3dbc63c313ed8c5d" + integrity sha512-kNzubk7n4YHSrErzjLK72j0B5i969GsuCGazRl3G6j1zqZBLjuSlYBdVdkDOgzGdPIffUOc9nmgiadTEVoq91g== dependencies: - "@remix-run/router" "1.14.1" - react-router "6.21.1" + "@remix-run/router" "1.14.2" + react-router "6.21.3" -react-router@6.21.1: - version "6.21.1" - resolved "https://registry.yarnpkg.com/react-router/-/react-router-6.21.1.tgz#8db7ee8d7cfc36513c9a66b44e0897208c33be34" - integrity sha512-W0l13YlMTm1YrpVIOpjCADJqEUpz1vm+CMo47RuFX4Ftegwm6KOYsL5G3eiE52jnJpKvzm6uB/vTKTPKM8dmkA== +react-router@6.21.3: + version "6.21.3" + resolved "https://registry.yarnpkg.com/react-router/-/react-router-6.21.3.tgz#8086cea922c2bfebbb49c6594967418f1f167d70" + integrity sha512-a0H638ZXULv1OdkmiK6s6itNhoy33ywxmUFT/xtSoVyf9VnC7n7+VT4LjVzdIHSaF5TIh9ylUgxMXksHTgGrKg== dependencies: - "@remix-run/router" "1.14.1" + "@remix-run/router" "1.14.2" react-style-singleton@^2.2.1: version "2.2.1" @@ -3460,23 +3465,25 @@ rimraf@^3.0.2: glob "^7.1.3" rollup@^4.2.0: - version "4.9.2" - resolved "https://registry.yarnpkg.com/rollup/-/rollup-4.9.2.tgz#19d730219b7ec5f51372c6cf15cfb841990489fe" - integrity sha512-66RB8OtFKUTozmVEh3qyNfH+b+z2RXBVloqO2KCC/pjFaGaHtxP9fVfOQKPSGXg2mElmjmxjW/fZ7iKrEpMH5Q== + version "4.9.6" + resolved "https://registry.yarnpkg.com/rollup/-/rollup-4.9.6.tgz#4515facb0318ecca254a2ee1315e22e09efc50a0" + integrity sha512-05lzkCS2uASX0CiLFybYfVkwNbKZG5NFQ6Go0VWyogFTXXbR039UVsegViTntkk4OglHBdF54ccApXRRuXRbsg== + dependencies: + "@types/estree" "1.0.5" optionalDependencies: - "@rollup/rollup-android-arm-eabi" "4.9.2" - "@rollup/rollup-android-arm64" "4.9.2" - "@rollup/rollup-darwin-arm64" "4.9.2" - "@rollup/rollup-darwin-x64" "4.9.2" - "@rollup/rollup-linux-arm-gnueabihf" "4.9.2" - "@rollup/rollup-linux-arm64-gnu" "4.9.2" - "@rollup/rollup-linux-arm64-musl" "4.9.2" - "@rollup/rollup-linux-riscv64-gnu" "4.9.2" - "@rollup/rollup-linux-x64-gnu" "4.9.2" - "@rollup/rollup-linux-x64-musl" "4.9.2" - "@rollup/rollup-win32-arm64-msvc" "4.9.2" - "@rollup/rollup-win32-ia32-msvc" "4.9.2" - "@rollup/rollup-win32-x64-msvc" "4.9.2" + "@rollup/rollup-android-arm-eabi" "4.9.6" + "@rollup/rollup-android-arm64" "4.9.6" + "@rollup/rollup-darwin-arm64" "4.9.6" + "@rollup/rollup-darwin-x64" "4.9.6" + "@rollup/rollup-linux-arm-gnueabihf" "4.9.6" + "@rollup/rollup-linux-arm64-gnu" "4.9.6" + "@rollup/rollup-linux-arm64-musl" "4.9.6" + "@rollup/rollup-linux-riscv64-gnu" "4.9.6" + "@rollup/rollup-linux-x64-gnu" "4.9.6" + "@rollup/rollup-linux-x64-musl" "4.9.6" + "@rollup/rollup-win32-arm64-msvc" "4.9.6" + "@rollup/rollup-win32-ia32-msvc" "4.9.6" + "@rollup/rollup-win32-x64-msvc" "4.9.6" fsevents "~2.3.2" run-parallel@^1.1.9: @@ -3487,22 +3494,22 @@ run-parallel@^1.1.9: queue-microtask "^1.2.2" safe-array-concat@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/safe-array-concat/-/safe-array-concat-1.0.1.tgz#91686a63ce3adbea14d61b14c99572a8ff84754c" - integrity sha512-6XbUAseYE2KtOuGueyeobCySj9L4+66Tn6KQMOPQJrAJEowYKW/YR/MGJZl7FdydUdaFu4LYyDZjxf4/Nmo23Q== + version "1.1.0" + resolved "https://registry.yarnpkg.com/safe-array-concat/-/safe-array-concat-1.1.0.tgz#8d0cae9cb806d6d1c06e08ab13d847293ebe0692" + integrity sha512-ZdQ0Jeb9Ofti4hbt5lX3T2JcAamT9hfzYU1MNB+z/jaEbB6wfFfPIR/zEORmZqobkCCJhSjodobH6WHNmJ97dg== dependencies: - call-bind "^1.0.2" - get-intrinsic "^1.2.1" + call-bind "^1.0.5" + get-intrinsic "^1.2.2" has-symbols "^1.0.3" isarray "^2.0.5" safe-regex-test@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/safe-regex-test/-/safe-regex-test-1.0.0.tgz#793b874d524eb3640d1873aad03596db2d4f2295" - integrity sha512-JBUUzyOgEwXQY1NuPtvcj/qcBDbDmEvWufhlnXZIm75DEHp+afM1r1ujJpJsV/gSM4t59tpDyPi1sd6ZaPFfsA== + version "1.0.2" + resolved "https://registry.yarnpkg.com/safe-regex-test/-/safe-regex-test-1.0.2.tgz#3ba32bdb3ea35f940ee87e5087c60ee786c3f6c5" + integrity sha512-83S9w6eFq12BBIJYvjMux6/dkirb8+4zJRA9cxNBVb7Wq5fJBW+Xze48WqR8pxua7bDuAaaAxtVVd4Idjp1dBQ== dependencies: - call-bind "^1.0.2" - get-intrinsic "^1.1.3" + call-bind "^1.0.5" + get-intrinsic "^1.2.2" is-regex "^1.1.4" scheduler@^0.23.0: @@ -3525,14 +3532,15 @@ semver@^7.0.0, semver@^7.5.3, semver@^7.5.4: lru-cache "^6.0.0" set-function-length@^1.1.1: - version "1.1.1" - resolved "https://registry.yarnpkg.com/set-function-length/-/set-function-length-1.1.1.tgz#4bc39fafb0307224a33e106a7d35ca1218d659ed" - integrity sha512-VoaqjbBJKiWtg4yRcKBQ7g7wnGnLV3M8oLvVWwOk2PdYY6PEFegR1vezXR0tw6fZGF9csVakIRjrJiy2veSBFQ== + version "1.2.0" + resolved "https://registry.yarnpkg.com/set-function-length/-/set-function-length-1.2.0.tgz#2f81dc6c16c7059bda5ab7c82c11f03a515ed8e1" + integrity sha512-4DBHDoyHlM1IRPGYcoxexgh67y4ueR53FKV1yyxwFMY7aCqcN/38M1+SwZ/qJQ8iLv7+ck385ot4CcisOAPT9w== dependencies: define-data-property "^1.1.1" - get-intrinsic "^1.2.1" + function-bind "^1.1.2" + get-intrinsic "^1.2.2" gopd "^1.0.1" - has-property-descriptors "^1.0.0" + has-property-descriptors "^1.0.1" set-function-name@^2.0.0, set-function-name@^2.0.1: version "2.0.1" @@ -3811,9 +3819,9 @@ use-sidecar@^1.1.2: tslib "^2.0.0" vite@^5.0.8: - version "5.0.10" - resolved "https://registry.yarnpkg.com/vite/-/vite-5.0.10.tgz#1e13ef5c3cf5aa4eed81f5df6d107b3c3f1f6356" - integrity sha512-2P8J7WWgmc355HUMlFrwofacvr98DAjoE52BfdbwQtyLH06XKwaL/FMnmKM2crF0iX4MpmMKoDlNCB1ok7zHCw== + version "5.0.12" + resolved "https://registry.yarnpkg.com/vite/-/vite-5.0.12.tgz#8a2ffd4da36c132aec4adafe05d7adde38333c47" + integrity sha512-4hsnEkG3q0N4Tzf1+t6NdN9dg/L3BM+q8SWgbSPnJvrgH2kgdyzfVJwbR1ic69/4uMJJ/3dqDZZE5/WwqW8U1w== dependencies: esbuild "^0.19.3" postcss "^8.4.32" diff --git a/examples/skywalking/Dockerfile-elasticsearch b/examples/skywalking/Dockerfile-elasticsearch index 04285912d22d6..d7cda60fda582 100644 --- a/examples/skywalking/Dockerfile-elasticsearch +++ b/examples/skywalking/Dockerfile-elasticsearch @@ -1 +1 @@ -FROM elasticsearch:8.11.3@sha256:58a3a280935d830215802322e9a0373faaacdfd646477aa7e718939c2f29292a +FROM elasticsearch:8.12.0@sha256:2529e4b8062e4b9f0a31bea3ee797a58dae4cfe2d2b5879b4a1b03250c7ad31c diff --git a/examples/zipkin/Dockerfile-zipkin b/examples/zipkin/Dockerfile-zipkin index 6766427249a8e..cab650491ebba 100644 --- a/examples/zipkin/Dockerfile-zipkin +++ b/examples/zipkin/Dockerfile-zipkin @@ -1 +1 @@ -FROM openzipkin/zipkin:latest@sha256:4fb7fa559331b9f041b79a64b2116008479837f65cfb5c40d28825c692dd7709 +FROM openzipkin/zipkin:latest@sha256:4c7427bcdbaf27a49ed0a4c24b026704a78134c58d35ff970c983580e37276cf diff --git a/mobile/.bazelrc b/mobile/.bazelrc index f9880490b7790..31e14663c3502 100644 --- a/mobile/.bazelrc +++ b/mobile/.bazelrc @@ -73,9 +73,10 @@ build:mobile-dbg-ios --config=mobile-dbg-common build:mobile-dbg-ios --config=ios # Default flags for Android tests -# TODO(jpsim): Explicitly register test extensions for Android tests -# https://github.com/envoyproxy/envoy/issues/24977 -build:test-android --define=static_extension_registration=enabled +build:mobile-test-android --define=static_extension_registration=disabled + +# Default flags for iOS tests. +build:mobile-test-ios --config=ios # Locally-runnable ASAN config for MacOS & Linux with standard dev environment # See also: @@ -252,7 +253,7 @@ build:mobile-remote-ci --config=remote-ci build:mobile-remote-ci-android --config=mobile-remote-ci test:mobile-remote-ci-android --build_tests_only -test:mobile-remote-ci-android --config=test-android +test:mobile-remote-ci-android --config=mobile-test-android test:mobile-remote-ci-android --config=mobile-remote-ci test:mobile-remote-ci-android --define=signal_trace=disabled @@ -294,7 +295,7 @@ build:mobile-remote-ci-macos-kotlin --define=envoy_yaml=disabled build:mobile-remote-ci-macos-kotlin --@com_envoyproxy_protoc_gen_validate//bazel:template-flavor= build:mobile-remote-ci-macos-swift --config=mobile-remote-ci-macos -build:mobile-remote-ci-macos-swift --config=ios +build:mobile-remote-ci-macos-swift --config=mobile-test-ios build:mobile-remote-ci-macos-swift --config=mobile-remote-ci-macos build:mobile-remote-ci-macos-swift --define=signal_trace=disabled build:mobile-remote-ci-macos-swift --define=envoy_mobile_request_compression=disabled @@ -311,7 +312,7 @@ test:mobile-remote-ci-core --test_env=ENVOY_IP_TEST_VERSIONS=v4only test:mobile-remote-ci-core --define=envoy_yaml=disabled build:mobile-remote-ci-macos-ios --config=mobile-remote-ci-macos -build:mobile-remote-ci-macos-ios --config=ios +build:mobile-remote-ci-macos-ios --config=mobile-test-ios build:mobile-remote-ci-macos-ios-admin --config=mobile-remote-ci-macos-ios build:mobile-remote-ci-macos-ios-admin --define=admin_functionality=enabled diff --git a/mobile/bazel/BUILD b/mobile/bazel/BUILD index f5f28ce578955..76e472c619cd1 100644 --- a/mobile/bazel/BUILD +++ b/mobile/bazel/BUILD @@ -37,11 +37,11 @@ alias( actual = "@bazel_tools//tools/zip:zipper", ) -# Don't depend on these directly, use //library/common/jni:jni_import_lib. +# Don't depend on these directly, use //library/jni:jni_import_lib. alias( name = "jni", actual = "@bazel_tools//tools/jdk:jni", - visibility = ["//library/common/jni/import:__pkg__"], + visibility = ["//library/jni/import:__pkg__"], ) # autoformat requires that there be no @bazel_tools references outside of //bazel, diff --git a/mobile/bazel/kotlin_test.bzl b/mobile/bazel/kotlin_test.bzl index 2eea069b7275b..0db4624029f2f 100644 --- a/mobile/bazel/kotlin_test.bzl +++ b/mobile/bazel/kotlin_test.bzl @@ -34,7 +34,7 @@ def _internal_kt_test(name, srcs, deps = [], data = [], jvm_flags = [], reposito # envoy_mobile_android_test. def jvm_flags(lib_name): return [ - "-Djava.library.path=library/common/jni:test/common/jni", + "-Djava.library.path=library/jni:test/jni", "-Denvoy_jni_library_name={}".format(lib_name), "-Xcheck:jni", ] + select({ diff --git a/mobile/ci/linux_ci_setup.sh b/mobile/ci/linux_ci_setup.sh index b4fb35ce27fe3..f8149613f449f 100755 --- a/mobile/ci/linux_ci_setup.sh +++ b/mobile/ci/linux_ci_setup.sh @@ -5,8 +5,8 @@ set -e # Set up necessary Android SDK and NDK. ANDROID_HOME=$ANDROID_SDK_ROOT SDKMANAGER="${ANDROID_SDK_ROOT}/cmdline-tools/latest/bin/sdkmanager" -"${SDKMANAGER}" --install "platforms;android-30" +"${SDKMANAGER}" --install "platform-tools" "platforms;android-30" "${SDKMANAGER}" --uninstall "ndk-bundle" "${SDKMANAGER}" --install "ndk;21.4.7075529" -"${SDKMANAGER}" --install "build-tools;30.0.3" +"${SDKMANAGER}" --install "build-tools;30.0.2" echo "ANDROID_NDK_HOME=${ANDROID_HOME}/ndk/21.4.7075529" >> "$GITHUB_ENV" diff --git a/mobile/ci/mac_ci_setup.sh b/mobile/ci/mac_ci_setup.sh index a9712563e4c92..f01a7ba449f17 100755 --- a/mobile/ci/mac_ci_setup.sh +++ b/mobile/ci/mac_ci_setup.sh @@ -61,11 +61,10 @@ if [[ "${1:-}" == "--android" ]]; then # https://github.com/actions/virtual-environments/issues/5595 ANDROID_HOME=$ANDROID_SDK_ROOT SDKMANAGER="${ANDROID_SDK_ROOT}/cmdline-tools/latest/bin/sdkmanager" - "${SDKMANAGER}" --install "platforms;android-30" + "${SDKMANAGER}" --install "platform-tools" "platforms;android-30" "${SDKMANAGER}" --uninstall "ndk-bundle" "${SDKMANAGER}" --install "ndk;21.4.7075529" - # Download and set up build-tools 30.0.3, 31.0.0 is missing dx.jar. - "${SDKMANAGER}" --install "build-tools;30.0.3" + "${SDKMANAGER}" --install "build-tools;30.0.2" ANDROID_NDK_HOME="${ANDROID_HOME}/ndk/21.4.7075529" export ANDROID_NDK_HOME fi diff --git a/mobile/docs/root/api/starting_envoy.rst b/mobile/docs/root/api/starting_envoy.rst index cb65abea481c2..f136b785c7770 100644 --- a/mobile/docs/root/api/starting_envoy.rst +++ b/mobile/docs/root/api/starting_envoy.rst @@ -236,9 +236,10 @@ Specify a closure to be called when Envoy's engine emits a log message. // Kotlin // This interface is pending for Kotlin + builder.setLogger { level, message -> /* log it */ } // Swift - builder.setLogger { msg in + builder.setLogger { level, msg in NSLog("Envoy log: \(msg)") } diff --git a/mobile/examples/kotlin/hello_world/MainActivity.kt b/mobile/examples/kotlin/hello_world/MainActivity.kt index c117ddb87304b..1a59ccf6916fe 100644 --- a/mobile/examples/kotlin/hello_world/MainActivity.kt +++ b/mobile/examples/kotlin/hello_world/MainActivity.kt @@ -64,7 +64,7 @@ class MainActivity : Activity() { Log.d("MainActivity", "Event emitted: ${entry.key}, ${entry.value}") } }) - .setLogger { Log.d("MainActivity", it) } + .setLogger { _, message -> Log.d("MainActivity", message) } .build() recyclerView = findViewById(R.id.recycler_view) as RecyclerView diff --git a/mobile/library/cc/BUILD b/mobile/library/cc/BUILD index 4b04dcb82b899..96f01b436fcd5 100644 --- a/mobile/library/cc/BUILD +++ b/mobile/library/cc/BUILD @@ -86,7 +86,6 @@ envoy_cc_library( "headers_builder.h", "key_value_store.h", "log_level.h", - "pulse_client.h", "request_headers.h", "request_headers_builder.h", "request_method.h", @@ -108,7 +107,7 @@ envoy_cc_library( repository = "@envoy", visibility = ["//visibility:public"], deps = [ - "//library/common:envoy_main_interface_lib_no_stamp", + "//library/common:internal_engine_lib_no_stamp", "//library/common/api:c_types", "//library/common/data:utility_lib", "//library/common/extensions/key_value/platform:config", diff --git a/mobile/library/cc/bridge_utility.h b/mobile/library/cc/bridge_utility.h index 0be9e0407854d..73b63f4c151cc 100644 --- a/mobile/library/cc/bridge_utility.h +++ b/mobile/library/cc/bridge_utility.h @@ -3,7 +3,7 @@ #include #include -#include "headers.h" +#include "library/cc/headers.h" #include "library/common/types/c_types.h" namespace Envoy { diff --git a/mobile/library/cc/engine.cc b/mobile/library/cc/engine.cc index 3283939837758..d94ce7480fe87 100644 --- a/mobile/library/cc/engine.cc +++ b/mobile/library/cc/engine.cc @@ -1,17 +1,15 @@ #include "engine.h" -#include "library/common/data/utility.h" -#include "library/common/engine.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" #include "library/common/types/c_types.h" namespace Envoy { namespace Platform { -Engine::Engine(::Envoy::Engine* engine) : engine_(engine), terminated_(false) {} +Engine::Engine(::Envoy::InternalEngine* engine) : engine_(engine) {} Engine::~Engine() { - if (!terminated_) { + if (!engine_->isTerminated()) { terminate(); } } @@ -24,28 +22,9 @@ StreamClientSharedPtr Engine::streamClient() { return std::make_shared(shared_from_this()); } -PulseClientSharedPtr Engine::pulseClient() { return std::make_shared(); } +std::string Engine::dumpStats() { return engine_->dumpStats(); } -std::string Engine::dumpStats() { - envoy_data data; - if (dump_stats(reinterpret_cast(engine_), &data) == ENVOY_FAILURE) { - return ""; - } - const std::string to_return = Data::Utility::copyToString(data); - release_envoy_data(data); - - return to_return; -} - -envoy_status_t Engine::terminate() { - if (terminated_) { - IS_ENVOY_BUG("attempted to double terminate engine"); - return ENVOY_FAILURE; - } - envoy_status_t ret = engine_->terminate(); - terminated_ = true; - return ret; -} +envoy_status_t Engine::terminate() { return engine_->terminate(); } } // namespace Platform } // namespace Envoy diff --git a/mobile/library/cc/engine.h b/mobile/library/cc/engine.h index eb78464ecd338..cefa8fa7552cf 100644 --- a/mobile/library/cc/engine.h +++ b/mobile/library/cc/engine.h @@ -2,13 +2,12 @@ #include +#include "library/cc/log_level.h" +#include "library/cc/stream_client.h" #include "library/common/types/c_types.h" -#include "log_level.h" -#include "pulse_client.h" -#include "stream_client.h" namespace Envoy { -class Engine; +class InternalEngine; class BaseClientIntegrationTest; namespace Platform { @@ -22,12 +21,12 @@ class Engine : public std::enable_shared_from_this { std::string dumpStats(); StreamClientSharedPtr streamClient(); - PulseClientSharedPtr pulseClient(); envoy_status_t terminate(); + Envoy::InternalEngine* engine() { return engine_; } private: - Engine(::Envoy::Engine* engine); + Engine(::Envoy::InternalEngine* engine); // required to access private constructor friend class EngineBuilder; @@ -36,13 +35,11 @@ class Engine : public std::enable_shared_from_this { // for testing only friend class ::Envoy::BaseClientIntegrationTest; - Envoy::Engine* engine_; + Envoy::InternalEngine* engine_; StreamClientSharedPtr stream_client_; - PulseClientSharedPtr pulse_client_; - bool terminated_; }; -using EngineSharedPtr = std::shared_ptr; +using InternalEngineSharedPtr = std::shared_ptr; } // namespace Platform } // namespace Envoy diff --git a/mobile/library/cc/engine_builder.cc b/mobile/library/cc/engine_builder.cc index cea99eaa3c2a3..888b4e98dcf3d 100644 --- a/mobile/library/cc/engine_builder.cc +++ b/mobile/library/cc/engine_builder.cc @@ -24,13 +24,12 @@ #include "absl/strings/str_join.h" #include "absl/strings/str_replace.h" #include "fmt/core.h" -#include "library/common/engine.h" +#include "library/common/internal_engine.h" #include "library/common/extensions/cert_validator/platform_bridge/platform_bridge.pb.h" #include "library/common/extensions/filters/http/local_error/filter.pb.h" #include "library/common/extensions/filters/http/network_configuration/filter.pb.h" #include "library/common/extensions/filters/http/socket_tag/filter.pb.h" #include "library/common/extensions/key_value/platform/platform.pb.h" -#include "library/common/main_interface.h" namespace Envoy { namespace Platform { @@ -830,15 +829,15 @@ EngineSharedPtr EngineBuilder::build() { envoy_event_tracker null_tracker{}; - Envoy::Engine* envoy_engine = - new Envoy::Engine(callbacks_->asEnvoyEngineCallbacks(), null_logger, null_tracker); + Envoy::InternalEngine* envoy_engine = + new Envoy::InternalEngine(callbacks_->asEnvoyEngineCallbacks(), null_logger, null_tracker); for (const auto& [name, store] : key_value_stores_) { // TODO(goaway): This leaks, but it's tied to the life of the engine. if (!Api::External::retrieveApi(name, true)) { auto* api = new envoy_kv_store(); *api = store->asEnvoyKeyValueStore(); - register_platform_api(name.c_str(), api); + Envoy::Api::External::registerApi(name.c_str(), api); } } @@ -847,7 +846,7 @@ EngineSharedPtr EngineBuilder::build() { if (!Api::External::retrieveApi(name, true)) { auto* api = new envoy_string_accessor(); *api = StringAccessor::asEnvoyStringAccessor(accessor); - register_platform_api(name.c_str(), api); + Envoy::Api::External::registerApi(name.c_str(), api); } } diff --git a/mobile/library/cc/engine_builder.h b/mobile/library/cc/engine_builder.h index 8e4b8b42aaa66..e43aba4b97c5e 100644 --- a/mobile/library/cc/engine_builder.h +++ b/mobile/library/cc/engine_builder.h @@ -13,12 +13,12 @@ #include "absl/container/flat_hash_map.h" #include "absl/types/optional.h" #include "direct_response_testing.h" -#include "engine.h" -#include "engine_callbacks.h" -#include "key_value_store.h" +#include "library/cc/engine.h" +#include "library/cc/engine_callbacks.h" +#include "library/cc/key_value_store.h" +#include "library/cc/log_level.h" +#include "library/cc/string_accessor.h" #include "library/common/types/matcher_data.h" -#include "log_level.h" -#include "string_accessor.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/engine_callbacks.cc b/mobile/library/cc/engine_callbacks.cc index 12995f293950a..ba570a8d1fe61 100644 --- a/mobile/library/cc/engine_callbacks.cc +++ b/mobile/library/cc/engine_callbacks.cc @@ -1,4 +1,4 @@ -#include "engine_callbacks.h" +#include "library/cc/engine_callbacks.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/engine_callbacks.h b/mobile/library/cc/engine_callbacks.h index 61c1d196f4021..ee82028c84f43 100644 --- a/mobile/library/cc/engine_callbacks.h +++ b/mobile/library/cc/engine_callbacks.h @@ -3,7 +3,7 @@ #include #include -#include "engine.h" +#include "library/cc/engine.h" #include "library/common/types/c_types.h" namespace Envoy { diff --git a/mobile/library/cc/headers.cc b/mobile/library/cc/headers.cc index af18119172828..dd8c5f10a0bc5 100644 --- a/mobile/library/cc/headers.cc +++ b/mobile/library/cc/headers.cc @@ -1,4 +1,4 @@ -#include "headers.h" +#include "library/cc/headers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/headers_builder.cc b/mobile/library/cc/headers_builder.cc index 3469095e4853d..55595a22b0f39 100644 --- a/mobile/library/cc/headers_builder.cc +++ b/mobile/library/cc/headers_builder.cc @@ -1,4 +1,4 @@ -#include "headers_builder.h" +#include "library/cc/headers_builder.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/pulse_client.h b/mobile/library/cc/pulse_client.h deleted file mode 100644 index c54988ebcc5c5..0000000000000 --- a/mobile/library/cc/pulse_client.h +++ /dev/null @@ -1,23 +0,0 @@ -#pragma once - -#include - -namespace Envoy { -namespace Platform { - -// TODO(crockeo): although this is stubbed out since it's in the main directory, it depends on -// objects defined under stats. this will not be fully stubbed until stats is stubbed - -class PulseClient { -public: - // TODO: when these are commented out, you're going to have to - // #include "envoy/common/pure.h" - // - // virtual Counter counter(Element element) PURE; - // virtual Gauge gauge(Element element) PURE; -}; - -using PulseClientSharedPtr = std::shared_ptr; - -} // namespace Platform -} // namespace Envoy diff --git a/mobile/library/cc/request_headers.cc b/mobile/library/cc/request_headers.cc index 2563b5769230b..1257e0e621a06 100644 --- a/mobile/library/cc/request_headers.cc +++ b/mobile/library/cc/request_headers.cc @@ -1,4 +1,4 @@ -#include "request_headers.h" +#include "library/cc/request_headers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/request_headers.h b/mobile/library/cc/request_headers.h index a0836f44ce698..1a88c10f4f2dc 100644 --- a/mobile/library/cc/request_headers.h +++ b/mobile/library/cc/request_headers.h @@ -3,10 +3,10 @@ #include #include "absl/types/optional.h" -#include "headers.h" -#include "request_headers_builder.h" -#include "request_method.h" -#include "retry_policy.h" +#include "library/cc/headers.h" +#include "library/cc/request_headers_builder.h" +#include "library/cc/request_method.h" +#include "library/cc/retry_policy.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/request_headers_builder.h b/mobile/library/cc/request_headers_builder.h index 4daa65196e367..db565ce2a83af 100644 --- a/mobile/library/cc/request_headers_builder.h +++ b/mobile/library/cc/request_headers_builder.h @@ -2,9 +2,9 @@ #include -#include "headers_builder.h" -#include "request_headers.h" -#include "request_method.h" +#include "library/cc/headers_builder.h" +#include "library/cc/request_headers.h" +#include "library/cc/request_method.h" #include "retry_policy.h" namespace Envoy { diff --git a/mobile/library/cc/request_trailers.h b/mobile/library/cc/request_trailers.h index ba3915b4ad346..bf3cb548c1dba 100644 --- a/mobile/library/cc/request_trailers.h +++ b/mobile/library/cc/request_trailers.h @@ -1,7 +1,7 @@ #pragma once -#include "request_trailers_builder.h" -#include "trailers.h" +#include "library/cc/request_trailers_builder.h" +#include "library/cc/trailers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/request_trailers_builder.cc b/mobile/library/cc/request_trailers_builder.cc index e11f6f70c7ae9..eb4a3f1444260 100644 --- a/mobile/library/cc/request_trailers_builder.cc +++ b/mobile/library/cc/request_trailers_builder.cc @@ -1,4 +1,4 @@ -#include "request_trailers_builder.h" +#include "library/cc/request_trailers_builder.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/request_trailers_builder.h b/mobile/library/cc/request_trailers_builder.h index 3f149e5c36666..77df313df1988 100644 --- a/mobile/library/cc/request_trailers_builder.h +++ b/mobile/library/cc/request_trailers_builder.h @@ -1,7 +1,7 @@ #pragma once -#include "headers_builder.h" -#include "request_trailers.h" +#include "library/cc/headers_builder.h" +#include "library/cc/request_trailers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_headers.cc b/mobile/library/cc/response_headers.cc index 1dcf44cee0746..dadac12c53ae3 100644 --- a/mobile/library/cc/response_headers.cc +++ b/mobile/library/cc/response_headers.cc @@ -1,4 +1,4 @@ -#include "response_headers.h" +#include "library/cc/response_headers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_headers.h b/mobile/library/cc/response_headers.h index b1e029bd89408..34f4d11c955e1 100644 --- a/mobile/library/cc/response_headers.h +++ b/mobile/library/cc/response_headers.h @@ -1,7 +1,7 @@ #pragma once -#include "headers.h" -#include "response_headers_builder.h" +#include "library/cc/headers.h" +#include "library/cc/response_headers_builder.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_headers_builder.cc b/mobile/library/cc/response_headers_builder.cc index b4a0300303d02..a92887e59f8c8 100644 --- a/mobile/library/cc/response_headers_builder.cc +++ b/mobile/library/cc/response_headers_builder.cc @@ -1,4 +1,4 @@ -#include "response_headers_builder.h" +#include "library/cc/response_headers_builder.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_headers_builder.h b/mobile/library/cc/response_headers_builder.h index 2118832ce9031..8b33c4cd719d8 100644 --- a/mobile/library/cc/response_headers_builder.h +++ b/mobile/library/cc/response_headers_builder.h @@ -1,7 +1,7 @@ #pragma once -#include "headers_builder.h" -#include "response_headers.h" +#include "library/cc/headers_builder.h" +#include "library/cc/response_headers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_trailers.cc b/mobile/library/cc/response_trailers.cc index 9cacd43464130..47869d8a61934 100644 --- a/mobile/library/cc/response_trailers.cc +++ b/mobile/library/cc/response_trailers.cc @@ -1,4 +1,4 @@ -#include "response_trailers.h" +#include "library/cc/response_trailers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_trailers.h b/mobile/library/cc/response_trailers.h index 7ef00ddde45fd..8e4a61713a770 100644 --- a/mobile/library/cc/response_trailers.h +++ b/mobile/library/cc/response_trailers.h @@ -1,7 +1,7 @@ #pragma once -#include "response_trailers_builder.h" -#include "trailers.h" +#include "library/cc/response_trailers_builder.h" +#include "library/cc/trailers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_trailers_builder.cc b/mobile/library/cc/response_trailers_builder.cc index 197d2ad940f47..0ec526f23a80b 100644 --- a/mobile/library/cc/response_trailers_builder.cc +++ b/mobile/library/cc/response_trailers_builder.cc @@ -1,4 +1,4 @@ -#include "response_trailers_builder.h" +#include "library/cc/response_trailers_builder.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/response_trailers_builder.h b/mobile/library/cc/response_trailers_builder.h index c3d8aee8d4fa6..668b5593180b7 100644 --- a/mobile/library/cc/response_trailers_builder.h +++ b/mobile/library/cc/response_trailers_builder.h @@ -1,7 +1,7 @@ #pragma once -#include "headers_builder.h" -#include "response_trailers.h" +#include "library/cc/headers_builder.h" +#include "library/cc/response_trailers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/retry_policy.cc b/mobile/library/cc/retry_policy.cc index 37f457a5ee394..c24642a52bc6b 100644 --- a/mobile/library/cc/retry_policy.cc +++ b/mobile/library/cc/retry_policy.cc @@ -1,4 +1,4 @@ -#include "retry_policy.h" +#include "library/cc/retry_policy.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/retry_policy.h b/mobile/library/cc/retry_policy.h index b6f76ad064e3c..edfd913798690 100644 --- a/mobile/library/cc/retry_policy.h +++ b/mobile/library/cc/retry_policy.h @@ -4,8 +4,8 @@ #include #include "absl/types/optional.h" -#include "headers.h" -#include "request_headers.h" +#include "library/cc/headers.h" +#include "library/cc/request_headers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/stream.cc b/mobile/library/cc/stream.cc index 7e46d0ad38b5c..09d49d046a0b6 100644 --- a/mobile/library/cc/stream.cc +++ b/mobile/library/cc/stream.cc @@ -1,39 +1,39 @@ #include "stream.h" -#include "bridge_utility.h" -#include "library/common/main_interface.h" +#include "library/cc/bridge_utility.h" +#include "library/common/internal_engine.h" #include "library/common/types/c_types.h" namespace Envoy { namespace Platform { -Stream::Stream(envoy_engine_t engine_handle, envoy_stream_t handle) - : engine_handle_(engine_handle), handle_(handle) {} +Stream::Stream(Envoy::InternalEngine* engine, envoy_stream_t handle) + : engine_(engine), handle_(handle) {} Stream& Stream::sendHeaders(RequestHeadersSharedPtr headers, bool end_stream) { envoy_headers raw_headers = rawHeaderMapAsEnvoyHeaders(headers->allHeaders()); - ::send_headers(engine_handle_, handle_, raw_headers, end_stream); + engine_->sendHeaders(handle_, raw_headers, end_stream); return *this; } Stream& Stream::sendData(envoy_data data) { - ::send_data(engine_handle_, handle_, data, false); + engine_->sendData(handle_, data, false); return *this; } Stream& Stream::readData(size_t bytes_to_read) { - ::read_data(engine_handle_, handle_, bytes_to_read); + engine_->readData(handle_, bytes_to_read); return *this; } void Stream::close(RequestTrailersSharedPtr trailers) { envoy_headers raw_headers = rawHeaderMapAsEnvoyHeaders(trailers->allHeaders()); - ::send_trailers(engine_handle_, handle_, raw_headers); + engine_->sendTrailers(handle_, raw_headers); } -void Stream::close(envoy_data data) { ::send_data(engine_handle_, handle_, data, true); } +void Stream::close(envoy_data data) { engine_->sendData(handle_, data, true); } -void Stream::cancel() { reset_stream(engine_handle_, handle_); } +void Stream::cancel() { engine_->cancelStream(handle_); } } // namespace Platform } // namespace Envoy diff --git a/mobile/library/cc/stream.h b/mobile/library/cc/stream.h index 946402cb44cb1..6a6214c24625e 100644 --- a/mobile/library/cc/stream.h +++ b/mobile/library/cc/stream.h @@ -2,20 +2,18 @@ #include +#include "library/cc/request_headers.h" +#include "library/cc/request_trailers.h" +#include "library/cc/stream_callbacks.h" #include "library/common/types/c_types.h" -#include "request_headers.h" -#include "request_trailers.h" -#include "stream_callbacks.h" namespace Envoy { +class InternalEngine; namespace Platform { -class Engine; -using EngineSharedPtr = std::shared_ptr; - class Stream { public: - Stream(envoy_engine_t engine_handle, envoy_stream_t handle); + Stream(Envoy::InternalEngine* engine, envoy_stream_t handle); Stream& sendHeaders(RequestHeadersSharedPtr headers, bool end_stream); Stream& sendData(envoy_data data); @@ -25,7 +23,7 @@ class Stream { void cancel(); private: - envoy_engine_t engine_handle_; + Envoy::InternalEngine* engine_; envoy_stream_t handle_; }; diff --git a/mobile/library/cc/stream_callbacks.cc b/mobile/library/cc/stream_callbacks.cc index bc73a9bc6cc77..31caeafa5a57c 100644 --- a/mobile/library/cc/stream_callbacks.cc +++ b/mobile/library/cc/stream_callbacks.cc @@ -1,9 +1,9 @@ #include "stream_callbacks.h" -#include "bridge_utility.h" +#include "library/cc/bridge_utility.h" +#include "library/cc/response_headers_builder.h" +#include "library/cc/response_trailers_builder.h" #include "library/common/data/utility.h" -#include "response_headers_builder.h" -#include "response_trailers_builder.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/stream_callbacks.h b/mobile/library/cc/stream_callbacks.h index 21c9769bb3be0..29c0b32f890dd 100644 --- a/mobile/library/cc/stream_callbacks.h +++ b/mobile/library/cc/stream_callbacks.h @@ -5,11 +5,11 @@ #include #include "absl/types/optional.h" -#include "envoy_error.h" +#include "library/cc/envoy_error.h" +#include "library/cc/response_headers.h" +#include "library/cc/response_trailers.h" +#include "library/cc/stream.h" #include "library/common/types/c_types.h" -#include "response_headers.h" -#include "response_trailers.h" -#include "stream.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/stream_client.cc b/mobile/library/cc/stream_client.cc index 84dcfd9f08033..f780ca454044f 100644 --- a/mobile/library/cc/stream_client.cc +++ b/mobile/library/cc/stream_client.cc @@ -1,4 +1,4 @@ -#include "stream_client.h" +#include "library/cc/stream_client.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/stream_client.h b/mobile/library/cc/stream_client.h index ad3e8a4eec8b7..0bac6267a2d5a 100644 --- a/mobile/library/cc/stream_client.h +++ b/mobile/library/cc/stream_client.h @@ -2,8 +2,8 @@ #include -#include "engine.h" -#include "stream_prototype.h" +#include "library/cc/engine.h" +#include "library/cc/stream_prototype.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/stream_prototype.cc b/mobile/library/cc/stream_prototype.cc index 788de1276885d..7f7aa5f3d951c 100644 --- a/mobile/library/cc/stream_prototype.cc +++ b/mobile/library/cc/stream_prototype.cc @@ -1,6 +1,6 @@ #include "stream_prototype.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" namespace Envoy { namespace Platform { @@ -10,11 +10,10 @@ StreamPrototype::StreamPrototype(EngineSharedPtr engine) : engine_(engine) { } StreamSharedPtr StreamPrototype::start(bool explicit_flow_control) { - envoy_engine_t engine_handle = reinterpret_cast(engine_->engine_); - auto envoy_stream = init_stream(engine_handle); - start_stream(engine_handle, envoy_stream, callbacks_->asEnvoyHttpCallbacks(), - explicit_flow_control); - return std::make_shared(engine_handle, envoy_stream); + auto envoy_stream = engine_->engine_->initStream(); + engine_->engine_->startStream(envoy_stream, callbacks_->asEnvoyHttpCallbacks(), + explicit_flow_control); + return std::make_shared(engine_->engine_, envoy_stream); } StreamPrototype& StreamPrototype::setOnHeaders(OnHeadersCallback closure) { diff --git a/mobile/library/cc/stream_prototype.h b/mobile/library/cc/stream_prototype.h index 3278a7a2f0de0..f6b551c4fb3ac 100644 --- a/mobile/library/cc/stream_prototype.h +++ b/mobile/library/cc/stream_prototype.h @@ -2,13 +2,13 @@ #include -#include "engine.h" -#include "envoy_error.h" +#include "library/cc/engine.h" +#include "library/cc/envoy_error.h" +#include "library/cc/response_headers.h" +#include "library/cc/response_trailers.h" +#include "library/cc/stream.h" +#include "library/cc/stream_callbacks.h" #include "library/common/types/c_types.h" -#include "response_headers.h" -#include "response_trailers.h" -#include "stream.h" -#include "stream_callbacks.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/cc/trailers.h b/mobile/library/cc/trailers.h index 620a54cfa2160..ba60592b7b43f 100644 --- a/mobile/library/cc/trailers.h +++ b/mobile/library/cc/trailers.h @@ -1,6 +1,6 @@ #pragma once -#include "headers.h" +#include "library/cc/headers.h" namespace Envoy { namespace Platform { diff --git a/mobile/library/common/BUILD b/mobile/library/common/BUILD index 9969ada7b673c..c4d3455b6c95c 100644 --- a/mobile/library/common/BUILD +++ b/mobile/library/common/BUILD @@ -5,29 +5,27 @@ licenses(["notice"]) # Apache 2 envoy_mobile_package() envoy_cc_library( - name = "envoy_main_interface_lib", + name = "internal_engine_lib", repository = "@envoy", deps = [ ":engine_common_lib_stamped", - ":envoy_main_interface_lib_no_stamp", + ":internal_engine_lib_no_stamp", ], ) envoy_cc_library( - name = "envoy_main_interface_lib_no_stamp", + name = "internal_engine_lib_no_stamp", srcs = [ - "engine.cc", - "engine.h", - "main_interface.cc", + "internal_engine.cc", ], hdrs = [ - "main_interface.h", + "internal_engine.h", ], repository = "@envoy", deps = [ ":engine_common_lib", "//library/common/bridge:utility_lib", - "//library/common/common:lambda_logger_delegate_lib", + "//library/common/common:logger_delegate_lib", "//library/common/data:utility_lib", "//library/common/event:provisional_dispatcher_lib", "//library/common/http:client_lib", diff --git a/mobile/library/common/api/external.cc b/mobile/library/common/api/external.cc index 6b61712e34e0f..e62ceacaa578d 100644 --- a/mobile/library/common/api/external.cc +++ b/mobile/library/common/api/external.cc @@ -1,5 +1,7 @@ #include "external.h" +#include + #include "source/common/common/assert.h" #include "absl/container/flat_hash_map.h" @@ -15,16 +17,14 @@ static absl::flat_hash_map registry_{}; // TODO(goaway): To expose this for general usage, it will need to be made thread-safe. For now it // relies on the assumption that usage will occur only as part of Engine configuration, and thus be // limited to a single thread. -void registerApi(std::string name, void* api) { +void registerApi(std::string&& name, void* api) { RELEASE_ASSERT(api != nullptr, "cannot register null API"); - registry_[name] = api; + registry_[std::move(name)] = api; } // TODO(goaway): This is not thread-safe, but the assumption here is that all writes will complete // before any reads occur. -// TODO(alyssawilk, abeyad): gracefully handle the case where an Api by the given name is not -// registered. -void* retrieveApi(std::string name, bool allow_absent) { +void* retrieveApi(absl::string_view name, bool allow_absent) { void* api = registry_[name]; if (!allow_absent) { RELEASE_ASSERT(api != nullptr, fmt::format("{} not registered", name)); diff --git a/mobile/library/common/api/external.h b/mobile/library/common/api/external.h index 1097ff49cf2ab..1761995280dc0 100644 --- a/mobile/library/common/api/external.h +++ b/mobile/library/common/api/external.h @@ -2,6 +2,8 @@ #include +#include "absl/strings/string_view.h" + namespace Envoy { namespace Api { namespace External { @@ -9,12 +11,12 @@ namespace External { /** * Register an external runtime API for usage (e.g. in extensions). */ -void registerApi(std::string name, void* api); +void registerApi(std::string&& name, void* api); /** * Retrieve an external runtime API for usage (e.g. in extensions). */ -void* retrieveApi(std::string name, bool allow_absent = false); +void* retrieveApi(absl::string_view name, bool allow_absent = false); } // namespace External } // namespace Api diff --git a/mobile/library/common/common/BUILD b/mobile/library/common/common/BUILD index a0cc2959038d8..0378d11374e66 100644 --- a/mobile/library/common/common/BUILD +++ b/mobile/library/common/common/BUILD @@ -31,8 +31,8 @@ envoy_cc_library( "//library/common/extensions/cert_validator/platform_bridge:c_types_lib", ] + select({ ":use_android_system_helper": [ - "//library/common/jni:android_jni_utility_lib", - "//library/common/jni:android_network_utility_lib", + "//library/jni:android_jni_utility_lib", + "//library/jni:android_network_utility_lib", ], "//conditions:default": [], }) + select({ @@ -63,9 +63,9 @@ envoy_cc_library( ) envoy_cc_library( - name = "lambda_logger_delegate_lib", - srcs = ["lambda_logger_delegate.cc"], - hdrs = ["lambda_logger_delegate.h"], + name = "logger_delegate_lib", + srcs = ["logger_delegate.cc"], + hdrs = ["logger_delegate.h"], repository = "@envoy", deps = [ "//library/common/api:external_api_lib", diff --git a/mobile/library/common/common/default_system_helper_android.cc b/mobile/library/common/common/default_system_helper_android.cc index fca30e45e38f6..f9f8b64319b0c 100644 --- a/mobile/library/common/common/default_system_helper_android.cc +++ b/mobile/library/common/common/default_system_helper_android.cc @@ -1,6 +1,6 @@ #include "library/common/common/default_system_helper.h" -#include "library/common/jni/android_jni_utility.h" -#include "library/common/jni/android_network_utility.h" +#include "library/jni/android_jni_utility.h" +#include "library/jni/android_network_utility.h" namespace Envoy { diff --git a/mobile/library/common/common/lambda_logger_delegate.cc b/mobile/library/common/common/logger_delegate.cc similarity index 52% rename from mobile/library/common/common/lambda_logger_delegate.cc rename to mobile/library/common/common/logger_delegate.cc index 9f018af779fe5..6d7928aee29f2 100644 --- a/mobile/library/common/common/lambda_logger_delegate.cc +++ b/mobile/library/common/common/logger_delegate.cc @@ -1,4 +1,4 @@ -#include "library/common/common/lambda_logger_delegate.h" +#include "library/common/common/logger_delegate.h" #include @@ -8,6 +8,31 @@ namespace Envoy { namespace Logger { +namespace { + +envoy_log_level toEnvoyLogLevel(spdlog::level::level_enum spd_log_level) { + switch (spd_log_level) { + case spdlog::level::trace: + return envoy_log_level::ENVOY_LOG_LEVEL_TRACE; + case spdlog::level::debug: + return envoy_log_level::ENVOY_LOG_LEVEL_DEBUG; + case spdlog::level::info: + return envoy_log_level::ENVOY_LOG_LEVEL_INFO; + case spdlog::level::warn: + return envoy_log_level::ENVOY_LOG_LEVEL_WARN; + case spdlog::level::err: + return envoy_log_level::ENVOY_LOG_LEVEL_ERROR; + case spdlog::level::critical: + return envoy_log_level::ENVOY_LOG_LEVEL_CRITICAL; + case spdlog::level::off: + return envoy_log_level::ENVOY_LOG_LEVEL_OFF; + default: + PANIC("not implemented"); + } +} + +} // namespace + void EventTrackingDelegate::logWithStableName(absl::string_view stable_name, absl::string_view, absl::string_view, absl::string_view msg) { if (event_tracker_.track == nullptr) { @@ -30,8 +55,9 @@ LambdaDelegate::~LambdaDelegate() { logger_.release(logger_.context); } -void LambdaDelegate::log(absl::string_view msg, const spdlog::details::log_msg&) { - logger_.log(Data::Utility::copyToBridgeData(msg), logger_.context); +void LambdaDelegate::log(absl::string_view msg, const spdlog::details::log_msg& log_msg) { + logger_.log(toEnvoyLogLevel(log_msg.level), Data::Utility::copyToBridgeData(msg), + logger_.context); } DefaultDelegate::DefaultDelegate(absl::Mutex& mutex, DelegatingLogSinkSharedPtr log_sink) @@ -41,5 +67,16 @@ DefaultDelegate::DefaultDelegate(absl::Mutex& mutex, DelegatingLogSinkSharedPtr DefaultDelegate::~DefaultDelegate() { restoreDelegate(); } +// SinkDelegate +void DefaultDelegate::log(absl::string_view msg, const spdlog::details::log_msg&) { + absl::MutexLock l(&mutex_); + std::cerr << msg; +} + +void DefaultDelegate::flush() { + absl::MutexLock l(&mutex_); + std::cerr << std::flush; +} + } // namespace Logger } // namespace Envoy diff --git a/mobile/library/common/common/lambda_logger_delegate.h b/mobile/library/common/common/logger_delegate.h similarity index 91% rename from mobile/library/common/common/lambda_logger_delegate.h rename to mobile/library/common/common/logger_delegate.h index 14656594344ff..a40400ac15fc6 100644 --- a/mobile/library/common/common/lambda_logger_delegate.h +++ b/mobile/library/common/common/logger_delegate.h @@ -50,14 +50,9 @@ class DefaultDelegate : public EventTrackingDelegate { ~DefaultDelegate() override; // SinkDelegate - void log(absl::string_view msg, const spdlog::details::log_msg&) override { - absl::MutexLock l(&mutex_); - std::cerr << msg; - } - void flush() override { - absl::MutexLock l(&mutex_); - std::cerr << std::flush; - }; + void log(absl::string_view msg, const spdlog::details::log_msg&) override; + + void flush() override; private: absl::Mutex& mutex_; diff --git a/mobile/library/common/common/system_helper.cc b/mobile/library/common/common/system_helper.cc index c2f11fefcd9e1..20e3f5616c3fd 100644 --- a/mobile/library/common/common/system_helper.cc +++ b/mobile/library/common/common/system_helper.cc @@ -12,7 +12,7 @@ namespace Envoy { -std::unique_ptr SystemHelper::instance_ = std::make_unique(); +SystemHelper* SystemHelper::instance_ = new DefaultSystemHelper(); SystemHelper& SystemHelper::getInstance() { return *instance_; } diff --git a/mobile/library/common/common/system_helper.h b/mobile/library/common/common/system_helper.h index b558c0e13c03e..d18c6537e49a4 100644 --- a/mobile/library/common/common/system_helper.h +++ b/mobile/library/common/common/system_helper.h @@ -47,7 +47,7 @@ class SystemHelper { private: friend class test::SystemHelperPeer; - static std::unique_ptr instance_; + static SystemHelper* instance_; }; } // namespace Envoy diff --git a/mobile/library/common/http/client.cc b/mobile/library/common/http/client.cc index 063dd123e1a4e..42a983819b3bb 100644 --- a/mobile/library/common/http/client.cc +++ b/mobile/library/common/http/client.cc @@ -248,14 +248,20 @@ void Client::DirectStreamCallbacks::resumeData(size_t bytes_to_send) { } void Client::DirectStreamCallbacks::closeStream(bool end_stream) { + ENVOY_LOG(debug, "[S{}] close stream end stream {}\n", direct_stream_.stream_handle_, end_stream); remote_end_stream_received_ |= end_stream; - // Latch stream intel on stream completion, as the stream info will go away. - direct_stream_.saveFinalStreamIntel(); + if (end_stream) { + // Latch stream intel on stream completion, as the stream info will go away. + // If end_stream is false this is the stream reset case and data is latched + // in resetStream + direct_stream_.saveFinalStreamIntel(); + } auto& client = direct_stream_.parent_; auto stream = client.getStream(direct_stream_.stream_handle_, ALLOW_ONLY_FOR_OPEN_STREAMS); ASSERT(stream != nullptr); if (stream) { + ENVOY_LOG(debug, "[S{}] erased stream\n", direct_stream_.stream_handle_); client.closed_streams_.emplace(direct_stream_.stream_handle_, std::move(stream)); size_t erased = client.streams_.erase(direct_stream_.stream_handle_); ASSERT(erased == 1, "closeStream should always remove one entry from the streams map"); @@ -296,11 +302,11 @@ void Client::DirectStreamCallbacks::onError() { // TODO(goaway): What is the expected behavior when an error is received, held, and then another // error occurs (e.g., timeout)? - error_ = streamError(); if (explicit_flow_control_ && response_headers_forwarded_ && bytes_to_send_ == 0) { ENVOY_LOG(debug, "[S{}] defering remote reset stream due to explicit flow control", direct_stream_.stream_handle_); - if (!remote_end_stream_received_) { + if (direct_stream_.parent_.getStream(direct_stream_.stream_handle_, + ALLOW_ONLY_FOR_OPEN_STREAMS)) { closeStream(false); } return; @@ -406,39 +412,46 @@ void Client::DirectStream::saveLatestStreamIntel() { } void Client::DirectStream::saveFinalStreamIntel() { + if (!parent_.getStream(stream_handle_, ALLOW_ONLY_FOR_OPEN_STREAMS)) { + return; + } OptRef request_decoder = requestDecoder(); - if (!request_decoder || !parent_.getStream(stream_handle_, ALLOW_ONLY_FOR_OPEN_STREAMS)) { + if (!request_decoder) { return; } StreamInfo::setFinalStreamIntel(request_decoder->streamInfo(), parent_.dispatcher_.timeSource(), envoy_final_stream_intel_); } -envoy_error Client::DirectStreamCallbacks::streamError() { - envoy_error error{}; +void Client::DirectStreamCallbacks::latchError() { + if (error_.has_value()) { + return; // Only latch error once. + } + error_ = envoy_error(); + OptRef request_decoder = direct_stream_.requestDecoder(); if (!request_decoder) { - return error; + error_->message = envoy_nodata; + return; } const auto& info = request_decoder->streamInfo(); if (info.responseCode().has_value()) { - error.error_code = Bridge::Utility::errorCodeFromLocalStatus( + error_->error_code = Bridge::Utility::errorCodeFromLocalStatus( static_cast(info.responseCode().value())); } else if (StreamInfo::isStreamIdleTimeout(info)) { - error.error_code = ENVOY_REQUEST_TIMEOUT; + error_->error_code = ENVOY_REQUEST_TIMEOUT; } else { - error.error_code = ENVOY_STREAM_RESET; + error_->error_code = ENVOY_STREAM_RESET; } if (info.responseCodeDetails().has_value()) { - error.message = Data::Utility::copyToBridgeData(info.responseCodeDetails().value()); + error_->message = Data::Utility::copyToBridgeData(info.responseCodeDetails().value()); } else { - error.message = envoy_nodata; + error_->message = envoy_nodata; } - error.attempt_count = info.attemptCount().value_or(0); - return error; + error_->attempt_count = info.attemptCount().value_or(0); } Client::DirectStream::DirectStream(envoy_stream_t stream_handle, Client& http_client) @@ -446,6 +459,21 @@ Client::DirectStream::DirectStream(envoy_stream_t stream_handle, Client& http_cl Client::DirectStream::~DirectStream() { ENVOY_LOG(debug, "[S{}] destroy stream", stream_handle_); } +CodecEventCallbacks* +Client::DirectStream::registerCodecEventCallbacks(CodecEventCallbacks* codec_callbacks) { + // registerCodecEventCallbacks is called with nullptr when the underlying + // Envoy stream is going away. Make sure Envoy Mobile sees the stream as + // closed as well. + if (codec_callbacks == nullptr && + parent_.getStream(stream_handle_, ALLOW_ONLY_FOR_OPEN_STREAMS)) { + // Generally this only happens if Envoy closes the (virtual) downstream + // connection, otherwise Envoy would inform the codec to send a reset. + callbacks_->closeStream(false); + } + std::swap(codec_callbacks, codec_callbacks_); + return codec_callbacks; +} + // Correctly receiving resetStream() for errors in Http::Client relies on at least one filter // resetting the stream when handling a pending local response. By default, the LocalReplyFilter // has this responsibility. @@ -453,7 +481,8 @@ void Client::DirectStream::resetStream(StreamResetReason reason) { // This seems in line with other codec implementations, and so the assumption is that this is in // line with upstream expectations. // TODO(goaway): explore an upstream fix to get the HCM to clean up ActiveStream itself. - saveFinalStreamIntel(); // Take a snapshot now in case the stream gets destroyed. + saveFinalStreamIntel(); // Take a snapshot now in case the stream gets destroyed. + callbacks_->latchError(); // Latch the error in case the stream gets destroyed. runResetCallbacks(reason); if (!parent_.getStream(stream_handle_, GetStreamFilters::ALLOW_FOR_ALL_STREAMS)) { // We don't assert here, because Envoy will issue a stream reset if a stream closes remotely @@ -655,6 +684,7 @@ void Client::cancelStream(envoy_stream_t stream) { if (direct_stream) { // Attempt to latch the latest stream info. This will be a no-op if the stream // is already complete. + ENVOY_LOG(debug, "[S{}] application cancelled stream", stream); direct_stream->saveFinalStreamIntel(); bool stream_was_open = getStream(stream, GetStreamFilters::ALLOW_ONLY_FOR_OPEN_STREAMS) != nullptr; @@ -662,7 +692,6 @@ void Client::cancelStream(envoy_stream_t stream) { direct_stream->notifyAdapter(DirectStream::AdapterSignal::Cancel); removeStream(direct_stream->stream_handle_); - ENVOY_LOG(debug, "[S{}] application cancelled stream", stream); direct_stream->callbacks_->onCancel(); // Since https://github.com/envoyproxy/envoy/pull/13052, the connection manager expects that diff --git a/mobile/library/common/http/client.h b/mobile/library/common/http/client.h index 186900271bc57..e18c0816ee583 100644 --- a/mobile/library/common/http/client.h +++ b/mobile/library/common/http/client.h @@ -151,10 +151,6 @@ class Client : public Logger::Loggable { void onError(); void onSendWindowAvailable(); - // Remove the stream and clear up state if possible, else set up deferred - // removal path. - void removeStream(); - // ResponseEncoder void encodeHeaders(const ResponseHeaderMap& headers, bool end_stream) override; void encodeData(Buffer::Instance& data, bool end_stream) override; @@ -188,7 +184,7 @@ class Client : public Logger::Loggable { // than bytes_to_send. void resumeData(size_t bytes_to_send); - void setFinalStreamIntel(StreamInfo::StreamInfo& stream_info); + void latchError(); private: bool hasBufferedData() { return response_data_.get() && response_data_->length() != 0; } @@ -198,7 +194,6 @@ class Client : public Logger::Loggable { void sendErrorToBridge(); envoy_stream_intel streamIntel(); envoy_final_stream_intel& finalStreamIntel(); - envoy_error streamError(); DirectStream& direct_stream_; const envoy_http_callbacks bridge_callbacks_; @@ -239,11 +234,7 @@ class Client : public Logger::Loggable { // Stream void addCallbacks(StreamCallbacks& callbacks) override { addCallbacksHelper(callbacks); } void removeCallbacks(StreamCallbacks& callbacks) override { removeCallbacksHelper(callbacks); } - CodecEventCallbacks* - registerCodecEventCallbacks(CodecEventCallbacks* codec_callbacks) override { - std::swap(codec_callbacks, codec_callbacks_); - return codec_callbacks; - } + CodecEventCallbacks* registerCodecEventCallbacks(CodecEventCallbacks* codec_callbacks) override; void resetStream(StreamResetReason) override; Network::ConnectionInfoProvider& connectionInfoProvider() override { diff --git a/mobile/library/common/engine.cc b/mobile/library/common/internal_engine.cc similarity index 74% rename from mobile/library/common/engine.cc rename to mobile/library/common/internal_engine.cc index b7e6e2e4a4233..3240169e7fc06 100644 --- a/mobile/library/common/engine.cc +++ b/mobile/library/common/internal_engine.cc @@ -1,17 +1,22 @@ -#include "library/common/engine.h" +#include "library/common/internal_engine.h" #include "source/common/api/os_sys_calls_impl.h" #include "source/common/common/lock_guard.h" #include "source/common/runtime/runtime_features.h" +#include "absl/synchronization/notification.h" #include "library/common/bridge/utility.h" #include "library/common/data/utility.h" #include "library/common/stats/utility.h" namespace Envoy { -Engine::Engine(envoy_engine_callbacks callbacks, envoy_logger logger, - envoy_event_tracker event_tracker) +static std::atomic current_stream_handle_{0}; + +envoy_stream_t InternalEngine::initStream() { return current_stream_handle_++; } + +InternalEngine::InternalEngine(envoy_engine_callbacks callbacks, envoy_logger logger, + envoy_event_tracker event_tracker) : callbacks_(callbacks), logger_(logger), event_tracker_(event_tracker), dispatcher_(std::make_unique()) { ExtensionRegistry::registerFactories(); @@ -27,7 +32,7 @@ Engine::Engine(envoy_engine_callbacks callbacks, envoy_logger logger, Runtime::maybeSetRuntimeGuard("envoy.reloadable_features.dfp_mixed_scheme", true); } -envoy_status_t Engine::run(const std::string config, const std::string log_level) { +envoy_status_t InternalEngine::run(const std::string& config, const std::string& log_level) { // Start the Envoy on the dedicated thread. Note: due to how the assignment operator works with // std::thread, main_thread_ is the same object after this call, but its state is replaced with // that of the temporary. The temporary object's state becomes the default state, which does @@ -35,18 +40,18 @@ envoy_status_t Engine::run(const std::string config, const std::string log_level auto options = std::make_unique(); options->setConfigYaml(config); if (!log_level.empty()) { - ENVOY_BUG(options->setLogLevel(log_level.c_str()).ok(), "invalid log level"); + ENVOY_BUG(options->setLogLevel(log_level).ok(), "invalid log level"); } options->setConcurrency(1); return run(std::move(options)); } -envoy_status_t Engine::run(std::unique_ptr&& options) { - main_thread_ = std::thread(&Engine::main, this, std::move(options)); +envoy_status_t InternalEngine::run(std::unique_ptr&& options) { + main_thread_ = std::thread(&InternalEngine::main, this, std::move(options)); return ENVOY_SUCCESS; } -envoy_status_t Engine::main(std::unique_ptr&& options) { +envoy_status_t InternalEngine::main(std::unique_ptr&& options) { // Using unique_ptr ensures main_common's lifespan is strictly scoped to this function. std::unique_ptr main_common; { @@ -140,7 +145,11 @@ envoy_status_t Engine::main(std::unique_ptr&& options) { return run_success ? ENVOY_SUCCESS : ENVOY_FAILURE; } -envoy_status_t Engine::terminate() { +envoy_status_t InternalEngine::terminate() { + if (terminated_) { + IS_ENVOY_BUG("attempted to double terminate engine"); + return ENVOY_FAILURE; + } // If main_thread_ has finished (or hasn't started), there's nothing more to do. if (!main_thread_.joinable()) { return ENVOY_FAILURE; @@ -172,38 +181,50 @@ envoy_status_t Engine::terminate() { if (std::this_thread::get_id() != main_thread_.get_id()) { main_thread_.join(); } - + terminated_ = true; return ENVOY_SUCCESS; } -Engine::~Engine() { terminate(); } - -envoy_status_t Engine::recordCounterInc(const std::string& elements, envoy_stats_tags tags, - uint64_t count) { - ENVOY_LOG(trace, "[pulse.{}] recordCounterInc", elements); - ASSERT(dispatcher_->isThreadSafe(), "pulse calls must run from dispatcher's context"); - Stats::StatNameTagVector tags_vctr = - Stats::Utility::transformToStatNameTagVector(tags, stat_name_set_); - std::string name = Stats::Utility::sanitizeStatsName(elements); - Stats::Utility::counterFromElements(*client_scope_, {Stats::DynamicName(name)}, tags_vctr) - .add(count); - return ENVOY_SUCCESS; +bool InternalEngine::isTerminated() const { return terminated_; } + +InternalEngine::InternalEngine() { + if (!terminated_) { + terminate(); + } } -Event::ProvisionalDispatcher& Engine::dispatcher() { return *dispatcher_; } +envoy_status_t InternalEngine::setProxySettings(const char* hostname, const uint16_t port) { + return dispatcher_->post([&, host = std::string(hostname), port]() -> void { + connectivity_manager_->setProxySettings(Network::ProxySettings::parseHostAndPort(host, port)); + }); +} + +envoy_status_t InternalEngine::resetConnectivityState() { + return dispatcher_->post([&]() -> void { connectivity_manager_->resetConnectivityState(); }); +} -Http::Client& Engine::httpClient() { - RELEASE_ASSERT(dispatcher_->isThreadSafe(), - "httpClient must be accessed from dispatcher's context"); - return *http_client_; +envoy_status_t InternalEngine::setPreferredNetwork(envoy_network_t network) { + return dispatcher_->post([&, network]() -> void { + envoy_netconf_t configuration_key = + Envoy::Network::ConnectivityManagerImpl::setPreferredNetwork(network); + connectivity_manager_->refreshDns(configuration_key, true); + }); } -Network::ConnectivityManager& Engine::networkConnectivityManager() { - RELEASE_ASSERT(dispatcher_->isThreadSafe(), - "networkConnectivityManager must be accessed from dispatcher's context"); - return *connectivity_manager_; +envoy_status_t InternalEngine::recordCounterInc(absl::string_view elements, envoy_stats_tags tags, + uint64_t count) { + return dispatcher_->post( + [&, name = Stats::Utility::sanitizeStatsName(elements), tags, count]() -> void { + ENVOY_LOG(trace, "[pulse.{}] recordCounterInc", name); + Stats::StatNameTagVector tags_vctr = + Stats::Utility::transformToStatNameTagVector(tags, stat_name_set_); + Stats::Utility::counterFromElements(*client_scope_, {Stats::DynamicName(name)}, tags_vctr) + .add(count); + }); } +Event::ProvisionalDispatcher& InternalEngine::dispatcher() { return *dispatcher_; } + void statsAsText(const std::map& all_stats, const std::vector& histograms, Buffer::Instance& response) { @@ -243,27 +264,38 @@ void handlerStats(Stats::Store& stats, Buffer::Instance& response) { statsAsText(all_stats, histograms, response); } -Envoy::Buffer::OwnedImpl Engine::dumpStats() { - ASSERT(dispatcher_->isThreadSafe(), "dumpStats must be called from the dispatcher's context"); +std::string InternalEngine::dumpStats() { + if (!main_thread_.joinable()) { + return ""; + } - Envoy::Buffer::OwnedImpl instance; - handlerStats(server_->stats(), instance); - return instance; + std::string stats; + absl::Notification stats_received; + if (dispatcher_->post([&]() -> void { + Envoy::Buffer::OwnedImpl instance; + handlerStats(server_->stats(), instance); + stats = instance.toString(); + stats_received.Notify(); + }) == ENVOY_SUCCESS) { + stats_received.WaitForNotification(); + return stats; + } + return stats; } -Upstream::ClusterManager& Engine::getClusterManager() { +Upstream::ClusterManager& InternalEngine::getClusterManager() { ASSERT(dispatcher_->isThreadSafe(), "getClusterManager must be called from the dispatcher's context"); return server_->clusterManager(); } -Stats::Store& Engine::getStatsStore() { +Stats::Store& InternalEngine::getStatsStore() { ASSERT(dispatcher_->isThreadSafe(), "getStatsStore must be called from the dispatcher's context"); return server_->stats(); } -void Engine::logInterfaces(absl::string_view event, - std::vector& interfaces) { +void InternalEngine::logInterfaces(absl::string_view event, + std::vector& interfaces) { std::vector names; names.resize(interfaces.size()); std::transform(interfaces.begin(), interfaces.end(), names.begin(), diff --git a/mobile/library/common/engine.h b/mobile/library/common/internal_engine.h similarity index 50% rename from mobile/library/common/engine.h rename to mobile/library/common/internal_engine.h index 3a130ad5d89d1..adcb1a825e441 100644 --- a/mobile/library/common/engine.h +++ b/mobile/library/common/internal_engine.h @@ -7,7 +7,7 @@ #include "absl/base/call_once.h" #include "extension_registry.h" -#include "library/common/common/lambda_logger_delegate.h" +#include "library/common/common/logger_delegate.h" #include "library/common/engine_common.h" #include "library/common/http/client.h" #include "library/common/network/connectivity_manager.h" @@ -15,7 +15,7 @@ namespace Envoy { -class Engine : public Logger::Loggable { +class InternalEngine : public Logger::Loggable { public: /** * Constructor for a new engine instance. @@ -23,43 +23,75 @@ class Engine : public Logger::Loggable { * @param logger, the callbacks to use for engine logging. * @param event_tracker, the event tracker to use for the emission of events. */ - Engine(envoy_engine_callbacks callbacks, envoy_logger logger, envoy_event_tracker event_tracker); + InternalEngine(envoy_engine_callbacks callbacks, envoy_logger logger, + envoy_event_tracker event_tracker); /** - * Engine destructor. + * InternalEngine destructor. */ - ~Engine(); + InternalEngine(); /** * Run the engine with the provided configuration. * @param config, the Envoy bootstrap configuration to use. * @param log_level, the log level. */ - envoy_status_t run(std::string config, std::string log_level); + envoy_status_t run(const std::string& config, const std::string& log_level); envoy_status_t run(std::unique_ptr&& options); /** - * Immediately terminate the engine, if running. + * Immediately terminate the engine, if running. Calling this function when + * the engine has been terminated will result in `ENVOY_FAILURE`. */ envoy_status_t terminate(); + /** Returns true if the Engine has been terminated; false otherwise. */ + bool isTerminated() const; + /** * Accessor for the provisional event dispatcher. * @return Event::ProvisionalDispatcher&, the engine dispatcher. */ Event::ProvisionalDispatcher& dispatcher(); - /** - * Accessor for the http client. Must be called from the dispatcher's context. - * @return Http::Client&, the (default) http client. - */ - Http::Client& httpClient(); - - /** - * Accessor for the network configuraator. Must be called from the dispatcher's context. - * @return Network::ConnectivityManager&, the network connectivity_manager. - */ - Network::ConnectivityManager& networkConnectivityManager(); + envoy_stream_t initStream(); + + // These functions are wrappers around http client functions, which hand off + // to http client functions of the same name after doing a dispatcher post + // (thread context switch) + envoy_status_t startStream(envoy_stream_t stream, envoy_http_callbacks bridge_callbacks, + bool explicit_flow_control) { + return dispatcher_->post([&, stream, bridge_callbacks, explicit_flow_control]() { + http_client_->startStream(stream, bridge_callbacks, explicit_flow_control); + }); + } + envoy_status_t sendHeaders(envoy_stream_t stream, envoy_headers headers, bool end_stream) { + return dispatcher_->post([&, stream, headers, end_stream]() { + http_client_->sendHeaders(stream, headers, end_stream); + }); + } + envoy_status_t readData(envoy_stream_t stream, size_t bytes_to_read) { + return dispatcher_->post( + [&, stream, bytes_to_read]() { http_client_->readData(stream, bytes_to_read); }); + } + envoy_status_t sendData(envoy_stream_t stream, envoy_data data, bool end_stream) { + return dispatcher_->post( + [&, stream, data, end_stream]() { http_client_->sendData(stream, data, end_stream); }); + } + envoy_status_t sendTrailers(envoy_stream_t stream, envoy_headers trailers) { + return dispatcher_->post( + [&, stream, trailers]() { http_client_->sendTrailers(stream, trailers); }); + } + + envoy_status_t cancelStream(envoy_stream_t stream) { + return dispatcher_->post([&, stream]() { http_client_->cancelStream(stream); }); + } + + // These functions are wrappers around networkConnectivityManager functions, which hand off + // to networkConnectivityManager after doing a dispatcher post (thread context switch) + envoy_status_t setProxySettings(const char* host, const uint16_t port); + envoy_status_t resetConnectivityState(); + envoy_status_t setPreferredNetwork(envoy_network_t network); /** * Increment a counter with a given string of elements and by the given count. @@ -67,14 +99,13 @@ class Engine : public Logger::Loggable { * @param tags, custom tags of the reporting stat. * @param count, amount to add to the counter. */ - envoy_status_t recordCounterInc(const std::string& elements, envoy_stats_tags tags, + envoy_status_t recordCounterInc(absl::string_view elements, envoy_stats_tags tags, uint64_t count); /** - * Dump Envoy stats into the returned buffer - * @returns a buffer with referenced stats dumped in Envoy's standard text format. + * Dumps Envoy stats into string. Returns an empty string when an error occurred. */ - Buffer::OwnedImpl dumpStats(); + std::string dumpStats(); /** * Get cluster manager from the Engine. @@ -112,9 +143,10 @@ class Engine : public Logger::Loggable { // main_thread_ should be destroyed first, hence it is the last member variable. Objects with // instructions scheduled on the main_thread_ need to have a longer lifetime. std::thread main_thread_{}; // Empty placeholder to be populated later. + bool terminated_{false}; }; -using EngineSharedPtr = std::shared_ptr; -using EngineWeakPtr = std::weak_ptr; +using InternalEngineSharedPtr = std::shared_ptr; +using InternalEngineWeakPtr = std::weak_ptr; } // namespace Envoy diff --git a/mobile/library/common/main_interface.cc b/mobile/library/common/main_interface.cc deleted file mode 100644 index 8acf5749c4bc8..0000000000000 --- a/mobile/library/common/main_interface.cc +++ /dev/null @@ -1,121 +0,0 @@ -#include "library/common/main_interface.h" - -#include -#include - -#include "absl/synchronization/notification.h" -#include "library/common/api/external.h" -#include "library/common/data/utility.h" -#include "library/common/engine.h" -#include "library/common/extensions/filters/http/platform_bridge/c_types.h" -#include "library/common/http/client.h" -#include "library/common/network/connectivity_manager.h" - -// NOLINT(namespace-envoy) - -namespace { -envoy_status_t runOnEngineDispatcher(envoy_engine_t handle, - std::function func) { - if (auto engine = reinterpret_cast(handle)) { - return engine->dispatcher().post([engine, func]() { func(*engine); }); - } - return ENVOY_FAILURE; -} -} // namespace - -static std::atomic current_stream_handle_{0}; - -envoy_stream_t init_stream(envoy_engine_t) { return current_stream_handle_++; } - -envoy_status_t start_stream(envoy_engine_t engine, envoy_stream_t stream, - envoy_http_callbacks callbacks, bool explicit_flow_control) { - return runOnEngineDispatcher( - engine, [stream, callbacks, explicit_flow_control](auto& engine) -> void { - engine.httpClient().startStream(stream, callbacks, explicit_flow_control); - }); -} - -envoy_status_t send_headers(envoy_engine_t engine, envoy_stream_t stream, envoy_headers headers, - bool end_stream) { - return runOnEngineDispatcher(engine, ([stream, headers, end_stream](auto& engine) -> void { - engine.httpClient().sendHeaders(stream, headers, end_stream); - })); -} - -envoy_status_t read_data(envoy_engine_t engine, envoy_stream_t stream, size_t bytes_to_read) { - return runOnEngineDispatcher(engine, [stream, bytes_to_read](auto& engine) -> void { - engine.httpClient().readData(stream, bytes_to_read); - }); -} - -envoy_status_t send_data(envoy_engine_t engine, envoy_stream_t stream, envoy_data data, - bool end_stream) { - return runOnEngineDispatcher(engine, [stream, data, end_stream](auto& engine) -> void { - engine.httpClient().sendData(stream, data, end_stream); - }); -} - -// TODO: implement. -envoy_status_t send_metadata(envoy_engine_t, envoy_stream_t, envoy_headers) { - return ENVOY_FAILURE; -} - -envoy_status_t send_trailers(envoy_engine_t engine, envoy_stream_t stream, envoy_headers trailers) { - return runOnEngineDispatcher(engine, [stream, trailers](auto& engine) -> void { - engine.httpClient().sendTrailers(stream, trailers); - }); -} - -envoy_status_t reset_stream(envoy_engine_t engine, envoy_stream_t stream) { - return runOnEngineDispatcher( - engine, [stream](auto& engine) -> void { engine.httpClient().cancelStream(stream); }); -} - -envoy_status_t set_preferred_network(envoy_engine_t engine, envoy_network_t network) { - envoy_netconf_t configuration_key = - Envoy::Network::ConnectivityManagerImpl::setPreferredNetwork(network); - runOnEngineDispatcher(engine, [configuration_key](auto& engine) -> void { - engine.networkConnectivityManager().refreshDns(configuration_key, true); - }); - // TODO(snowp): Should this return failure ever? - return ENVOY_SUCCESS; -} - -envoy_status_t set_proxy_settings(envoy_engine_t e, const char* host, const uint16_t port) { - return runOnEngineDispatcher( - e, - [proxy_settings = Envoy::Network::ProxySettings::parseHostAndPort(host, port)](auto& engine) - -> void { engine.networkConnectivityManager().setProxySettings(proxy_settings); }); -} - -envoy_status_t record_counter_inc(envoy_engine_t e, const char* elements, envoy_stats_tags tags, - uint64_t count) { - return runOnEngineDispatcher(e, - [name = std::string(elements), tags, count](auto& engine) -> void { - engine.recordCounterInc(name, tags, count); - }); -} - -envoy_status_t dump_stats(envoy_engine_t engine, envoy_data* out) { - absl::Notification stats_received; - if (runOnEngineDispatcher(engine, ([out, &stats_received](auto& engine) -> void { - Envoy::Buffer::OwnedImpl dumped_stats = engine.dumpStats(); - *out = Envoy::Data::Utility::toBridgeData(dumped_stats, - 1024 * 1024 * 100); - stats_received.Notify(); - })) == ENVOY_FAILURE) { - return ENVOY_FAILURE; - } - stats_received.WaitForNotification(); - return ENVOY_SUCCESS; -} - -envoy_status_t register_platform_api(const char* name, void* api) { - Envoy::Api::External::registerApi(std::string(name), api); - return ENVOY_SUCCESS; -} - -envoy_status_t reset_connectivity_state(envoy_engine_t e) { - return runOnEngineDispatcher( - e, [](auto& engine) { engine.networkConnectivityManager().resetConnectivityState(); }); -} diff --git a/mobile/library/common/main_interface.h b/mobile/library/common/main_interface.h deleted file mode 100644 index 5a4020a14e171..0000000000000 --- a/mobile/library/common/main_interface.h +++ /dev/null @@ -1,197 +0,0 @@ -#pragma once - -#include -#include -#include - -#include "library/common/types/c_types.h" - -// NOLINT(namespace-envoy) - -#ifdef __cplusplus -extern "C" { // functions -#endif - -/** - * Initialize an underlying HTTP stream. - * @param engine, handle to the engine that will manage this stream. - * @return envoy_stream_t, handle to the underlying stream. - */ -envoy_stream_t init_stream(envoy_engine_t engine); - -/** - * Open an underlying HTTP stream. Note: Streams must be started before other other interaction can - * can occur. - * @param engine, handle to the engine associated with this stream. - * @param stream, handle to the stream to be started. - * @param callbacks, the callbacks that will run the stream callbacks. - * @param explicit_flow_control, whether to enable explicit flow control on the response stream. - * @return envoy_stream, with a stream handle and a success status, or a failure status. - */ -envoy_status_t start_stream(envoy_engine_t engine, envoy_stream_t stream, - envoy_http_callbacks callbacks, bool explicit_flow_control); - -/** - * Send headers over an open HTTP stream. This method can be invoked once and needs to be called - * before send_data. - * @param engine, the engine associated with this stream. - * @param stream, the stream to send headers over. - * @param headers, the headers to send. - * @param end_stream, supplies whether this is headers only. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t send_headers(envoy_engine_t engine, envoy_stream_t stream, envoy_headers headers, - bool end_stream); - -/** - * Notify the stream that the caller is ready to receive more data from the response stream. Only - * used in explicit flow control mode. - * @param bytes_to_read, the quantity of data the caller is prepared to process. - */ -envoy_status_t read_data(envoy_engine_t engine, envoy_stream_t stream, size_t bytes_to_read); - -/** - * Send data over an open HTTP stream. This method can be invoked multiple times. - * @param engine, the engine associated with this stream. - * @param stream, the stream to send data over. - * @param data, the data to send. - * @param end_stream, supplies whether this is the last data in the stream. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t send_data(envoy_engine_t engine, envoy_stream_t stream, envoy_data data, - bool end_stream); - -/** - * Send metadata over an HTTP stream. This method can be invoked multiple times. - * @param engine, the engine associated with this stream. - * @param stream, the stream to send metadata over. - * @param metadata, the metadata to send. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t send_metadata(envoy_engine_t engine, envoy_stream_t stream, envoy_headers metadata); - -/** - * Send trailers over an open HTTP stream. This method can only be invoked once per stream. - * Note that this method implicitly ends the stream. - * @param engine, the engine associated with this stream. - * @param stream, the stream to send trailers over. - * @param trailers, the trailers to send. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t send_trailers(envoy_engine_t engine, envoy_stream_t stream, envoy_headers trailers); - -/** - * Detach all callbacks from a stream and send an interrupt upstream if supported by transport. - * @param engine, the engine associated with this stream. - * @param stream, the stream to evict. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t reset_stream(envoy_engine_t engine, envoy_stream_t stream); - -/** - * Update the network interface to the preferred network for opening new streams. - * Note that this state is shared by all engines. - * @param engine, the engine whose preferred network should be set. - * @param network, the network to be preferred for new streams. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t set_preferred_network(envoy_engine_t engine, envoy_network_t network); - -/** - * @brief Update the currently active proxy settings. - * - * @param engine, the engine whose proxy settings should be updated. - * @param host, the proxy host. - * @param port, the proxy port. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t set_proxy_settings(envoy_engine_t engine, const char* host, const uint16_t port); - -/** - * Increment a counter with the given elements and by the given count. - * @param engine, the engine that owns the counter. - * @param elements, the string that identifies the counter to increment. - * @param tags, a map of {key, value} pairs of tags. - * @param count, the count to increment by. - */ -envoy_status_t record_counter_inc(envoy_engine_t, const char* elements, envoy_stats_tags tags, - uint64_t count); - -/** - * Set a gauge of a given string of elements with the given value. - * @param engine, the engine that owns the gauge. - * @param elements, the string that identifies the gauge to set value with. - * @param tags, a map of {key, value} pairs of tags. - * @param value, the value to set to the gauge. - */ -envoy_status_t record_gauge_set(envoy_engine_t engine, const char* elements, envoy_stats_tags tags, - uint64_t value); - -/** - * Add the gauge with the given string of elements and by the given amount. - * @param engine, the engine that owns the gauge. - * @param elements, the string that identifies the gauge to add to. - * @param tags, a map of {key, value} pairs of tags. - * @param amount, the amount to add to the gauge. - */ -envoy_status_t record_gauge_add(envoy_engine_t engine, const char* elements, envoy_stats_tags tags, - uint64_t amount); - -/** - * Subtract from the gauge with the given string of elements and by the given amount. - * @param engine, the engine that owns the gauge. - * @param elements, the string that identifies the gauge to subtract from. - * @param tags, a map of {key, value} pairs of tags. - * @param amount, amount to subtract from the gauge. - */ -envoy_status_t record_gauge_sub(envoy_engine_t engine, const char* elements, envoy_stats_tags tags, - uint64_t amount); - -/** - * Add another recorded amount to the histogram with the given string of elements and unit - * measurement. - * @param engine, the engine that owns the histogram. - * @param elements, the string that identifies the histogram to subtract from. - * @param tags, a map of {key, value} pairs of tags. - * @param value, amount to record as a new value for the histogram distribution. - * @param unit_measure, the unit of measurement (e.g. milliseconds, bytes, etc.) - */ -envoy_status_t record_histogram_value(envoy_engine_t engine, const char* elements, - envoy_stats_tags tags, uint64_t value, - envoy_histogram_stat_unit_t unit_measure); - -/** - * Flush the stats sinks outside of a flushing interval. - * Note: flushing before the engine has started will result in a no-op. - * Note: stats flushing may not be synchronous. - * Therefore, this function may return prior to flushing taking place. - */ -void flush_stats(envoy_engine_t engine); - -/** - * Collect a snapshot of all active stats. - * Note: this function may block for some time while collecting stats. - * @param engine, the engine whose stats to dump. - * @param data, out parameter to populate with stats data. - */ -envoy_status_t dump_stats(envoy_engine_t engine, envoy_data* data); - -/** - * Statically register APIs leveraging platform libraries. - * Warning: Must be completed before any calls to run_engine(). - * @param name, identifier of the platform API - * @param api, type-erased c struct containing function pointers and context. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t register_platform_api(const char* name, void* api); - -/** - * Refresh DNS, and drain connections associated with an engine. - * @param engine, handle to the engine to drain. - * @return envoy_status_t, the resulting status of the operation. - */ -envoy_status_t reset_connectivity_state(envoy_engine_t engine); - -#ifdef __cplusplus -} // functions -#endif diff --git a/mobile/library/common/network/BUILD b/mobile/library/common/network/BUILD index 332b4149265ea..7a119bf0bd521 100644 --- a/mobile/library/common/network/BUILD +++ b/mobile/library/common/network/BUILD @@ -46,7 +46,7 @@ envoy_cc_library( hdrs = ["socket_tag_socket_option_impl.h"], repository = "@envoy", deps = [ - "//library/common/jni:android_jni_utility_lib", + "//library/jni:android_jni_utility_lib", "@envoy//envoy/network:address_interface", "@envoy//source/common/common:scalar_to_byte_vector_lib", "@envoy//source/common/network:socket_option_lib", diff --git a/mobile/library/common/network/socket_tag_socket_option_impl.cc b/mobile/library/common/network/socket_tag_socket_option_impl.cc index 31aa2c3c8b660..8d7de6bac390d 100644 --- a/mobile/library/common/network/socket_tag_socket_option_impl.cc +++ b/mobile/library/common/network/socket_tag_socket_option_impl.cc @@ -5,7 +5,7 @@ #include "source/common/common/assert.h" #include "source/common/common/scalar_to_byte_vector.h" -#include "library/common/jni/android_jni_utility.h" +#include "library/jni/android_jni_utility.h" namespace Envoy { namespace Network { diff --git a/mobile/library/common/stream_info/extra_stream_info.cc b/mobile/library/common/stream_info/extra_stream_info.cc index 5ee40ae5627ea..25f60f81010d9 100644 --- a/mobile/library/common/stream_info/extra_stream_info.cc +++ b/mobile/library/common/stream_info/extra_stream_info.cc @@ -78,7 +78,7 @@ void setFinalStreamIntel(StreamInfo& stream_info, TimeSource& time_source, final_intel.sent_byte_count = stream_info.getUpstreamBytesMeter()->wireBytesSent(); final_intel.received_byte_count = stream_info.getUpstreamBytesMeter()->wireBytesReceived(); } - final_intel.response_flags = stream_info.responseFlags(); + final_intel.response_flags = stream_info.legacyResponseFlags(); } bool isStreamIdleTimeout(const StreamInfo& stream_info) { diff --git a/mobile/library/common/types/c_types.h b/mobile/library/common/types/c_types.h index 69bb7ba353d7a..1fa9ab7795095 100644 --- a/mobile/library/common/types/c_types.h +++ b/mobile/library/common/types/c_types.h @@ -211,7 +211,7 @@ typedef struct { uint64_t received_byte_count; // The final response flags for the stream. See // https://github.com/envoyproxy/envoy/blob/main/envoy/stream_info/stream_info.h - // for the ResponseFlag enum. + // for the CoreResponseFlag enum. uint64_t response_flags; // The upstream protocol, if an upstream connection was established. Field // entries are based off of Envoy's Http::Protocol @@ -222,6 +222,17 @@ typedef struct { int64_t upstream_protocol; } envoy_final_stream_intel; +/** The log level for the Envoy logger. The values should match with `Logger::Levels`. */ +typedef enum { + ENVOY_LOG_LEVEL_TRACE = 0, + ENVOY_LOG_LEVEL_DEBUG = 1, + ENVOY_LOG_LEVEL_INFO = 2, + ENVOY_LOG_LEVEL_WARN = 3, + ENVOY_LOG_LEVEL_ERROR = 4, + ENVOY_LOG_LEVEL_CRITICAL = 5, + ENVOY_LOG_LEVEL_OFF = 6, +} envoy_log_level; + #ifdef __cplusplus extern "C" { // utility functions #endif @@ -418,11 +429,12 @@ typedef void (*envoy_on_engine_running_f)(void* context); /** * Called when envoy's logger logs data. * + * @param level the log level * @param data, the logged data. * @param context, contains the necessary state to carry out platform-specific dispatch and * execution. */ -typedef void (*envoy_logger_log_f)(envoy_data data, const void* context); +typedef void (*envoy_logger_log_f)(envoy_log_level level, envoy_data data, const void* context); /** * Called when Envoy is done with the logger. diff --git a/mobile/library/java/io/envoyproxy/envoymobile/engine/types/EnvoyLogger.java b/mobile/library/java/io/envoyproxy/envoymobile/engine/types/EnvoyLogger.java index 9fe567ccf7e16..871e29b9960d7 100644 --- a/mobile/library/java/io/envoyproxy/envoymobile/engine/types/EnvoyLogger.java +++ b/mobile/library/java/io/envoyproxy/envoymobile/engine/types/EnvoyLogger.java @@ -1,5 +1,17 @@ package io.envoyproxy.envoymobile.engine.types; public interface EnvoyLogger { - void log(String str); + /** The log level for this logger. */ + interface Level { + int TRACE = 0; + int DEBUG = 1; + int INFO = 2; + int WARN = 3; + int ERROR = 4; + int CRITICAL = 5; + int OFF = 6; + } + + /** Logs the given string with the specified log level. */ + void log(int logLevel, String str); } diff --git a/mobile/library/java/org/chromium/net/impl/CronvoyEngineBuilderImpl.java b/mobile/library/java/org/chromium/net/impl/CronvoyEngineBuilderImpl.java index 7813bb95592a7..300050049da71 100644 --- a/mobile/library/java/org/chromium/net/impl/CronvoyEngineBuilderImpl.java +++ b/mobile/library/java/org/chromium/net/impl/CronvoyEngineBuilderImpl.java @@ -20,6 +20,8 @@ import org.chromium.net.ICronetEngineBuilder; import org.chromium.net.impl.Annotations.HttpCacheType; +import io.envoyproxy.envoymobile.engine.EnvoyEngine; + /** Implementation of {@link ICronetEngineBuilder} that builds Envoy-Mobile based Cronet engine. */ public abstract class CronvoyEngineBuilderImpl extends ICronetEngineBuilder { @@ -66,6 +68,8 @@ final static class Pkp { private String mExperimentalOptions; private boolean mNetworkQualityEstimatorEnabled; private int mThreadPriority = INVALID_THREAD_PRIORITY; + private EnvoyEngine.LogLevel mLogLevel = EnvoyEngine.LogLevel.OFF; + private CronvoyLogger mCronvoyLogger = new CronvoyLogger(); /** * Default config enables SPDY and QUIC, disables SDCH and HTTP cache. @@ -357,4 +361,22 @@ int threadPriority(int defaultThreadPriority) { * @return {@link Context} for builder. */ Context getContext() { return mApplicationContext; } + + /** Sets the log level. */ + public CronvoyEngineBuilderImpl setLogLevel(EnvoyEngine.LogLevel logLevel) { + this.mLogLevel = logLevel; + return this; + } + + /** Gets the log level. It defaults to `OFF` when not set. */ + public EnvoyEngine.LogLevel getLogLevel() { return mLogLevel; } + + /** Sets the {@link io.envoyproxy.envoymobile.engine.types.EnvoyLogger}. */ + public CronvoyEngineBuilderImpl setLogger(CronvoyLogger cronvoyLogger) { + this.mCronvoyLogger = cronvoyLogger; + return this; + } + + /** Gets the {@link org.chromium.net.impl.CronvoyLogger} implementation. */ + public CronvoyLogger getLogger() { return mCronvoyLogger; } } diff --git a/mobile/library/java/org/chromium/net/impl/CronvoyLogger.java b/mobile/library/java/org/chromium/net/impl/CronvoyLogger.java index 5bc09b0bee5cd..07d238f60af71 100644 --- a/mobile/library/java/org/chromium/net/impl/CronvoyLogger.java +++ b/mobile/library/java/org/chromium/net/impl/CronvoyLogger.java @@ -6,6 +6,7 @@ import java.nio.file.Files; import java.nio.file.Path; import java.nio.file.Paths; + import io.envoyproxy.envoymobile.engine.types.EnvoyLogger; /* @@ -21,7 +22,7 @@ * the desired file until CronvoyUrlRequestContext.stopNetLog disables Envoy logging. * */ -final class CronvoyLogger implements EnvoyLogger { +public class CronvoyLogger implements EnvoyLogger { private int mFilesize = 0; private String mFileName = null; private FileWriter mWriter = null; @@ -42,7 +43,7 @@ public void stopLogging() { } @Override - public void log(String str) { + public void log(int logLevel, String str) { if (mWriter != null) { try { Path path = Paths.get(mFileName); diff --git a/mobile/library/java/org/chromium/net/impl/CronvoyUrlRequestContext.java b/mobile/library/java/org/chromium/net/impl/CronvoyUrlRequestContext.java index 175314abdb493..bf6e5ae606431 100644 --- a/mobile/library/java/org/chromium/net/impl/CronvoyUrlRequestContext.java +++ b/mobile/library/java/org/chromium/net/impl/CronvoyUrlRequestContext.java @@ -47,7 +47,7 @@ public final class CronvoyUrlRequestContext extends CronvoyEngineBase { private final Object mLock = new Object(); private final ConditionVariable mInitCompleted = new ConditionVariable(false); private final AtomicInteger mActiveRequestCount = new AtomicInteger(0); - private EnvoyEngine.LogLevel mLogLevel = EnvoyEngine.LogLevel.OFF; + private EnvoyEngine.LogLevel mLogLevel; @GuardedBy("mLock") private EnvoyEngine mEngine; /** @@ -61,7 +61,7 @@ public final class CronvoyUrlRequestContext extends CronvoyEngineBase { private final String mUserAgent; private final AtomicReference mInitializationCompleter = new AtomicReference<>(); - private final CronvoyLogger mCronvoyLogger = new CronvoyLogger(); + private final CronvoyLogger mCronvoyLogger; /** * Locks operations on the list of RequestFinishedInfo.Listeners, because operations can happen @@ -84,8 +84,9 @@ public CronvoyUrlRequestContext(NativeCronvoyEngineBuilderImpl builder) { final int threadPriority = builder.threadPriority(THREAD_PRIORITY_BACKGROUND + THREAD_PRIORITY_MORE_FAVORABLE); mUserAgent = builder.getUserAgent(); + mLogLevel = builder.getLogLevel(); + mCronvoyLogger = builder.getLogger(); synchronized (mLock) { - mEngine = builder.createEngine(() -> { mNetworkThread = Thread.currentThread(); android.os.Process.setThreadPriority(threadPriority); diff --git a/mobile/library/common/jni/BUILD b/mobile/library/jni/BUILD similarity index 87% rename from mobile/library/common/jni/BUILD rename to mobile/library/jni/BUILD index 3e267aa786a0b..f19cffb1cb8a4 100644 --- a/mobile/library/common/jni/BUILD +++ b/mobile/library/jni/BUILD @@ -20,7 +20,7 @@ envoy_cc_library( }), repository = "@envoy", deps = [ - "//library/common/jni/import:jni_import_lib", + "//library/jni/import:jni_import_lib", ], ) @@ -37,12 +37,12 @@ envoy_cc_library( deps = [ ":jni_helper_lib", ":jni_support_lib", - "//library/common/jni/import:jni_import_lib", - "//library/common/jni/types:jni_env_lib", - "//library/common/jni/types:jni_exception_lib", "//library/common/types:c_types_lib", "//library/common/types:managed_types_lib", "//library/common/types:matcher_data_lib", + "//library/jni/import:jni_import_lib", + "//library/jni/types:jni_env_lib", + "//library/jni/types:jni_exception_lib", "@envoy//source/common/common:assert_lib", "@envoy//source/common/protobuf", ], @@ -58,7 +58,7 @@ envoy_cc_library( ], repository = "@envoy", deps = [ - "//library/common/jni/import:jni_import_lib", + "//library/jni/import:jni_import_lib", "@envoy//source/common/common:assert_lib", ], ) @@ -75,13 +75,13 @@ envoy_cc_library( ":android_network_utility_lib", ":jni_utility_lib", "//library/cc:engine_builder_lib", - "//library/common:envoy_main_interface_lib", + "//library/common:internal_engine_lib", "//library/common/api:c_types", "//library/common/extensions/cert_validator/platform_bridge:c_types_lib", "//library/common/extensions/key_value/platform:config", - "//library/common/jni/types:jni_exception_lib", - "//library/common/jni/types:jni_javavm_lib", "//library/common/types:managed_types_lib", + "//library/jni/types:jni_exception_lib", + "//library/jni/types:jni_javavm_lib", "@envoy//source/common/protobuf", ], # We need this to ensure that we link this into the .so even though there are no code references. @@ -103,10 +103,10 @@ envoy_cc_library( "//library/common/api:c_types", "//library/common/data:utility_lib", "//library/common/extensions/cert_validator/platform_bridge:c_types_lib", - "//library/common/jni/import:jni_import_lib", - "//library/common/jni/types:jni_exception_lib", - "//library/common/jni/types:jni_javavm_lib", "//library/common/types:c_types_lib", + "//library/jni/import:jni_import_lib", + "//library/jni/types:jni_exception_lib", + "//library/jni/types:jni_javavm_lib", "@envoy//bazel:boringssl", ], ) @@ -123,8 +123,8 @@ envoy_cc_library( ":jni_impl_lib", ":jni_support_lib", ":jni_utility_lib", - "//library/common:envoy_main_interface_lib", - "//library/common/jni/import:jni_import_lib", + "//library/common:internal_engine_lib", + "//library/jni/import:jni_import_lib", ], # We need this to ensure that we link this into the .so even though there are no code references. alwayslink = True, @@ -202,7 +202,7 @@ envoy_cc_library( ":jni_support_lib", ":jni_utility_lib", "//library/common/data:utility_lib", - "//library/common/jni/import:jni_import_lib", + "//library/jni/import:jni_import_lib", ], "//conditions:default": [], }), diff --git a/mobile/library/common/jni/android_jni_impl.cc b/mobile/library/jni/android_jni_impl.cc similarity index 82% rename from mobile/library/common/jni/android_jni_impl.cc rename to mobile/library/jni/android_jni_impl.cc index 46dc546f99be6..27dce22aac735 100644 --- a/mobile/library/common/jni/android_jni_impl.cc +++ b/mobile/library/jni/android_jni_impl.cc @@ -1,5 +1,5 @@ -#include "library/common/jni/import/jni_import.h" -#include "library/common/jni/jni_utility.h" +#include "library/jni/import/jni_import.h" +#include "library/jni/jni_utility.h" // NOLINT(namespace-envoy) diff --git a/mobile/library/common/jni/android_jni_utility.cc b/mobile/library/jni/android_jni_utility.cc similarity index 89% rename from mobile/library/common/jni/android_jni_utility.cc rename to mobile/library/jni/android_jni_utility.cc index c059b108950a6..ac11f1c4ed321 100644 --- a/mobile/library/common/jni/android_jni_utility.cc +++ b/mobile/library/jni/android_jni_utility.cc @@ -1,12 +1,12 @@ -#include "library/common/jni/android_jni_utility.h" +#include "library/jni/android_jni_utility.h" #include "source/common/common/assert.h" #if defined(__ANDROID_API__) #include "library/common/data/utility.h" -#include "library/common/jni/import/jni_import.h" -#include "library/common/jni/jni_support.h" -#include "library/common/jni/jni_utility.h" +#include "library/jni/import/jni_import.h" +#include "library/jni/jni_support.h" +#include "library/jni/jni_utility.h" #endif namespace Envoy { diff --git a/mobile/library/common/jni/android_jni_utility.h b/mobile/library/jni/android_jni_utility.h similarity index 100% rename from mobile/library/common/jni/android_jni_utility.h rename to mobile/library/jni/android_jni_utility.h diff --git a/mobile/library/common/jni/android_network_utility.cc b/mobile/library/jni/android_network_utility.cc similarity index 96% rename from mobile/library/common/jni/android_network_utility.cc rename to mobile/library/jni/android_network_utility.cc index 86d7cbb0d0dec..e8e2f71604cd6 100644 --- a/mobile/library/common/jni/android_network_utility.cc +++ b/mobile/library/jni/android_network_utility.cc @@ -1,10 +1,10 @@ -#include "library/common/jni/android_network_utility.h" +#include "library/jni/android_network_utility.h" #include "library/common/data/utility.h" -#include "library/common/jni/jni_support.h" -#include "library/common/jni/jni_utility.h" -#include "library/common/jni/types/exception.h" -#include "library/common/jni/types/java_virtual_machine.h" +#include "library/jni/jni_support.h" +#include "library/jni/jni_utility.h" +#include "library/jni/types/exception.h" +#include "library/jni/types/java_virtual_machine.h" #include "openssl/ssl.h" namespace Envoy { diff --git a/mobile/library/common/jni/android_network_utility.h b/mobile/library/jni/android_network_utility.h similarity index 90% rename from mobile/library/common/jni/android_network_utility.h rename to mobile/library/jni/android_network_utility.h index 034938a5ce1b1..ab02cde8ef390 100644 --- a/mobile/library/common/jni/android_network_utility.h +++ b/mobile/library/jni/android_network_utility.h @@ -6,8 +6,8 @@ #include "absl/strings/string_view.h" #include "library/common/api/c_types.h" #include "library/common/extensions/cert_validator/platform_bridge/c_types.h" -#include "library/common/jni/import/jni_import.h" -#include "library/common/jni/jni_helper.h" +#include "library/jni/import/jni_import.h" +#include "library/jni/jni_helper.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/import/BUILD b/mobile/library/jni/import/BUILD similarity index 100% rename from mobile/library/common/jni/import/BUILD rename to mobile/library/jni/import/BUILD diff --git a/mobile/library/common/jni/import/jni_import.h b/mobile/library/jni/import/jni_import.h similarity index 100% rename from mobile/library/common/jni/import/jni_import.h rename to mobile/library/jni/import/jni_import.h diff --git a/mobile/library/common/jni/java_jni_support.cc b/mobile/library/jni/java_jni_support.cc similarity index 88% rename from mobile/library/common/jni/java_jni_support.cc rename to mobile/library/jni/java_jni_support.cc index a24486c6de416..003cc31754b6f 100644 --- a/mobile/library/common/jni/java_jni_support.cc +++ b/mobile/library/jni/java_jni_support.cc @@ -1,4 +1,4 @@ -#include "library/common/jni/jni_support.h" +#include "library/jni/jni_support.h" // NOLINT(namespace-envoy) diff --git a/mobile/library/common/jni/jni_helper.cc b/mobile/library/jni/jni_helper.cc similarity index 99% rename from mobile/library/common/jni/jni_helper.cc rename to mobile/library/jni/jni_helper.cc index e22871d0c99e4..44beb06fc9ca4 100644 --- a/mobile/library/common/jni/jni_helper.cc +++ b/mobile/library/jni/jni_helper.cc @@ -1,4 +1,4 @@ -#include "library/common/jni/jni_helper.h" +#include "library/jni/jni_helper.h" #include "source/common/common/assert.h" diff --git a/mobile/library/common/jni/jni_helper.h b/mobile/library/jni/jni_helper.h similarity index 99% rename from mobile/library/common/jni/jni_helper.h rename to mobile/library/jni/jni_helper.h index 6eed430df777d..8b5f2e9e8f81b 100644 --- a/mobile/library/common/jni/jni_helper.h +++ b/mobile/library/jni/jni_helper.h @@ -2,7 +2,7 @@ #include -#include "library/common/jni/import/jni_import.h" +#include "library/jni/import/jni_import.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/jni_impl.cc b/mobile/library/jni/jni_impl.cc similarity index 93% rename from mobile/library/common/jni/jni_impl.cc rename to mobile/library/jni/jni_impl.cc index 49359696d6908..58f2dac107559 100644 --- a/mobile/library/common/jni/jni_impl.cc +++ b/mobile/library/jni/jni_impl.cc @@ -7,17 +7,16 @@ #include "library/cc/engine_builder.h" #include "library/common/api/c_types.h" #include "library/common/data/utility.h" -#include "library/common/engine.h" #include "library/common/extensions/filters/http/platform_bridge/c_types.h" #include "library/common/extensions/key_value/platform/c_types.h" -#include "library/common/jni/android_network_utility.h" -#include "library/common/jni/import/jni_import.h" -#include "library/common/jni/jni_support.h" -#include "library/common/jni/jni_utility.h" -#include "library/common/jni/types/exception.h" -#include "library/common/jni/types/java_virtual_machine.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" #include "library/common/types/managed_envoy_headers.h" +#include "library/jni/android_network_utility.h" +#include "library/jni/import/jni_import.h" +#include "library/jni/jni_support.h" +#include "library/jni/jni_utility.h" +#include "library/jni/types/exception.h" +#include "library/jni/types/java_virtual_machine.h" using Envoy::Platform::EngineBuilder; @@ -54,7 +53,7 @@ static void jvm_on_engine_running(void* context) { jni_helper.getEnv()->DeleteGlobalRef(j_context); } -static void jvm_on_log(envoy_data data, const void* context) { +static void jvm_on_log(envoy_log_level log_level, envoy_data data, const void* context) { if (context == nullptr) { return; } @@ -66,8 +65,8 @@ static void jvm_on_log(envoy_data data, const void* context) { Envoy::JNI::LocalRefUniquePtr jcls_JvmLoggerContext = jni_helper.getObjectClass(j_context); jmethodID jmid_onLog = - jni_helper.getMethodId(jcls_JvmLoggerContext.get(), "log", "(Ljava/lang/String;)V"); - jni_helper.callVoidMethod(j_context, jmid_onLog, str.get()); + jni_helper.getMethodId(jcls_JvmLoggerContext.get(), "log", "(ILjava/lang/String;)V"); + jni_helper.callVoidMethod(j_context, jmid_onLog, log_level, str.get()); release_envoy_data(data); } @@ -131,13 +130,15 @@ extern "C" JNIEXPORT jlong JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibr event_tracker.context = retained_context; } - return reinterpret_cast(new Envoy::Engine(native_callbacks, logger, event_tracker)); + return reinterpret_cast( + new Envoy::InternalEngine(native_callbacks, logger, event_tracker)); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_runEngine( JNIEnv* env, jclass, jlong engine, jstring config, jlong bootstrap_ptr, jstring log_level) { - const char* string_config = env->GetStringUTFChars(config, nullptr); - const char* string_log_level = env->GetStringUTFChars(log_level, nullptr); + Envoy::JNI::JniHelper jni_helper(env); + Envoy::JNI::StringUtfUniquePtr java_string_config = jni_helper.getStringUtfChars(config, nullptr); + Envoy::JNI::StringUtfUniquePtr java_log_level = jni_helper.getStringUtfChars(log_level, nullptr); // This should be either 0 (null) or a pointer generated by createBootstrap. // As documented in JniLibrary.java, take ownership. std::unique_ptr bootstrap( @@ -145,53 +146,45 @@ extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibra jint result; if (!bootstrap) { - result = reinterpret_cast(engine)->run(string_config, string_log_level); + result = reinterpret_cast(engine)->run(java_string_config.get(), + java_log_level.get()); } else { auto options = std::make_unique(); options->setConfigProto(std::move(bootstrap)); - ENVOY_BUG(options->setLogLevel(string_log_level).ok(), "invalid log level"); + ENVOY_BUG(options->setLogLevel(java_log_level.get()).ok(), "invalid log level"); options->setConcurrency(1); - result = reinterpret_cast(engine)->run(std::move(options)); + result = reinterpret_cast(engine)->run(std::move(options)); } - env->ReleaseStringUTFChars(config, string_config); - env->ReleaseStringUTFChars(log_level, string_log_level); return result; } extern "C" JNIEXPORT void JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_terminateEngine( JNIEnv* /*env*/, jclass, jlong engine_handle) { - reinterpret_cast(engine_handle)->terminate(); + reinterpret_cast(engine_handle)->terminate(); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_recordCounterInc( JNIEnv* env, jclass, // class - jlong engine, jstring elements, jobjectArray tags, jint count) { + jlong engine_handle, jstring elements, jobjectArray tags, jint count) { Envoy::JNI::JniHelper jni_helper(env); Envoy::JNI::StringUtfUniquePtr native_elements = jni_helper.getStringUtfChars(elements, nullptr); - jint result = record_counter_inc( - engine, native_elements.get(), - Envoy::JNI::javaArrayOfObjectArrayToEnvoyStatsTags(jni_helper, tags), count); - return result; + return reinterpret_cast(engine_handle) + ->recordCounterInc(native_elements.get(), + Envoy::JNI::javaArrayOfObjectArrayToEnvoyStatsTags(jni_helper, tags), + count); } extern "C" JNIEXPORT jstring JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_dumpStats(JNIEnv* env, jclass, // class - jlong engine) { + jlong engine_handle) { jni_log("[Envoy]", "dumpStats"); - envoy_data data; - jint result = dump_stats(engine, &data); - if (result != ENVOY_SUCCESS) { - return env->NewStringUTF(""); - } - + auto engine = reinterpret_cast(engine_handle); + std::string stats = engine->dumpStats(); Envoy::JNI::JniHelper jni_helper(env); - Envoy::JNI::LocalRefUniquePtr str = Envoy::JNI::envoyDataToJavaString(jni_helper, data); - release_envoy_data(data); - - return str.release(); + return jni_helper.newStringUtf(stats.c_str()).release(); } // JvmCallbackContext @@ -916,13 +909,13 @@ static envoy_data jvm_get_string(const void* context) { extern "C" JNIEXPORT jlong JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_initStream( JNIEnv* /*env*/, jclass, jlong engine_handle) { - return init_stream(static_cast(engine_handle)); + auto engine = reinterpret_cast(engine_handle); + return engine->initStream(); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_startStream( JNIEnv* env, jclass, jlong engine_handle, jlong stream_handle, jobject j_context, jboolean explicit_flow_control) { - // TODO: To be truly safe we may need stronger guarantees of operation ordering on this ref. jobject retained_context = env->NewGlobalRef(j_context); envoy_http_callbacks native_callbacks = {jvm_on_response_headers, @@ -934,9 +927,9 @@ extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibra jvm_on_cancel, jvm_on_send_window_available, retained_context}; - envoy_status_t result = start_stream(static_cast(engine_handle), - static_cast(stream_handle), native_callbacks, - explicit_flow_control); + auto engine = reinterpret_cast(engine_handle); + envoy_status_t result = engine->startStream(static_cast(stream_handle), + native_callbacks, explicit_flow_control); if (result != ENVOY_SUCCESS) { env->DeleteGlobalRef(retained_context); // No callbacks are fired and we need to release } @@ -962,8 +955,10 @@ Java_io_envoyproxy_envoymobile_engine_JniLibrary_registerKeyValueStore(JNIEnv* e api->remove = jvm_kv_store_remove; api->context = retained_context; - envoy_status_t result = register_platform_api(env->GetStringUTFChars(name, nullptr), api); - return result; + Envoy::JNI::JniHelper jni_helper(env); + Envoy::JNI::StringUtfUniquePtr native_java_string = jni_helper.getStringUtfChars(name, nullptr); + Envoy::Api::External::registerApi(/*name=*/std::string(native_java_string.get()), api); + return ENVOY_SUCCESS; } // EnvoyHTTPFilter @@ -997,8 +992,11 @@ Java_io_envoyproxy_envoymobile_engine_JniLibrary_registerFilterFactory(JNIEnv* e api->static_context = retained_context; api->instance_context = nullptr; - envoy_status_t result = register_platform_api(env->GetStringUTFChars(filter_name, nullptr), api); - return result; + Envoy::JNI::JniHelper jni_helper(env); + Envoy::JNI::StringUtfUniquePtr native_java_string = + jni_helper.getStringUtfChars(filter_name, nullptr); + Envoy::Api::External::registerApi(/*name=*/std::string(native_java_string.get()), api); + return ENVOY_SUCCESS; } extern "C" JNIEXPORT void JNICALL @@ -1041,8 +1039,8 @@ Java_io_envoyproxy_envoymobile_engine_EnvoyHTTPFilterCallbacksImpl_callReleaseCa extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_readData( JNIEnv* /*env*/, jclass, jlong engine_handle, jlong stream_handle, jlong byte_count) { - return read_data(static_cast(engine_handle), - static_cast(stream_handle), byte_count); + return reinterpret_cast(engine_handle) + ->readData(static_cast(stream_handle), byte_count); } // The Java counterpart guarantees to invoke this method with a non-null direct ByteBuffer where the @@ -1054,9 +1052,9 @@ extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibra if (end_stream) { jni_log("[Envoy]", "jvm_send_data_end_stream"); } - return send_data(static_cast(engine_handle), - static_cast(stream_handle), - Envoy::JNI::javaByteBufferToEnvoyData(jni_helper, data, length), end_stream); + return reinterpret_cast(engine_handle) + ->sendData(static_cast(stream_handle), + Envoy::JNI::javaByteBufferToEnvoyData(jni_helper, data, length), end_stream); } // The Java counterpart guarantees to invoke this method with a non-null jbyteArray where the @@ -1073,33 +1071,34 @@ Java_io_envoyproxy_envoymobile_engine_JniLibrary_sendDataByteArray(JNIEnv* env, if (end_stream) { jni_log("[Envoy]", "jvm_send_data_end_stream"); } - return send_data(static_cast(engine_handle), - static_cast(stream_handle), - Envoy::JNI::javaByteArrayToEnvoyData(jni_helper, data, length), end_stream); + return reinterpret_cast(engine_handle) + ->sendData(static_cast(stream_handle), + Envoy::JNI::javaByteArrayToEnvoyData(jni_helper, data, length), end_stream); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_sendHeaders( JNIEnv* env, jclass, jlong engine_handle, jlong stream_handle, jobjectArray headers, jboolean end_stream) { Envoy::JNI::JniHelper jni_helper(env); - return send_headers( - static_cast(engine_handle), static_cast(stream_handle), - Envoy::JNI::javaArrayOfObjectArrayToEnvoyHeaders(jni_helper, headers), end_stream); + return reinterpret_cast(engine_handle) + ->sendHeaders(static_cast(stream_handle), + Envoy::JNI::javaArrayOfObjectArrayToEnvoyHeaders(jni_helper, headers), + end_stream); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_sendTrailers( JNIEnv* env, jclass, jlong engine_handle, jlong stream_handle, jobjectArray trailers) { Envoy::JNI::JniHelper jni_helper(env); jni_log("[Envoy]", "jvm_send_trailers"); - return send_trailers(static_cast(engine_handle), - static_cast(stream_handle), - Envoy::JNI::javaArrayOfObjectArrayToEnvoyHeaders(jni_helper, trailers)); + return reinterpret_cast(engine_handle) + ->sendTrailers(static_cast(stream_handle), + Envoy::JNI::javaArrayOfObjectArrayToEnvoyHeaders(jni_helper, trailers)); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_resetStream( JNIEnv* /*env*/, jclass, jlong engine_handle, jlong stream_handle) { - return reset_stream(static_cast(engine_handle), - static_cast(stream_handle)); + return reinterpret_cast(engine_handle) + ->cancelStream(static_cast(stream_handle)); } // EnvoyStringAccessor @@ -1118,9 +1117,12 @@ Java_io_envoyproxy_envoymobile_engine_JniLibrary_registerStringAccessor(JNIEnv* string_accessor->get_string = jvm_get_string; string_accessor->context = retained_context; - envoy_status_t result = - register_platform_api(env->GetStringUTFChars(accessor_name, nullptr), string_accessor); - return result; + Envoy::JNI::JniHelper jni_helper(env); + Envoy::JNI::StringUtfUniquePtr native_java_string = + jni_helper.getStringUtfChars(accessor_name, nullptr); + Envoy::Api::External::registerApi(/*name=*/std::string(native_java_string.get()), + string_accessor); + return ENVOY_SUCCESS; } // Takes a jstring from Java, converts it to a C++ string, calls the supplied @@ -1369,7 +1371,7 @@ Java_io_envoyproxy_envoymobile_engine_JniLibrary_resetConnectivityState(JNIEnv* jclass, // class jlong engine) { jni_log("[Envoy]", "resetConnectivityState"); - return reset_connectivity_state(engine); + return reinterpret_cast(engine)->resetConnectivityState(); } extern "C" JNIEXPORT jint JNICALL @@ -1377,8 +1379,8 @@ Java_io_envoyproxy_envoymobile_engine_JniLibrary_setPreferredNetwork(JNIEnv* /*e jclass, // class jlong engine, jint network) { jni_log("[Envoy]", "setting preferred network"); - return set_preferred_network(static_cast(engine), - static_cast(network)); + return reinterpret_cast(engine)->setPreferredNetwork( + static_cast(network)); } extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibrary_setProxySettings( @@ -1387,13 +1389,13 @@ extern "C" JNIEXPORT jint JNICALL Java_io_envoyproxy_envoymobile_engine_JniLibra jlong engine, jstring host, jint port) { jni_log("[Envoy]", "setProxySettings"); - const char* native_host = env->GetStringUTFChars(host, nullptr); + Envoy::JNI::JniHelper jni_helper(env); + Envoy::JNI::StringUtfUniquePtr java_host = jni_helper.getStringUtfChars(host, nullptr); const uint16_t native_port = static_cast(port); - envoy_status_t result = - set_proxy_settings(static_cast(engine), native_host, native_port); + envoy_status_t result = reinterpret_cast(engine)->setProxySettings( + java_host.get(), native_port); - env->ReleaseStringUTFChars(host, native_host); return result; } diff --git a/mobile/library/common/jni/jni_support.h b/mobile/library/jni/jni_support.h similarity index 83% rename from mobile/library/common/jni/jni_support.h rename to mobile/library/jni/jni_support.h index 41b493c3ef1cc..45fef67f3fa3e 100644 --- a/mobile/library/common/jni/jni_support.h +++ b/mobile/library/jni/jni_support.h @@ -1,6 +1,6 @@ #pragma once -#include "library/common/jni/import/jni_import.h" +#include "library/jni/import/jni_import.h" // NOLINT(namespace-envoy) diff --git a/mobile/library/common/jni/jni_utility.cc b/mobile/library/jni/jni_utility.cc similarity index 98% rename from mobile/library/common/jni/jni_utility.cc rename to mobile/library/jni/jni_utility.cc index 3105aa0d5be2a..998a57b024c98 100644 --- a/mobile/library/common/jni/jni_utility.cc +++ b/mobile/library/jni/jni_utility.cc @@ -1,13 +1,13 @@ -#include "library/common/jni/jni_utility.h" +#include "library/jni/jni_utility.h" #include #include #include "source/common/common/assert.h" -#include "library/common/jni/jni_support.h" -#include "library/common/jni/types/env.h" -#include "library/common/jni/types/exception.h" +#include "library/jni/jni_support.h" +#include "library/jni/types/env.h" +#include "library/jni/types/exception.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/jni_utility.h b/mobile/library/jni/jni_utility.h similarity index 98% rename from mobile/library/common/jni/jni_utility.h rename to mobile/library/jni/jni_utility.h index e7db6f4289a1b..e98233891929e 100644 --- a/mobile/library/common/jni/jni_utility.h +++ b/mobile/library/jni/jni_utility.h @@ -5,11 +5,11 @@ #include "source/common/protobuf/protobuf.h" -#include "library/common/jni/import/jni_import.h" -#include "library/common/jni/jni_helper.h" #include "library/common/types/c_types.h" #include "library/common/types/managed_envoy_headers.h" #include "library/common/types/matcher_data.h" +#include "library/jni/import/jni_import.h" +#include "library/jni/jni_helper.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/ndk_jni_support.cc b/mobile/library/jni/ndk_jni_support.cc similarity index 91% rename from mobile/library/common/jni/ndk_jni_support.cc rename to mobile/library/jni/ndk_jni_support.cc index a3b8ca02eb20e..ecd4f2c98a82e 100644 --- a/mobile/library/common/jni/ndk_jni_support.cc +++ b/mobile/library/jni/ndk_jni_support.cc @@ -1,6 +1,6 @@ #include -#include "library/common/jni/jni_support.h" +#include "library/jni/jni_support.h" // NOLINT(namespace-envoy) diff --git a/mobile/library/common/jni/types/BUILD b/mobile/library/jni/types/BUILD similarity index 76% rename from mobile/library/common/jni/types/BUILD rename to mobile/library/jni/types/BUILD index 76b702d9b2c5e..b8fbd4f7ebac3 100644 --- a/mobile/library/common/jni/types/BUILD +++ b/mobile/library/jni/types/BUILD @@ -14,8 +14,8 @@ envoy_cc_library( ], repository = "@envoy", deps = [ - "//library/common/jni/import:jni_import_lib", - "//library/common/jni/types:jni_string_lib", + "//library/jni/import:jni_import_lib", + "//library/jni/types:jni_string_lib", "@envoy//source/common/common:assert_lib", ], # We need this to ensure that we link this into the .so even though there are no code references. @@ -29,8 +29,8 @@ envoy_cc_library( ], repository = "@envoy", deps = [ - "//library/common/jni/import:jni_import_lib", - "//library/common/jni/types:jni_env_lib", + "//library/jni/import:jni_import_lib", + "//library/jni/types:jni_env_lib", ], # We need this to ensure that we link this into the .so even though there are no code references. alwayslink = True, @@ -46,9 +46,9 @@ envoy_cc_library( ], repository = "@envoy", deps = [ - "//library/common/jni:jni_support_lib", - "//library/common/jni/import:jni_import_lib", - "//library/common/jni/types:jni_javavm_lib", + "//library/jni:jni_support_lib", + "//library/jni/import:jni_import_lib", + "//library/jni/types:jni_javavm_lib", "@envoy//source/common/common:assert_lib", ], # We need this to ensure that we link this into the .so even though there are no code references. @@ -65,8 +65,8 @@ envoy_cc_library( ], repository = "@envoy", deps = [ - "//library/common/jni:jni_support_lib", - "//library/common/jni/import:jni_import_lib", + "//library/jni:jni_support_lib", + "//library/jni/import:jni_import_lib", "@envoy//source/common/common:assert_lib", ], # We need this to ensure that we link this into the .so even though there are no code references. diff --git a/mobile/library/common/jni/types/env.cc b/mobile/library/jni/types/env.cc similarity index 86% rename from mobile/library/common/jni/types/env.cc rename to mobile/library/jni/types/env.cc index d4e2ad8b5b355..d0591ce5a4b08 100644 --- a/mobile/library/common/jni/types/env.cc +++ b/mobile/library/jni/types/env.cc @@ -1,9 +1,9 @@ -#include "library/common/jni/types/env.h" +#include "library/jni/types/env.h" #include "source/common/common/assert.h" -#include "library/common/jni/jni_support.h" -#include "library/common/jni/types/java_virtual_machine.h" +#include "library/jni/jni_support.h" +#include "library/jni/types/java_virtual_machine.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/types/env.h b/mobile/library/jni/types/env.h similarity index 82% rename from mobile/library/common/jni/types/env.h rename to mobile/library/jni/types/env.h index b44eec694e2e8..a6f2621b19284 100644 --- a/mobile/library/common/jni/types/env.h +++ b/mobile/library/jni/types/env.h @@ -1,6 +1,6 @@ #pragma once -#include "library/common/jni/import/jni_import.h" +#include "library/jni/import/jni_import.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/types/exception.cc b/mobile/library/jni/types/exception.cc similarity index 97% rename from mobile/library/common/jni/types/exception.cc rename to mobile/library/jni/types/exception.cc index 3519d909ce532..1d328a2c3809f 100644 --- a/mobile/library/common/jni/types/exception.cc +++ b/mobile/library/jni/types/exception.cc @@ -1,10 +1,10 @@ -#include "library/common/jni/types/exception.h" +#include "library/jni/types/exception.h" #include "source/common/common/assert.h" #include "fmt/format.h" -#include "library/common/jni/types/env.h" -#include "library/common/jni/types/string.h" +#include "library/jni/types/env.h" +#include "library/jni/types/string.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/types/exception.h b/mobile/library/jni/types/exception.h similarity index 96% rename from mobile/library/common/jni/types/exception.h rename to mobile/library/jni/types/exception.h index 38535767cc272..f6c4c7e8d5d72 100644 --- a/mobile/library/common/jni/types/exception.h +++ b/mobile/library/jni/types/exception.h @@ -2,7 +2,7 @@ #include -#include "library/common/jni/import/jni_import.h" +#include "library/jni/import/jni_import.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/types/java_virtual_machine.cc b/mobile/library/jni/types/java_virtual_machine.cc similarity index 88% rename from mobile/library/common/jni/types/java_virtual_machine.cc rename to mobile/library/jni/types/java_virtual_machine.cc index cbf6671fb2918..b9db12d6b9d79 100644 --- a/mobile/library/common/jni/types/java_virtual_machine.cc +++ b/mobile/library/jni/types/java_virtual_machine.cc @@ -1,8 +1,8 @@ -#include "library/common/jni/types/java_virtual_machine.h" +#include "library/jni/types/java_virtual_machine.h" #include "source/common/common/assert.h" -#include "library/common/jni/jni_support.h" +#include "library/jni/jni_support.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/types/java_virtual_machine.h b/mobile/library/jni/types/java_virtual_machine.h similarity index 92% rename from mobile/library/common/jni/types/java_virtual_machine.h rename to mobile/library/jni/types/java_virtual_machine.h index fd5113036ffad..fb36be6285efc 100644 --- a/mobile/library/common/jni/types/java_virtual_machine.h +++ b/mobile/library/jni/types/java_virtual_machine.h @@ -1,6 +1,6 @@ #pragma once -#include "library/common/jni/import/jni_import.h" +#include "library/jni/import/jni_import.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/common/jni/types/string.h b/mobile/library/jni/types/string.h similarity index 92% rename from mobile/library/common/jni/types/string.h rename to mobile/library/jni/types/string.h index 3229a717db076..f444ce65dfaee 100644 --- a/mobile/library/common/jni/types/string.h +++ b/mobile/library/jni/types/string.h @@ -1,8 +1,8 @@ #pragma once #include "absl/strings/string_view.h" -#include "library/common/jni/import/jni_import.h" -#include "library/common/jni/types/env.h" +#include "library/jni/import/jni_import.h" +#include "library/jni/types/env.h" namespace Envoy { namespace JNI { diff --git a/mobile/library/kotlin/io/envoyproxy/envoymobile/AndroidEngineBuilder.kt b/mobile/library/kotlin/io/envoyproxy/envoymobile/AndroidEngineBuilder.kt index 9d07422f17290..3ef9ff70a6f04 100644 --- a/mobile/library/kotlin/io/envoyproxy/envoymobile/AndroidEngineBuilder.kt +++ b/mobile/library/kotlin/io/envoyproxy/envoymobile/AndroidEngineBuilder.kt @@ -10,7 +10,13 @@ constructor(context: Context, baseConfiguration: BaseConfiguration = Standard()) EngineBuilder(baseConfiguration) { init { addEngineType { - AndroidEngineImpl(context, onEngineRunning, logger, eventTracker, enableProxying) + AndroidEngineImpl( + context, + onEngineRunning, + { level, msg -> logger?.let { it(LogLevel.from(level), msg) } }, + eventTracker, + enableProxying + ) } } } diff --git a/mobile/library/kotlin/io/envoyproxy/envoymobile/BUILD b/mobile/library/kotlin/io/envoyproxy/envoymobile/BUILD index 190c67a334926..9cac0f660b8f6 100644 --- a/mobile/library/kotlin/io/envoyproxy/envoymobile/BUILD +++ b/mobile/library/kotlin/io/envoyproxy/envoymobile/BUILD @@ -14,8 +14,8 @@ android_artifacts( archive_name = "envoy", manifest = "EnvoyManifest.xml", native_deps = select({ - "@envoy//bazel:opt_build": ["//library/common/jni:libenvoy_jni.so.debug_info"], - "//conditions:default": ["//library/common/jni:libenvoy_jni.so"], + "@envoy//bazel:opt_build": ["//library/jni:libenvoy_jni.so.debug_info"], + "//conditions:default": ["//library/jni:libenvoy_jni.so"], }), proguard_rules = "//library:proguard_rules", substitutions = { @@ -31,8 +31,8 @@ android_artifacts( archive_name = "envoy_xds", manifest = "EnvoyManifest.xml", native_deps = select({ - "@envoy//bazel:opt_build": ["//library/common/jni:libenvoy_jni.so.debug_info"], - "//conditions:default": ["//library/common/jni:libenvoy_jni.so"], + "@envoy//bazel:opt_build": ["//library/jni:libenvoy_jni.so.debug_info"], + "//conditions:default": ["//library/jni:libenvoy_jni.so"], }), proguard_rules = "//library:proguard_rules", substitutions = { diff --git a/mobile/library/kotlin/io/envoyproxy/envoymobile/EngineBuilder.kt b/mobile/library/kotlin/io/envoyproxy/envoymobile/EngineBuilder.kt index 71775630f3fd2..5bab475bf68ba 100644 --- a/mobile/library/kotlin/io/envoyproxy/envoymobile/EngineBuilder.kt +++ b/mobile/library/kotlin/io/envoyproxy/envoymobile/EngineBuilder.kt @@ -130,12 +130,16 @@ open class XdsBuilder(internal val xdsServerAddress: String, internal val xdsSer /** Builder used for creating and running a new `Engine` instance. */ open class EngineBuilder(private val configuration: BaseConfiguration = Standard()) { protected var onEngineRunning: (() -> Unit) = {} - protected var logger: ((String) -> Unit)? = null + protected var logger: ((LogLevel, String) -> Unit)? = null protected var eventTracker: ((Map) -> Unit)? = null protected var enableProxying = false private var runtimeGuards = mutableMapOf() private var engineType: () -> EnvoyEngine = { - EnvoyEngineImpl(onEngineRunning, logger, eventTracker) + EnvoyEngineImpl( + onEngineRunning, + { level, msg -> logger?.let { it(LogLevel.from(level), msg) } }, + eventTracker + ) } private var logLevel = LogLevel.INFO private var connectTimeoutSeconds = 30 @@ -474,7 +478,7 @@ open class EngineBuilder(private val configuration: BaseConfiguration = Standard * @param closure: The closure to be called. * @return This builder. */ - fun setLogger(closure: (String) -> Unit): EngineBuilder { + fun setLogger(closure: (LogLevel, String) -> Unit): EngineBuilder { this.logger = closure return this } diff --git a/mobile/library/kotlin/io/envoyproxy/envoymobile/LogLevel.kt b/mobile/library/kotlin/io/envoyproxy/envoymobile/LogLevel.kt index 63887409a5800..60091aa7712f0 100644 --- a/mobile/library/kotlin/io/envoyproxy/envoymobile/LogLevel.kt +++ b/mobile/library/kotlin/io/envoyproxy/envoymobile/LogLevel.kt @@ -13,5 +13,20 @@ enum class LogLevel(internal val level: String, val levelInt: Int) { WARN("warn", 3), ERROR("error", 4), CRITICAL("critical", 5), - OFF("off", -1) + OFF("off", 6); + + companion object { + /** Converts from numeric int to `LogLevel`. */ + fun from(level: Int): LogLevel { + return when (level) { + 0 -> TRACE + 1 -> DEBUG + 2 -> INFO + 3 -> WARN + 4 -> ERROR + 5 -> CRITICAL + else -> OFF + } + } + } } diff --git a/mobile/library/objective-c/BUILD b/mobile/library/objective-c/BUILD index 44d83f5f69a40..00d6435a4939c 100644 --- a/mobile/library/objective-c/BUILD +++ b/mobile/library/objective-c/BUILD @@ -27,13 +27,13 @@ envoy_objc_library( "EnvoyHTTPFilterFactory.h", "EnvoyHTTPFilterFactory.m", "EnvoyHTTPStream.h", - "EnvoyHTTPStreamImpl.m", + "EnvoyHTTPStreamImpl.mm", "EnvoyLogger.h", "EnvoyLogger.m", "EnvoyNativeFilterConfig.h", "EnvoyNativeFilterConfig.m", "EnvoyNetworkMonitor.h", - "EnvoyNetworkMonitor.m", + "EnvoyNetworkMonitor.mm", "EnvoyStringAccessor.h", "EnvoyStringAccessor.m", ], @@ -57,7 +57,7 @@ envoy_objc_library( ":envoy_key_value_store_lib", ":envoy_objc_bridge_lib", "//library/cc:engine_builder_lib", - "//library/common:envoy_main_interface_lib", + "//library/common:internal_engine_lib", "//library/common/api:c_types", "//library/common/network:apple_platform_cert_verifier", ], diff --git a/mobile/library/objective-c/EnvoyConfiguration.mm b/mobile/library/objective-c/EnvoyConfiguration.mm index 00a60f6bb1ccd..02b8cf8a253bc 100644 --- a/mobile/library/objective-c/EnvoyConfiguration.mm +++ b/mobile/library/objective-c/EnvoyConfiguration.mm @@ -1,6 +1,5 @@ #import "library/objective-c/EnvoyEngine.h" -#import "library/common/main_interface.h" #import "library/cc/engine_builder.h" #include "source/common/protobuf/utility.h" diff --git a/mobile/library/objective-c/EnvoyEngine.h b/mobile/library/objective-c/EnvoyEngine.h index 80c47aae7c4c8..bddcd07755079 100644 --- a/mobile/library/objective-c/EnvoyEngine.h +++ b/mobile/library/objective-c/EnvoyEngine.h @@ -35,7 +35,7 @@ NS_ASSUME_NONNULL_BEGIN @param networkMonitoringMode Configure how the engines observe network reachability. */ - (instancetype)initWithRunningCallback:(nullable void (^)())onEngineRunning - logger:(nullable void (^)(NSString *))logger + logger:(nullable void (^)(NSInteger, NSString *))logger eventTracker:(nullable void (^)(EnvoyEvent *))eventTracker networkMonitoringMode:(int)networkMonitoringMode; /** diff --git a/mobile/library/objective-c/EnvoyEngineImpl.mm b/mobile/library/objective-c/EnvoyEngineImpl.mm index a912a0d1c2b5b..adac27f8ed0af 100644 --- a/mobile/library/objective-c/EnvoyEngineImpl.mm +++ b/mobile/library/objective-c/EnvoyEngineImpl.mm @@ -5,11 +5,10 @@ #include "library/common/api/c_types.h" -#import "library/common/main_interface.h" #import "library/common/types/c_types.h" #import "library/common/extensions/key_value/platform/c_types.h" #import "library/cc/engine_builder.h" -#import "library/common/engine.h" +#import "library/common/internal_engine.h" #if TARGET_OS_IPHONE #import @@ -38,12 +37,12 @@ static void ios_on_exit(void *context) { } } -static void ios_on_log(envoy_data data, const void *context) { +static void ios_on_log(envoy_log_level log_level, envoy_data data, const void *context) { // This code block runs inside the Envoy event loop. Therefore, an explicit autoreleasepool block // is necessary to act as a breaker for any Objective-C allocation that happens. @autoreleasepool { EnvoyLogger *logger = (__bridge EnvoyLogger *)context; - logger.log(to_ios_string(data)); + logger.log(log_level, to_ios_string(data)); } } @@ -399,12 +398,12 @@ static void ios_track_event(envoy_map map, const void *context) { @implementation EnvoyEngineImpl { envoy_engine_t _engineHandle; - Envoy::Engine *_engine; + Envoy::InternalEngine *_engine; EnvoyNetworkMonitor *_networkMonitor; } - (instancetype)initWithRunningCallback:(nullable void (^)())onEngineRunning - logger:(nullable void (^)(NSString *))logger + logger:(nullable void (^)(NSInteger, NSString *))logger eventTracker:(nullable void (^)(EnvoyEvent *))eventTracker networkMonitoringMode:(int)networkMonitoringMode { self = [super init]; @@ -434,7 +433,7 @@ - (instancetype)initWithRunningCallback:(nullable void (^)())onEngineRunning native_event_tracker.context = CFBridgingRetain(objcEventTracker); } - _engine = new Envoy::Engine(native_callbacks, native_logger, native_event_tracker); + _engine = new Envoy::InternalEngine(native_callbacks, native_logger, native_event_tracker); _engineHandle = reinterpret_cast(_engine); if (networkMonitoringMode == 1) { @@ -473,7 +472,7 @@ - (int)registerFilterFactory:(EnvoyHTTPFilterFactory *)filterFactory { api->static_context = CFBridgingRetain(filterFactory); api->instance_context = NULL; - register_platform_api(filterFactory.filterName.UTF8String, api); + Envoy::Api::External::registerApi(filterFactory.filterName.UTF8String, api); return kEnvoySuccess; } @@ -485,7 +484,8 @@ - (int)registerStringAccessor:(NSString *)name accessor:(EnvoyStringAccessor *)a accessorStruct->get_string = ios_get_string; accessorStruct->context = CFBridgingRetain(accessor); - return register_platform_api(name.UTF8String, accessorStruct); + Envoy::Api::External::registerApi(name.UTF8String, accessorStruct); + return ENVOY_SUCCESS; } - (int)registerKeyValueStore:(NSString *)name keyValueStore:(id)keyValueStore { @@ -495,7 +495,8 @@ - (int)registerKeyValueStore:(NSString *)name keyValueStore:(idremove = ios_kv_store_remove; api->context = CFBridgingRetain(keyValueStore); - return register_platform_api(name.UTF8String, api); + Envoy::Api::External::registerApi(name.UTF8String, api); + return ENVOY_SUCCESS; } - (void)performRegistrationsForConfig:(EnvoyConfiguration *)config { @@ -556,29 +557,24 @@ - (int)runWithYAML:(NSString *)yaml - (id)startStreamWithCallbacks:(EnvoyHTTPCallbacks *)callbacks explicitFlowControl:(BOOL)explicitFlowControl { - return [[EnvoyHTTPStreamImpl alloc] initWithHandle:init_stream(_engineHandle) - engine:_engineHandle + return [[EnvoyHTTPStreamImpl alloc] initWithHandle:_engine->initStream() + engine:reinterpret_cast(_engine) callbacks:callbacks explicitFlowControl:explicitFlowControl]; } - (int)recordCounterInc:(NSString *)elements tags:(EnvoyTags *)tags count:(NSUInteger)count { // TODO: update to use real tag array when the API layer change is ready. - return record_counter_inc(_engineHandle, elements.UTF8String, toNativeStatsTags(tags), count); + return _engine->recordCounterInc(elements.UTF8String, toNativeStatsTags(tags), count); } - (NSString *)dumpStats { - envoy_data data; - envoy_status_t status = dump_stats(_engineHandle, &data); - if (status != ENVOY_SUCCESS) { + std::string status = _engine->dumpStats(); + if (status == "") { return @""; } - NSString *stringCopy = [[NSString alloc] initWithBytes:data.bytes - length:data.length - encoding:NSUTF8StringEncoding]; - release_envoy_data(data); - return stringCopy; + return @(status.c_str()); } - (void)terminate { @@ -586,7 +582,7 @@ - (void)terminate { } - (void)resetConnectivityState { - reset_connectivity_state(_engineHandle); + _engine->resetConnectivityState(); } #pragma mark - Private diff --git a/mobile/library/objective-c/EnvoyHTTPStreamImpl.m b/mobile/library/objective-c/EnvoyHTTPStreamImpl.mm similarity index 90% rename from mobile/library/objective-c/EnvoyHTTPStreamImpl.m rename to mobile/library/objective-c/EnvoyHTTPStreamImpl.mm index 16d6f0af0f931..732eeac0e4c41 100644 --- a/mobile/library/objective-c/EnvoyHTTPStreamImpl.m +++ b/mobile/library/objective-c/EnvoyHTTPStreamImpl.mm @@ -1,8 +1,8 @@ #import "library/objective-c/EnvoyEngine.h" #import "library/objective-c/EnvoyBridgeUtility.h" -#import "library/common/main_interface.h" #import "library/common/types/c_types.h" +#import "library/common/internal_engine.h" #import @@ -138,11 +138,11 @@ @implementation EnvoyHTTPStreamImpl { EnvoyHTTPCallbacks *_platformCallbacks; envoy_http_callbacks _nativeCallbacks; envoy_stream_t _streamHandle; - envoy_engine_t _engineHandle; + Envoy::InternalEngine *_engine; } - (instancetype)initWithHandle:(envoy_stream_t)handle - engine:(envoy_engine_t)engineHandle + engine:(intptr_t)engine callbacks:(EnvoyHTTPCallbacks *)callbacks explicitFlowControl:(BOOL)explicitFlowControl { self = [super init]; @@ -168,17 +168,13 @@ - (instancetype)initWithHandle:(envoy_stream_t)handle context}; _nativeCallbacks = native_callbacks; - _engineHandle = engineHandle; + _engine = reinterpret_cast(engine); // We need create the native-held strong ref on this stream before we call start_stream because // start_stream could result in a reset that would release the native ref. _strongSelf = self; - envoy_status_t result = - start_stream(engineHandle, _streamHandle, native_callbacks, explicitFlowControl); - if (result != ENVOY_SUCCESS) { - _strongSelf = nil; - return nil; - } + _streamHandle = _engine->initStream(); + _engine->startStream(_streamHandle, native_callbacks, explicitFlowControl); return self; } @@ -190,23 +186,24 @@ - (void)dealloc { } - (void)sendHeaders:(EnvoyHeaders *)headers close:(BOOL)close { - send_headers(_engineHandle, _streamHandle, toNativeHeaders(headers), close); + _engine->sendHeaders(_streamHandle, toNativeHeaders(headers), close); } - (void)sendData:(NSData *)data close:(BOOL)close { - send_data(_engineHandle, _streamHandle, toNativeData(data), close); + _engine->sendData(_streamHandle, toNativeData(data), close); } - (void)readData:(size_t)byteCount { - read_data(_engineHandle, _streamHandle, byteCount); + _engine->readData(_streamHandle, byteCount); } - (void)sendTrailers:(EnvoyHeaders *)trailers { - send_trailers(_engineHandle, _streamHandle, toNativeHeaders(trailers)); + _engine->sendTrailers(_streamHandle, toNativeHeaders(trailers)); } - (int)cancel { - return reset_stream(_engineHandle, _streamHandle); + _engine->cancelStream(_streamHandle); + return ENVOY_SUCCESS; } - (void)cleanUp { diff --git a/mobile/library/objective-c/EnvoyLogger.h b/mobile/library/objective-c/EnvoyLogger.h index 971cae92be328..35db541e6737a 100644 --- a/mobile/library/objective-c/EnvoyLogger.h +++ b/mobile/library/objective-c/EnvoyLogger.h @@ -7,12 +7,12 @@ NS_ASSUME_NONNULL_BEGIN // Logging interface. @interface EnvoyLogger : NSObject -@property (nonatomic, copy) void (^log)(NSString *); +@property (nonatomic, copy) void (^log)(NSInteger, NSString *); /** Create a new instance of the logger. */ -- (instancetype)initWithLogClosure:(void (^)(NSString *))log; +- (instancetype)initWithLogClosure:(void (^)(NSInteger, NSString *))log; @end diff --git a/mobile/library/objective-c/EnvoyLogger.m b/mobile/library/objective-c/EnvoyLogger.m index d681cbdd64eb9..20abf6bb8c314 100644 --- a/mobile/library/objective-c/EnvoyLogger.m +++ b/mobile/library/objective-c/EnvoyLogger.m @@ -2,7 +2,7 @@ @implementation EnvoyLogger -- (instancetype)initWithLogClosure:(void (^)(NSString *))log { +- (instancetype)initWithLogClosure:(void (^)(NSInteger, NSString *))log { self = [super init]; if (!self) { return nil; diff --git a/mobile/library/objective-c/EnvoyNetworkMonitor.m b/mobile/library/objective-c/EnvoyNetworkMonitor.mm similarity index 93% rename from mobile/library/objective-c/EnvoyNetworkMonitor.m rename to mobile/library/objective-c/EnvoyNetworkMonitor.mm index d3f3cbfaf99c9..fc41e5ba43e7c 100644 --- a/mobile/library/objective-c/EnvoyNetworkMonitor.m +++ b/mobile/library/objective-c/EnvoyNetworkMonitor.mm @@ -1,13 +1,13 @@ #import "library/objective-c/EnvoyEngine.h" -#import "library/common/main_interface.h" +#import "library/common/internal_engine.h" #import #import #import @implementation EnvoyNetworkMonitor { - envoy_engine_t _engineHandle; + Envoy::InternalEngine *_engine; nw_path_monitor_t _path_monitor; SCNetworkReachabilityRef _reachability_ref; } @@ -18,7 +18,7 @@ - (instancetype)initWithEngine:(envoy_engine_t)engineHandle { return nil; } - _engineHandle = engineHandle; + _engine = reinterpret_cast(engineHandle); return self; } @@ -43,7 +43,7 @@ - (void)startPathMonitor { nw_path_monitor_set_queue(_path_monitor, queue); __block envoy_network_t previousNetworkType = (envoy_network_t)-1; - envoy_engine_t engineHandle = _engineHandle; + Envoy::InternalEngine *engine = _engine; nw_path_monitor_set_update_handler(_path_monitor, ^(nw_path_t _Nonnull path) { BOOL isSatisfied = nw_path_get_status(path) == nw_path_status_satisfied; if (!isSatisfied) { @@ -66,7 +66,7 @@ - (void)startPathMonitor { if (network != previousNetworkType) { NSLog(@"[Envoy] setting preferred network to %d", network); - set_preferred_network(engineHandle, network); + engine->setPreferredNetwork(network); previousNetworkType = network; } @@ -135,7 +135,7 @@ static void _reachability_callback(SCNetworkReachabilityRef target, NSLog(@"[Envoy] setting preferred network to %@", isUsingWWAN ? @"WWAN" : @"WLAN"); EnvoyNetworkMonitor *monitor = (__bridge EnvoyNetworkMonitor *)info; - set_preferred_network(monitor->_engineHandle, isUsingWWAN ? ENVOY_NET_WWAN : ENVOY_NET_WLAN); + monitor->_engine->setPreferredNetwork(isUsingWWAN ? ENVOY_NET_WWAN : ENVOY_NET_WLAN); } @end diff --git a/mobile/library/swift/EngineBuilder.swift b/mobile/library/swift/EngineBuilder.swift index 130fda3145630..2969e21bc3ea3 100644 --- a/mobile/library/swift/EngineBuilder.swift +++ b/mobile/library/swift/EngineBuilder.swift @@ -166,7 +166,7 @@ open class EngineBuilder: NSObject { private var appVersion: String = "unspecified" private var appId: String = "unspecified" private var onEngineRunning: (() -> Void)? - private var logger: ((String) -> Void)? + private var logger: ((LogLevel, String) -> Void)? private var eventTracker: (([String: String]) -> Void)? private(set) var monitoringMode: NetworkMonitoringMode = .pathMonitor private var nativeFilterChain: [EnvoyNativeFilterConfig] = [] @@ -573,7 +573,7 @@ open class EngineBuilder: NSObject { /// /// - returns: This builder. @discardableResult - public func setLogger(closure: @escaping (String) -> Void) -> Self { + public func setLogger(closure: @escaping (LogLevel, String) -> Void) -> Self { self.logger = closure return self } @@ -688,7 +688,14 @@ open class EngineBuilder: NSObject { /// /// - returns: The built `Engine`. public func build() -> Engine { - let engine = self.engineType.init(runningCallback: self.onEngineRunning, logger: self.logger, + let engine = self.engineType.init(runningCallback: self.onEngineRunning, + logger: { level, message in + if let log = self.logger { + if let lvl = LogLevel(rawValue: level) { + log(lvl, message) + } + } + }, eventTracker: self.eventTracker, networkMonitoringMode: Int32(self.monitoringMode.rawValue)) let config = self.makeConfig() diff --git a/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.cc b/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.cc index 3f72d4764ac93..4b5f306a51397 100644 --- a/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.cc +++ b/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.cc @@ -2,7 +2,7 @@ #include "source/server/options_impl_base.h" -#include "library/common/engine.h" +#include "library/common/internal_engine.h" namespace Envoy { namespace CxxSwift { @@ -12,7 +12,7 @@ void run(BootstrapPtr bootstrap_ptr, Platform::LogLevel log_level, envoy_engine_ options->setConfigProto(bootstrapFromPtr(bootstrap_ptr)); options->setLogLevel(static_cast(log_level)); options->setConcurrency(1); - reinterpret_cast(engine_handle)->run(std::move(options)); + reinterpret_cast(engine_handle)->run(std::move(options)); } } // namespace CxxSwift diff --git a/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.h b/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.h index 027f75282a2fd..04a63aaa46550 100644 --- a/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.h +++ b/mobile/library/swift/EnvoyCxxSwiftInterop/cxx_swift_interop.h @@ -5,7 +5,6 @@ #include "library/cc/engine_builder.h" #include "library/common/data/utility.h" #include "library/common/extensions/filters/http/platform_bridge/c_types.h" -#include "library/common/main_interface.h" #include "library/common/stats/utility.h" // This file exists in order to expose headers for Envoy's C++ libraries diff --git a/mobile/library/swift/mocks/MockEnvoyEngine.swift b/mobile/library/swift/mocks/MockEnvoyEngine.swift index 43c81d6744ce6..057699ef05a0a 100644 --- a/mobile/library/swift/mocks/MockEnvoyEngine.swift +++ b/mobile/library/swift/mocks/MockEnvoyEngine.swift @@ -3,7 +3,8 @@ import Foundation /// Mock implementation of `EnvoyEngine`. Used internally for testing the bridging layer & mocking. final class MockEnvoyEngine: NSObject { - init(runningCallback onEngineRunning: (() -> Void)? = nil, logger: ((String) -> Void)? = nil, + init(runningCallback onEngineRunning: (() -> Void)? = nil, + logger: ((Int, String) -> Void)? = nil, eventTracker: (([String: String]) -> Void)? = nil, networkMonitoringMode: Int32 = 0) {} /// Closure called when `run(withConfig:)` is called. diff --git a/mobile/test/cc/integration/send_headers_test.cc b/mobile/test/cc/integration/send_headers_test.cc index c55b1126c2b53..de3c540a497a9 100644 --- a/mobile/test/cc/integration/send_headers_test.cc +++ b/mobile/test/cc/integration/send_headers_test.cc @@ -38,7 +38,10 @@ TEST(SendHeadersTest, CanSendHeaders) { status.status_code = headers->httpStatus(); status.end_stream = end_stream; }) - .setOnData([&](envoy_data, bool end_stream) { status.end_stream = end_stream; }) + .setOnData([&](envoy_data data, bool end_stream) { + status.end_stream = end_stream; + data.release(data.context); + }) .setOnComplete( [&](envoy_stream_intel, envoy_final_stream_intel) { stream_complete.Notify(); }) .setOnError([&](Platform::EnvoyErrorSharedPtr, envoy_stream_intel, diff --git a/mobile/test/cc/unit/envoy_config_test.cc b/mobile/test/cc/unit/envoy_config_test.cc index 414cf2b0af79d..d08e684d696b2 100644 --- a/mobile/test/cc/unit/envoy_config_test.cc +++ b/mobile/test/cc/unit/envoy_config_test.cc @@ -442,7 +442,7 @@ TEST(TestConfig, DISABLED_StringAccessors) { std::string data_string = "envoy string"; auto accessor = std::make_shared(data_string); engine_builder.addStringAccessor(name, accessor); - EngineSharedPtr engine = engine_builder.build(); + Platform::EngineSharedPtr engine = engine_builder.build(); auto c_accessor = static_cast(Envoy::Api::External::retrieveApi(name)); ASSERT_TRUE(c_accessor != nullptr); EXPECT_EQ(0, accessor->count()); diff --git a/mobile/test/common/BUILD b/mobile/test/common/BUILD index 2751206ca5ba2..cc3f3f7a2009d 100644 --- a/mobile/test/common/BUILD +++ b/mobile/test/common/BUILD @@ -17,15 +17,15 @@ envoy_cc_test( ) envoy_cc_test( - name = "engine_test", + name = "internal_engine_test", srcs = envoy_select_enable_yaml( - ["engine_test.cc"], + ["internal_engine_test.cc"], "@envoy", ), repository = "@envoy", deps = [ "//library/cc:engine_builder_lib", - "//library/common:envoy_main_interface_lib_no_stamp", + "//library/common:internal_engine_lib_no_stamp", "//library/common/types:c_types_lib", "@envoy//test/common/http:common_lib", ], @@ -39,7 +39,7 @@ envoy_cc_test( ), repository = "@envoy", deps = [ - "//library/common:envoy_main_interface_lib_no_stamp", + "//library/common:internal_engine_lib_no_stamp", "//library/common/data:utility_lib", "//library/common/http:header_utility_lib", "//library/common/types:c_types_lib", diff --git a/mobile/test/common/common/BUILD b/mobile/test/common/common/BUILD index 55f2dcb7f3ec1..51c7cac5d5b98 100644 --- a/mobile/test/common/common/BUILD +++ b/mobile/test/common/common/BUILD @@ -5,12 +5,12 @@ licenses(["notice"]) # Apache 2 envoy_mobile_package() envoy_cc_test( - name = "lambda_logger_delegate_test", - srcs = ["lambda_logger_delegate_test.cc"], + name = "logger_delegate_test", + srcs = ["logger_delegate_test.cc"], repository = "@envoy", deps = [ "//library/common/api:external_api_lib", - "//library/common/common:lambda_logger_delegate_lib", + "//library/common/common:logger_delegate_lib", "//library/common/data:utility_lib", "//library/common/types:c_types_lib", ], diff --git a/mobile/test/common/common/lambda_logger_delegate_test.cc b/mobile/test/common/common/lambda_logger_delegate_test.cc deleted file mode 100644 index c2bcc22e41a5a..0000000000000 --- a/mobile/test/common/common/lambda_logger_delegate_test.cc +++ /dev/null @@ -1,89 +0,0 @@ -#include "gmock/gmock.h" -#include "gtest/gtest.h" -#include "library/common/api/external.h" -#include "library/common/common/lambda_logger_delegate.h" -#include "library/common/data/utility.h" - -using testing::_; -using testing::HasSubstr; -using testing::Not; - -namespace Envoy { -namespace Logger { - -class LambdaDelegateTest : public testing::Test { -public: - static envoy_event_tracker tracker; - - static void SetUpTestSuite() { - Api::External::registerApi(envoy_event_tracker_api_name, &tracker); - } -}; - -envoy_event_tracker LambdaDelegateTest::tracker{}; - -TEST_F(LambdaDelegateTest, LogCb) { - std::string expected_msg = "Hello LambdaDelegate"; - std::string actual_msg; - - LambdaDelegate delegate({[](envoy_data data, const void* context) -> void { - auto* actual_msg = - static_cast(const_cast(context)); - *actual_msg = Data::Utility::copyToString(data); - release_envoy_data(data); - }, - [](const void*) -> void {}, &actual_msg}, - Registry::getSink()); - - ENVOY_LOG_MISC(error, expected_msg); - EXPECT_THAT(actual_msg, HasSubstr(expected_msg)); -} - -TEST_F(LambdaDelegateTest, LogCbWithLevels) { - std::string unexpected_msg = "Hello NoLambdaDelegate"; - std::string expected_msg = "Hello LambdaDelegate"; - std::string actual_msg; - - LambdaDelegate delegate({[](envoy_data data, const void* context) -> void { - auto* actual_msg = - static_cast(const_cast(context)); - *actual_msg = Data::Utility::copyToString(data); - release_envoy_data(data); - }, - [](const void*) -> void {}, &actual_msg}, - Registry::getSink()); - - // Set the log to critical. The message should not be logged. - Context::changeAllLogLevels(spdlog::level::critical); - ENVOY_LOG_MISC(error, unexpected_msg); - EXPECT_THAT(actual_msg, Not(HasSubstr(unexpected_msg))); - - // Change to error. The message should be logged. - Context::changeAllLogLevels(spdlog::level::err); - ENVOY_LOG_MISC(error, expected_msg); - EXPECT_THAT(actual_msg, HasSubstr(expected_msg)); - - // Change back to critical and test one more time. - Context::changeAllLogLevels(spdlog::level::critical); - ENVOY_LOG_MISC(error, expected_msg); - EXPECT_THAT(actual_msg, Not(HasSubstr(unexpected_msg))); -} - -TEST_F(LambdaDelegateTest, ReleaseCb) { - bool released = false; - - { - LambdaDelegate({[](envoy_data data, const void*) -> void { release_envoy_data(data); }, - [](const void* context) -> void { - bool* released = static_cast(const_cast(context)); - *released = true; - }, - &released}, - Registry::getSink()); - } - - EXPECT_TRUE(released); -} - -} // namespace Logger -} // namespace Envoy diff --git a/mobile/test/common/common/logger_delegate_test.cc b/mobile/test/common/common/logger_delegate_test.cc new file mode 100644 index 0000000000000..a8e3997ab0c28 --- /dev/null +++ b/mobile/test/common/common/logger_delegate_test.cc @@ -0,0 +1,157 @@ +#include "gmock/gmock.h" +#include "gtest/gtest.h" +#include "library/common/api/external.h" +#include "library/common/common/logger_delegate.h" +#include "library/common/data/utility.h" + +using testing::_; +using testing::HasSubstr; +using testing::Not; + +namespace Envoy { +namespace Logger { + +class LambdaDelegateTest : public testing::Test { +public: + static envoy_event_tracker tracker; + + static void SetUpTestSuite() { + Api::External::registerApi(std::string(envoy_event_tracker_api_name), &tracker); + } +}; + +envoy_event_tracker LambdaDelegateTest::tracker{}; + +TEST_F(LambdaDelegateTest, LogCb) { + std::string expected_msg = "Hello LambdaDelegate"; + std::string actual_msg; + + LambdaDelegate delegate({[](envoy_log_level, envoy_data data, const void* context) -> void { + auto* actual_msg = + static_cast(const_cast(context)); + *actual_msg = Data::Utility::copyToString(data); + release_envoy_data(data); + }, + [](const void*) -> void {}, &actual_msg}, + Registry::getSink()); + + ENVOY_LOG_MISC(error, expected_msg); + EXPECT_THAT(actual_msg, HasSubstr(expected_msg)); +} + +TEST_F(LambdaDelegateTest, LogCbWithLevels) { + std::string unexpected_msg = "Hello NoLambdaDelegate"; + std::string expected_msg = "Hello LambdaDelegate"; + std::string actual_msg; + + LambdaDelegate delegate({[](envoy_log_level, envoy_data data, const void* context) -> void { + auto* actual_msg = + static_cast(const_cast(context)); + *actual_msg = Data::Utility::copyToString(data); + release_envoy_data(data); + }, + [](const void*) -> void {}, &actual_msg}, + Registry::getSink()); + + // Set the log to critical. The message should not be logged. + Context::changeAllLogLevels(spdlog::level::critical); + ENVOY_LOG_MISC(error, unexpected_msg); + EXPECT_THAT(actual_msg, Not(HasSubstr(unexpected_msg))); + + // Change to error. The message should be logged. + Context::changeAllLogLevels(spdlog::level::err); + ENVOY_LOG_MISC(error, expected_msg); + EXPECT_THAT(actual_msg, HasSubstr(expected_msg)); + + // Change back to critical and test one more time. + Context::changeAllLogLevels(spdlog::level::critical); + ENVOY_LOG_MISC(error, expected_msg); + EXPECT_THAT(actual_msg, Not(HasSubstr(unexpected_msg))); +} + +TEST_F(LambdaDelegateTest, ReleaseCb) { + bool released = false; + + { + LambdaDelegate( + {[](envoy_log_level, envoy_data data, const void*) -> void { release_envoy_data(data); }, + [](const void* context) -> void { + bool* released = static_cast(const_cast(context)); + *released = true; + }, + &released}, + Registry::getSink()); + } + + EXPECT_TRUE(released); +} + +class LambdaDelegateWithLevelTest + : public testing::TestWithParam< + std::tuple> {}; + +INSTANTIATE_TEST_SUITE_P( + LogLevel, LambdaDelegateWithLevelTest, + testing::Values(std::make_tuple<>(envoy_log_level::ENVOY_LOG_LEVEL_TRACE, Logger::Levels::trace, + spdlog::level::trace), + std::make_tuple<>(envoy_log_level::ENVOY_LOG_LEVEL_DEBUG, Logger::Levels::debug, + spdlog::level::debug), + std::make_tuple<>(envoy_log_level::ENVOY_LOG_LEVEL_INFO, Logger::Levels::info, + spdlog::level::info), + std::make_tuple<>(envoy_log_level::ENVOY_LOG_LEVEL_WARN, Logger::Levels::warn, + spdlog::level::warn), + std::make_tuple<>(envoy_log_level::ENVOY_LOG_LEVEL_ERROR, Logger::Levels::error, + spdlog::level::err), + std::make_tuple<>(envoy_log_level::ENVOY_LOG_LEVEL_CRITICAL, + Logger::Levels::critical, spdlog::level::critical))); + +TEST_P(LambdaDelegateWithLevelTest, Log) { + std::string expected_msg = "Hello LambdaDelegate"; + struct Actual { + envoy_log_level level; + std::string msg; + }; + Actual actual; + + LambdaDelegate delegate({[](envoy_log_level level, envoy_data data, const void* context) -> void { + auto* actual = static_cast(const_cast(context)); + actual->msg = Data::Utility::copyToString(data); + actual->level = level; + release_envoy_data(data); + }, + [](const void*) -> void {}, &actual}, + Registry::getSink()); + + envoy_log_level c_envoy_log_level = std::get<0>(GetParam()); + Logger::Levels envoy_log_level = std::get<1>(GetParam()); + spdlog::level::level_enum spd_log_level = std::get<2>(GetParam()); + + Context::changeAllLogLevels(spd_log_level); + switch (envoy_log_level) { + case Logger::Levels::trace: + ENVOY_LOG_MISC(trace, expected_msg); + break; + case Logger::Levels::debug: + ENVOY_LOG_MISC(debug, expected_msg); + break; + case Logger::Levels::info: + ENVOY_LOG_MISC(info, expected_msg); + break; + case Logger::Levels::warn: + ENVOY_LOG_MISC(warn, expected_msg); + break; + case Logger::Levels::error: + ENVOY_LOG_MISC(error, expected_msg); + break; + case Logger::Levels::critical: + ENVOY_LOG_MISC(critical, expected_msg); + break; + default: + break; + } + EXPECT_THAT(actual.msg, HasSubstr(expected_msg)); + EXPECT_LE(actual.level, c_envoy_log_level); +} + +} // namespace Logger +} // namespace Envoy diff --git a/mobile/test/common/extensions/filters/http/platform_bridge/platform_bridge_filter_integration_test.cc b/mobile/test/common/extensions/filters/http/platform_bridge/platform_bridge_filter_integration_test.cc index 5f8af586320e0..245f40e41bc04 100644 --- a/mobile/test/common/extensions/filters/http/platform_bridge/platform_bridge_filter_integration_test.cc +++ b/mobile/test/common/extensions/filters/http/platform_bridge/platform_bridge_filter_integration_test.cc @@ -33,8 +33,8 @@ class PlatformBridgeIntegrationTest : public testing::TestWithParam(context_, config); filter_ = std::make_shared(config_, dispatcher_); diff --git a/mobile/test/common/http/client_test.cc b/mobile/test/common/http/client_test.cc index 742fec0456d27..beaf5f3ef9361 100644 --- a/mobile/test/common/http/client_test.cc +++ b/mobile/test/common/http/client_test.cc @@ -22,6 +22,7 @@ #include "library/common/types/c_types.h" using testing::_; +using testing::AnyNumber; using testing::NiceMock; using testing::Return; using testing::ReturnPointee; @@ -127,6 +128,10 @@ class ClientTest : public testing::TestWithParam { helper_handle_ = test::SystemHelperPeer::replaceSystemHelper(); EXPECT_CALL(helper_handle_->mock_helper(), isCleartextPermitted(_)) .WillRepeatedly(Return(true)); + EXPECT_CALL(dispatcher_, post_(_)).Times(AnyNumber()).WillRepeatedly([](Event::PostCb cb) { + cb(); + return ENVOY_SUCCESS; + }); } envoy_headers defaultRequestHeaders() { diff --git a/mobile/test/common/http/filters/test_read/filter.cc b/mobile/test/common/http/filters/test_read/filter.cc index cec0323b2685a..27bfeeec3474c 100644 --- a/mobile/test/common/http/filters/test_read/filter.cc +++ b/mobile/test/common/http/filters/test_read/filter.cc @@ -34,7 +34,7 @@ Http::FilterHeadersStatus TestReadFilter::decodeHeaders(Http::RequestHeaderMap& return Http::FilterHeadersStatus::Continue; } -StreamInfo::ResponseFlag TestReadFilter::mapErrorToResponseFlag(uint64_t errorCode) { +StreamInfo::CoreResponseFlag TestReadFilter::mapErrorToResponseFlag(uint64_t errorCode) { switch (errorCode) { case 0x4000000: return StreamInfo::DnsResolutionFailed; diff --git a/mobile/test/common/http/filters/test_read/filter.h b/mobile/test/common/http/filters/test_read/filter.h index c59fdc4203ece..f11786a60bdd8 100644 --- a/mobile/test/common/http/filters/test_read/filter.h +++ b/mobile/test/common/http/filters/test_read/filter.h @@ -27,7 +27,7 @@ class TestReadFilter final : public Http::PassThroughFilter, /* A mapping of the envoymobile errors we care about for testing * From https://github.com/envoyproxy/envoy/blob/main/envoy/stream_info/stream_info.h */ - StreamInfo::ResponseFlag mapErrorToResponseFlag(uint64_t errorCode); + StreamInfo::CoreResponseFlag mapErrorToResponseFlag(uint64_t errorCode); }; } // namespace TestRead diff --git a/mobile/test/common/integration/BUILD b/mobile/test/common/integration/BUILD index e3b7ec92565e1..3b65dd43cbad9 100644 --- a/mobile/test/common/integration/BUILD +++ b/mobile/test/common/integration/BUILD @@ -172,6 +172,7 @@ envoy_cc_test_library( ], repository = "@envoy", deps = [ + "@envoy//source/common/listener_manager:listener_manager_lib", "@envoy//source/exe:process_wide_lib", "@envoy//test/integration:autonomous_upstream_lib", "@envoy//test/integration:utility_lib", diff --git a/mobile/test/common/integration/base_client_integration_test.cc b/mobile/test/common/integration/base_client_integration_test.cc index 9d5fbc34fb69d..aa514394047f8 100644 --- a/mobile/test/common/integration/base_client_integration_test.cc +++ b/mobile/test/common/integration/base_client_integration_test.cc @@ -9,8 +9,8 @@ #include "gtest/gtest.h" #include "library/cc/bridge_utility.h" #include "library/cc/log_level.h" -#include "library/common/engine.h" #include "library/common/http/header_utility.h" +#include "library/common/internal_engine.h" #include "spdlog/spdlog.h" namespace Envoy { @@ -221,7 +221,7 @@ uint64_t BaseClientIntegrationTest::getCounterValue(const std::string& name) { uint64_t counter_value = 0UL; uint64_t* counter_value_ptr = &counter_value; absl::Notification counter_value_set; - auto engine = reinterpret_cast(rawEngine()); + auto engine = reinterpret_cast(rawEngine()); engine->dispatcher().post([&] { Stats::CounterSharedPtr counter = TestUtility::findCounter(engine->getStatsStore(), name); if (counter != nullptr) { @@ -252,7 +252,7 @@ uint64_t BaseClientIntegrationTest::getGaugeValue(const std::string& name) { uint64_t gauge_value = 0UL; uint64_t* gauge_value_ptr = &gauge_value; absl::Notification gauge_value_set; - auto engine = reinterpret_cast(rawEngine()); + auto engine = reinterpret_cast(rawEngine()); engine->dispatcher().post([&] { Stats::GaugeSharedPtr gauge = TestUtility::findGauge(engine->getStatsStore(), name); if (gauge != nullptr) { diff --git a/mobile/test/common/integration/client_integration_test.cc b/mobile/test/common/integration/client_integration_test.cc index 234ca72756bc6..a3934d66eb3b4 100644 --- a/mobile/test/common/integration/client_integration_test.cc +++ b/mobile/test/common/integration/client_integration_test.cc @@ -14,7 +14,7 @@ #include "extension_registry.h" #include "library/common/data/utility.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" #include "library/common/network/proxy_settings.h" #include "library/common/types/c_types.h" @@ -914,6 +914,8 @@ TEST_P(ClientIntegrationTest, ResetWithBidiTraffic) { TEST_P(ClientIntegrationTest, ResetWithBidiTrafficExplicitData) { explicit_flow_control_ = true; autonomous_upstream_ = false; + // TODO(32024) remove trace logging. + builder_.addLogLevel(Platform::LogLevel::trace); initialize(); ConditionalInitializer headers_callback; @@ -937,10 +939,8 @@ TEST_P(ClientIntegrationTest, ResetWithBidiTrafficExplicitData) { upstream_request_->encodeHeaders(Http::TestResponseHeaderMapImpl{{":status", "200"}}, false); upstream_request_->encodeData(1, false); upstream_request_->encodeResetStream(); - if (getCodecType() != Http::CodecType::HTTP3) { - // Make sure the headers are sent up. - headers_callback.waitReady(); - } + // Make sure the headers are sent up. + headers_callback.waitReady(); // Encoding data should not be problematic. Buffer::OwnedImpl request_data = Buffer::OwnedImpl("request body"); @@ -954,12 +954,12 @@ TEST_P(ClientIntegrationTest, Proxying) { if (getCodecType() != Http::CodecType::HTTP1) { return; } - builder_.addLogLevel(Platform::LogLevel::trace); initialize(); - - set_proxy_settings(rawEngine(), fake_upstreams_[0]->localAddress()->asString().c_str(), - fake_upstreams_[0]->localAddress()->ip()->port()); - + { + absl::MutexLock l(&engine_lock_); + engine_->engine()->setProxySettings(fake_upstreams_[0]->localAddress()->asString().c_str(), + fake_upstreams_[0]->localAddress()->ip()->port()); + } // The initial request will do the DNS lookup. stream_->sendHeaders(envoyToMobileHeaders(default_request_headers_), true); terminal_callback_.waitReady(); diff --git a/mobile/test/common/integration/test_server.cc b/mobile/test/common/integration/test_server.cc index f771ba80c6ffd..4fda9549737b8 100644 --- a/mobile/test/common/integration/test_server.cc +++ b/mobile/test/common/integration/test_server.cc @@ -1,10 +1,19 @@ #include "test_server.h" #include "source/common/common/random_generator.h" +#include "source/common/listener_manager/connection_handler_impl.h" +#include "source/common/listener_manager/listener_manager_impl.h" +#include "source/common/quic/quic_server_transport_socket_factory.h" +#include "source/common/quic/server_codec_impl.h" #include "source/common/stats/allocator_impl.h" #include "source/common/stats/thread_local_store.h" #include "source/common/thread_local/thread_local_impl.h" +#include "source/extensions/quic/connection_id_generator/envoy_deterministic_connection_id_generator_config.h" +#include "source/extensions/quic/crypto_stream/envoy_quic_crypto_server_stream.h" +#include "source/extensions/quic/proof_source/envoy_quic_proof_source_factory_impl.h" +#include "source/extensions/transport_sockets/raw_buffer/config.h" #include "source/extensions/transport_sockets/tls/context_config_impl.h" +#include "source/extensions/udp_packet_writer/default/config.h" #include "source/server/hot_restart_nop_impl.h" #include "source/server/instance_impl.h" @@ -81,6 +90,16 @@ void TestServer::startTestServer(TestServerType test_server_type) { switch (test_server_type) { case TestServerType::HTTP3: + // Make sure if extensions aren't statically linked QUIC will work. + Quic::forceRegisterQuicServerTransportSocketConfigFactory(); + Network::forceRegisterUdpDefaultWriterFactoryFactory(); + Quic::forceRegisterQuicHttpServerConnectionFactoryImpl(); + Quic::forceRegisterEnvoyQuicCryptoServerStreamFactoryImpl(); + Quic::forceRegisterQuicServerTransportSocketConfigFactory(); + Quic::forceRegisterEnvoyQuicProofSourceFactoryImpl(); + Quic::forceRegisterEnvoyDeterministicConnectionIdGeneratorConfigFactory(); + + // envoy.quic.crypto_stream.server.quiche upstream_config_.upstream_protocol_ = Http::CodecType::HTTP3; upstream_config_.udp_fake_upstream_ = FakeUpstreamConfig::UdpConfig(); factory = createQuicUpstreamTlsContext(factory_context_); @@ -94,6 +113,10 @@ void TestServer::startTestServer(TestServerType test_server_type) { factory = Network::Test::createRawBufferDownstreamSocketFactory(); break; case TestServerType::HTTP_PROXY: { + Server::forceRegisterDefaultListenerManagerFactoryImpl(); + Extensions::TransportSockets::RawBuffer::forceRegisterDownstreamRawBufferSocketFactory(); + Server::forceRegisterConnectionHandlerFactoryImpl(); + std::string config_path = TestEnvironment::writeStringToFileForTest("config.yaml", http_proxy_config); test_server_ = IntegrationTestServer::create(config_path, Network::Address::IpVersion::v4, @@ -103,6 +126,9 @@ void TestServer::startTestServer(TestServerType test_server_type) { return; } case TestServerType::HTTPS_PROXY: { + Server::forceRegisterDefaultListenerManagerFactoryImpl(); + Extensions::TransportSockets::RawBuffer::forceRegisterDownstreamRawBufferSocketFactory(); + Server::forceRegisterConnectionHandlerFactoryImpl(); std::string config_path = TestEnvironment::writeStringToFileForTest("config.yaml", https_proxy_config); test_server_ = IntegrationTestServer::create(config_path, Network::Address::IpVersion::v4, diff --git a/mobile/test/common/engine_test.cc b/mobile/test/common/internal_engine_test.cc similarity index 84% rename from mobile/test/common/engine_test.cc rename to mobile/test/common/internal_engine_test.cc index db11acacd8ea9..57586f328e15d 100644 --- a/mobile/test/common/engine_test.cc +++ b/mobile/test/common/internal_engine_test.cc @@ -1,8 +1,7 @@ #include "absl/synchronization/notification.h" #include "gtest/gtest.h" #include "library/cc/engine_builder.h" -#include "library/common/engine.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" namespace Envoy { @@ -11,10 +10,10 @@ namespace Envoy { // between the main thread and the engine thread both writing to the // Envoy::Logger::current_log_context global. struct TestEngine { - std::unique_ptr engine_; + std::unique_ptr engine_; envoy_engine_t handle() { return reinterpret_cast(engine_.get()); } TestEngine(envoy_engine_callbacks callbacks, const std::string& level) { - engine_.reset(new Envoy::Engine(callbacks, {}, {})); + engine_.reset(new Envoy::InternalEngine(callbacks, {}, {})); Platform::EngineBuilder builder; auto bootstrap = builder.generateBootstrap(); std::string yaml = Envoy::MessageUtil::getYamlStringFromMessage(*bootstrap); @@ -22,8 +21,13 @@ struct TestEngine { } envoy_status_t terminate() { return engine_->terminate(); } + bool isTerminated() const { return engine_->isTerminated(); } - ~TestEngine() { engine_->terminate(); } + ~TestEngine() { + if (!engine_->isTerminated()) { + engine_->terminate(); + } + } }; class EngineTest : public testing::Test { @@ -52,13 +56,13 @@ TEST_F(EngineTest, EarlyExit) { &test_context /*context*/}; engine_ = std::make_unique(callbacks, level); - envoy_engine_t handle = engine_->handle(); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(10))); ASSERT_EQ(engine_->terminate(), ENVOY_SUCCESS); + ASSERT_TRUE(engine_->isTerminated()); ASSERT_TRUE(test_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(10))); - start_stream(handle, 0, {}, false); + engine_->engine_->startStream(0, {}, false); engine_.reset(); } @@ -75,19 +79,18 @@ TEST_F(EngineTest, AccessEngineAfterInitialization) { [](void*) -> void {} /*on_exit*/, &test_context /*context*/}; engine_ = std::make_unique(callbacks, level); - envoy_engine_t handle = engine_->handle(); + engine_->handle(); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(10))); absl::Notification getClusterManagerInvoked; - envoy_data stats_data; // Running engine functions should work because the engine is running - EXPECT_EQ(ENVOY_SUCCESS, dump_stats(handle, &stats_data)); - release_envoy_data(stats_data); + EXPECT_EQ("runtime.load_success: 1\n", engine_->engine_->dumpStats()); engine_->terminate(); + ASSERT_TRUE(engine_->isTerminated()); // Now that the engine has been shut down, we no longer expect scheduling to work. - EXPECT_EQ(ENVOY_FAILURE, dump_stats(handle, &stats_data)); + EXPECT_EQ("", engine_->engine_->dumpStats()); engine_.reset(); } diff --git a/mobile/test/common/main_interface_test.cc b/mobile/test/common/main_interface_test.cc index 286be2e896ad8..62d002cd341d7 100644 --- a/mobile/test/common/main_interface_test.cc +++ b/mobile/test/common/main_interface_test.cc @@ -9,9 +9,8 @@ #include "library/common/api/external.h" #include "library/common/bridge/utility.h" #include "library/common/data/utility.h" -#include "library/common/engine.h" #include "library/common/http/header_utility.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" using testing::_; using testing::HasSubstr; @@ -160,8 +159,7 @@ TEST_F(MainInterfaceTest, BasicStream) { exit->on_exit.Notify(); } /*on_exit*/, &engine_cbs_context /*context*/}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); - envoy_engine_t engine_handle = reinterpret_cast(engine.get()); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, {}, {})); engine->run(BUFFERED_TEST_CONFIG.c_str(), level.c_str()); ASSERT_TRUE( @@ -197,13 +195,13 @@ TEST_F(MainInterfaceTest, BasicStream) { Http::TestRequestTrailerMapImpl trailers; envoy_headers c_trailers = Http::Utility::toBridgeHeaders(trailers); - envoy_stream_t stream = init_stream(engine_handle); + envoy_stream_t stream = engine->initStream(); - start_stream(engine_handle, stream, stream_cbs, false); + engine->startStream(stream, stream_cbs, false); - send_headers(engine_handle, stream, c_headers, false); - send_data(engine_handle, stream, c_data, false); - send_trailers(engine_handle, stream, c_trailers); + engine->sendHeaders(stream, c_headers, false); + engine->sendData(stream, c_data, false); + engine->sendTrailers(stream, c_trailers); ASSERT_TRUE(on_complete_notification.WaitForNotificationWithTimeout(absl::Seconds(10))); @@ -212,47 +210,6 @@ TEST_F(MainInterfaceTest, BasicStream) { ASSERT_TRUE(engine_cbs_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(10))); } -TEST_F(MainInterfaceTest, SendMetadata) { - engine_test_context engine_cbs_context{}; - envoy_engine_callbacks engine_cbs{[](void* context) -> void { - auto* engine_running = - static_cast(context); - engine_running->on_engine_running.Notify(); - } /*on_engine_running*/, - [](void* context) -> void { - auto* exit = static_cast(context); - exit->on_exit.Notify(); - } /*on_exit*/, - &engine_cbs_context /*context*/}; - - // There is nothing functional about the config used to run the engine, as the created stream is - // only used for send_metadata. - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); - envoy_engine_t engine_handle = reinterpret_cast(engine.get()); - engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); - - ASSERT_TRUE( - engine_cbs_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(10))); - - envoy_http_callbacks stream_cbs{ - nullptr /* on_headers */, nullptr /* on_data */, - nullptr /* on_metadata */, nullptr /* on_trailers */, - nullptr /* on_error */, nullptr /* on_complete */, - nullptr /* on_cancel */, nullptr /* on_send_window_available */, - nullptr /* context */, - }; - - envoy_stream_t stream = init_stream(engine_handle); - - start_stream(engine_handle, stream, stream_cbs, false); - - EXPECT_EQ(ENVOY_FAILURE, send_metadata(engine_handle, stream, {})); - - engine->terminate(); - - ASSERT_TRUE(engine_cbs_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(10))); -} - TEST_F(MainInterfaceTest, ResetStream) { engine_test_context engine_cbs_context{}; envoy_engine_callbacks engine_cbs{[](void* context) -> void { @@ -268,8 +225,7 @@ TEST_F(MainInterfaceTest, ResetStream) { // There is nothing functional about the config used to run the engine, as the created stream is // immediately reset. - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); - envoy_engine_t engine_handle = reinterpret_cast(engine.get()); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, {}, {})); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE( @@ -291,11 +247,11 @@ TEST_F(MainInterfaceTest, ResetStream) { nullptr /* on_send_window_available */, &on_cancel_notification /* context */}; - envoy_stream_t stream = init_stream(engine_handle); + envoy_stream_t stream = engine->initStream(); - start_stream(engine_handle, stream, stream_cbs, false); + engine->startStream(stream, stream_cbs, false); - reset_stream(engine_handle, stream); + engine->cancelStream(stream); ASSERT_TRUE(on_cancel_notification.WaitForNotificationWithTimeout(absl::Seconds(10))); @@ -304,28 +260,6 @@ TEST_F(MainInterfaceTest, ResetStream) { ASSERT_TRUE(engine_cbs_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(10))); } -TEST_F(MainInterfaceTest, UsingMainInterfaceWithoutARunningEngine) { - Http::TestRequestHeaderMapImpl headers; - HttpTestUtility::addDefaultHeaders(headers); - envoy_headers c_headers = Http::Utility::toBridgeHeaders(headers); - - Buffer::OwnedImpl request_data = Buffer::OwnedImpl("request body"); - envoy_data c_data = Data::Utility::toBridgeData(request_data); - - Http::TestRequestTrailerMapImpl trailers; - envoy_headers c_trailers = Http::Utility::toBridgeHeaders(trailers); - - EXPECT_EQ(ENVOY_FAILURE, send_headers(0, 0, c_headers, false)); - EXPECT_EQ(ENVOY_FAILURE, send_data(0, 0, c_data, false)); - EXPECT_EQ(ENVOY_FAILURE, send_trailers(0, 0, c_trailers)); - EXPECT_EQ(ENVOY_FAILURE, reset_stream(0, 0)); - - // Release memory - release_envoy_headers(c_headers); - release_envoy_data(c_data); - release_envoy_headers(c_trailers); -} - TEST_F(MainInterfaceTest, RegisterPlatformApi) { engine_test_context engine_cbs_context{}; envoy_engine_callbacks engine_cbs{[](void* context) -> void { @@ -340,24 +274,20 @@ TEST_F(MainInterfaceTest, RegisterPlatformApi) { &engine_cbs_context /*context*/}; // Using the minimal envoy mobile config that allows for running the engine. - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, {}, {})); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE( engine_cbs_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(10))); uint64_t fake_api; - EXPECT_EQ(ENVOY_SUCCESS, register_platform_api("api", &fake_api)); + Envoy::Api::External::registerApi("api", &fake_api); engine->terminate(); ASSERT_TRUE(engine_cbs_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(10))); } -TEST_F(MainInterfaceTest, PreferredNetwork) { - EXPECT_EQ(ENVOY_SUCCESS, set_preferred_network(0, ENVOY_NET_WLAN)); -} - TEST(EngineTest, RecordCounter) { engine_test_context test_context{}; envoy_engine_callbacks engine_cbs{[](void* context) -> void { @@ -370,13 +300,11 @@ TEST(EngineTest, RecordCounter) { exit->on_exit.Notify(); } /*on_exit*/, &test_context /*context*/}; - EXPECT_EQ(ENVOY_FAILURE, record_counter_inc(0, "counter", envoy_stats_notags, 1)); - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); - envoy_engine_t engine_handle = reinterpret_cast(engine.get()); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, {}, {})); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(3))); - EXPECT_EQ(ENVOY_SUCCESS, record_counter_inc(engine_handle, "counter", envoy_stats_notags, 1)); + EXPECT_EQ(ENVOY_SUCCESS, engine->recordCounterInc("counter", envoy_stats_notags, 1)); engine->terminate(); ASSERT_TRUE(test_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(3))); @@ -396,7 +324,7 @@ TEST(EngineTest, Logger) { } /*on_exit*/, &test_context /*context*/}; - envoy_logger logger{[](envoy_data data, const void* context) -> void { + envoy_logger logger{[](envoy_log_level, envoy_data data, const void* context) -> void { auto* test_context = static_cast(const_cast(context)); release_envoy_data(data); @@ -410,7 +338,7 @@ TEST(EngineTest, Logger) { test_context->on_logger_release.Notify(); } /* release */, &test_context}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, logger, {})); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, logger, {})); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(3))); @@ -436,7 +364,7 @@ TEST(EngineTest, EventTrackerRegistersDefaultAPI) { } /*on_exit*/, &test_context /*context*/}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, {}, {})); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); // A default event tracker is registered in external API registry. @@ -480,7 +408,8 @@ TEST(EngineTest, EventTrackerRegistersAPI) { } /*track*/, &test_context /*context*/}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, event_tracker)); + std::unique_ptr engine( + new Envoy::InternalEngine(engine_cbs, {}, event_tracker)); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(3))); @@ -523,7 +452,8 @@ TEST(EngineTest, EventTrackerRegistersAssertionFailureRecordAction) { } /*track*/, &test_context /*context*/}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, event_tracker)); + std::unique_ptr engine( + new Envoy::InternalEngine(engine_cbs, {}, event_tracker)); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(3))); @@ -563,7 +493,8 @@ TEST(EngineTest, EventTrackerRegistersEnvoyBugRecordAction) { } /*track*/, &test_context /*context*/}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, event_tracker)); + std::unique_ptr engine( + new Envoy::InternalEngine(engine_cbs, {}, event_tracker)); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(3))); @@ -590,12 +521,11 @@ TEST_F(MainInterfaceTest, ResetConnectivityState) { exit->on_exit.Notify(); } /*on_exit*/, &test_context /*context*/}; - std::unique_ptr engine(new Envoy::Engine(engine_cbs, {}, {})); - envoy_engine_t engine_handle = reinterpret_cast(engine.get()); + std::unique_ptr engine(new Envoy::InternalEngine(engine_cbs, {}, {})); engine->run(MINIMAL_TEST_CONFIG.c_str(), LEVEL_DEBUG.c_str()); ASSERT_TRUE(test_context.on_engine_running.WaitForNotificationWithTimeout(absl::Seconds(3))); - ASSERT_EQ(ENVOY_SUCCESS, reset_connectivity_state(engine_handle)); + ASSERT_EQ(ENVOY_SUCCESS, engine->resetConnectivityState()); engine->terminate(); ASSERT_TRUE(test_context.on_exit.WaitForNotificationWithTimeout(absl::Seconds(3))); diff --git a/mobile/test/common/mocks/common/mocks.h b/mobile/test/common/mocks/common/mocks.h index e4b2d174e25f8..b1451495aa4dc 100644 --- a/mobile/test/common/mocks/common/mocks.h +++ b/mobile/test/common/mocks/common/mocks.h @@ -29,24 +29,27 @@ class SystemHelperPeer { // Handle's `mock_helper()` accessor. static std::unique_ptr replaceSystemHelper() { return std::make_unique(); } - // RAII type for replacing the SystemHelper singleton with a the MockSystemHelper. + // RAII type for replacing the SystemHelper singleton with the MockSystemHelper. // When this object is destroyed, it resets the SystemHelper singleton back // to the previous state. class Handle { public: Handle() { - previous_ = std::make_unique(); - SystemHelper::instance_.swap(previous_); + previous_ = new test::MockSystemHelper(); + std::swap(SystemHelper::instance_, previous_); } - ~Handle() { SystemHelper::instance_ = std::move(previous_); } + ~Handle() { + delete SystemHelper::instance_; + SystemHelper::instance_ = previous_; + } test::MockSystemHelper& mock_helper() { - return *static_cast(SystemHelper::instance_.get()); + return *static_cast(SystemHelper::instance_); } private: - std::unique_ptr previous_; + SystemHelper* previous_; }; }; diff --git a/mobile/test/common/stats/BUILD b/mobile/test/common/stats/BUILD index 5a053f1a6a0f4..98a255f270817 100644 --- a/mobile/test/common/stats/BUILD +++ b/mobile/test/common/stats/BUILD @@ -9,7 +9,7 @@ envoy_cc_test( srcs = ["utility_test.cc"], repository = "@envoy", deps = [ - "//library/common:envoy_main_interface_lib_no_stamp", + "//library/common:internal_engine_lib_no_stamp", "//library/common/data:utility_lib", "//library/common/types:c_types_lib", "@envoy//test/common/stats:stat_test_utility_lib", diff --git a/mobile/test/java/integration/BUILD b/mobile/test/java/integration/BUILD index 898bcece51e5b..98e30e7bb8337 100644 --- a/mobile/test/java/integration/BUILD +++ b/mobile/test/java/integration/BUILD @@ -15,10 +15,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -38,10 +38,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -62,10 +62,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -86,10 +86,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/io/envoyproxy/envoymobile/engine/BUILD b/mobile/test/java/io/envoyproxy/envoymobile/engine/BUILD index 2b8fe20f6f5d7..b2f645fa6c548 100644 --- a/mobile/test/java/io/envoyproxy/envoymobile/engine/BUILD +++ b/mobile/test/java/io/envoyproxy/envoymobile/engine/BUILD @@ -11,10 +11,10 @@ envoy_mobile_jni_kt_test( "EnvoyConfigurationTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -52,10 +52,10 @@ envoy_mobile_android_test( "AndroidNetworkMonitorTest.java", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/io/envoyproxy/envoymobile/engine/testing/BUILD b/mobile/test/java/io/envoyproxy/envoymobile/engine/testing/BUILD index 271ef49ae3d37..6abda8991014e 100644 --- a/mobile/test/java/io/envoyproxy/envoymobile/engine/testing/BUILD +++ b/mobile/test/java/io/envoyproxy/envoymobile/engine/testing/BUILD @@ -31,10 +31,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/io/envoyproxy/envoymobile/jni/BUILD b/mobile/test/java/io/envoyproxy/envoymobile/jni/BUILD index fa34649e5f64b..c88259eb6cd7f 100644 --- a/mobile/test/java/io/envoyproxy/envoymobile/jni/BUILD +++ b/mobile/test/java/io/envoyproxy/envoymobile/jni/BUILD @@ -11,7 +11,7 @@ envoy_mobile_android_test( "JniHelperTest.java", ], native_deps = [ - "//test/common/jni:libenvoy_jni_helper_test.so", + "//test/jni:libenvoy_jni_helper_test.so", ], native_lib_name = "envoy_jni_helper_test", ) @@ -22,7 +22,7 @@ envoy_mobile_android_test( "JniUtilityTest.java", ], native_deps = [ - "//test/common/jni:libenvoy_jni_utility_test.so", + "//test/jni:libenvoy_jni_utility_test.so", ], native_lib_name = "envoy_jni_utility_test", deps = [ diff --git a/mobile/test/java/io/envoyproxy/envoymobile/utilities/BUILD b/mobile/test/java/io/envoyproxy/envoymobile/utilities/BUILD index 4173f1d837e80..de8657c4d0da3 100644 --- a/mobile/test/java/io/envoyproxy/envoymobile/utilities/BUILD +++ b/mobile/test/java/io/envoyproxy/envoymobile/utilities/BUILD @@ -11,10 +11,10 @@ envoy_mobile_android_test( "CertificateVerificationTest.java", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/org/chromium/net/BUILD b/mobile/test/java/org/chromium/net/BUILD index 3f25190ac492d..19b6d3e91d645 100644 --- a/mobile/test/java/org/chromium/net/BUILD +++ b/mobile/test/java/org/chromium/net/BUILD @@ -22,10 +22,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -52,10 +52,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -81,10 +81,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -110,10 +110,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/org/chromium/net/impl/BUILD b/mobile/test/java/org/chromium/net/impl/BUILD index 38137996f7418..be008719fc397 100644 --- a/mobile/test/java/org/chromium/net/impl/BUILD +++ b/mobile/test/java/org/chromium/net/impl/BUILD @@ -20,10 +20,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/org/chromium/net/impl/CronvoyLoggerTest.java b/mobile/test/java/org/chromium/net/impl/CronvoyLoggerTest.java index 40afcb5786354..a1c318d6ddc1f 100644 --- a/mobile/test/java/org/chromium/net/impl/CronvoyLoggerTest.java +++ b/mobile/test/java/org/chromium/net/impl/CronvoyLoggerTest.java @@ -1,8 +1,5 @@ package org.chromium.net.impl; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertTrue; -import static org.junit.Assert.fail; import static org.junit.Assert.assertEquals; import androidx.test.ext.junit.runners.AndroidJUnit4; @@ -12,12 +9,13 @@ import org.junit.runner.RunWith; import org.junit.Rule; import org.junit.Test; -import org.chromium.net.impl.CronvoyLogger; import java.io.File; import java.nio.file.Files; import java.nio.file.Paths; +import io.envoyproxy.envoymobile.engine.types.EnvoyLogger; + /** * Tests that ConvoyLogger works as expected. */ @@ -32,7 +30,7 @@ public class CronvoyLoggerTest { public void logWithLoggerUnconfigured() throws Exception { CronvoyLogger logger = new CronvoyLogger(); // Should be a no-op. - logger.log("hello"); + logger.log(EnvoyLogger.Level.INFO, "hello"); } @Test @@ -44,9 +42,8 @@ public void testBasicLogToFile() throws Exception { String filename = file.getAbsolutePath() + "foo"; // Pick a path that doesn't exist. CronvoyLogger logger = new CronvoyLogger(); logger.setNetLogToFile(filename); - logger.log("hello"); + logger.log(EnvoyLogger.Level.INFO, "hello"); logger.stopLogging(); - char[] buffer = new char[5000]; byte[] bytes = Files.readAllBytes(Paths.get(filename)); String fileContent = new String(bytes); assertEquals(fileContent, "hello"); @@ -61,9 +58,8 @@ public void testBasicLogToDisk() throws Exception { String filename = file.getAbsolutePath() + "bar/foo"; // Pick a directory that doesn't exist. CronvoyLogger logger = new CronvoyLogger(); logger.setNetLogToDisk(filename, 5000); - logger.log("hello"); + logger.log(EnvoyLogger.Level.INFO, "hello"); logger.stopLogging(); - char[] buffer = new char[5000]; byte[] bytes = Files.readAllBytes(Paths.get(filename + "/netlog.json")); String fileContent = new String(bytes); assertEquals(fileContent, "hello"); @@ -78,10 +74,9 @@ public void testLogToDiskWithLimits() throws Exception { String filename = file.getAbsolutePath() + "bar"; CronvoyLogger logger = new CronvoyLogger(); logger.setNetLogToDisk(filename, 5); - logger.log("hello!"); - logger.log("goodbye"); + logger.log(EnvoyLogger.Level.INFO, "hello!"); + logger.log(EnvoyLogger.Level.INFO, "goodbye"); logger.stopLogging(); - char[] buffer = new char[5000]; byte[] bytes = Files.readAllBytes(Paths.get(filename + "/netlog.json")); String fileContent = new String(bytes); assertEquals("goodbye", fileContent); diff --git a/mobile/test/java/org/chromium/net/testing/BUILD b/mobile/test/java/org/chromium/net/testing/BUILD index fded9b2def000..d086f967686e6 100644 --- a/mobile/test/java/org/chromium/net/testing/BUILD +++ b/mobile/test/java/org/chromium/net/testing/BUILD @@ -61,10 +61,10 @@ envoy_mobile_android_test( "CronetTestRuleTest.java", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -89,10 +89,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -113,10 +113,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/java/org/chromium/net/urlconnection/BUILD b/mobile/test/java/org/chromium/net/urlconnection/BUILD index 56c47a6b9b9f2..c5424f48828a8 100644 --- a/mobile/test/java/org/chromium/net/urlconnection/BUILD +++ b/mobile/test/java/org/chromium/net/urlconnection/BUILD @@ -22,10 +22,10 @@ envoy_mobile_android_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/common/jni/BUILD b/mobile/test/jni/BUILD similarity index 92% rename from mobile/test/common/jni/BUILD rename to mobile/test/jni/BUILD index 4ff3d508af142..7e1d78cd76b00 100644 --- a/mobile/test/common/jni/BUILD +++ b/mobile/test/jni/BUILD @@ -11,7 +11,7 @@ cc_library( testonly = True, deps = [ ":server_envoy_jni_lib", - "//library/common/jni:envoy_jni_lib", + "//library/jni:envoy_jni_lib", "@envoy_build_config//:test_extensions", ], ) @@ -28,7 +28,7 @@ cc_library( "//conditions:default": [], }), deps = [ - "//library/common/jni:envoy_jni_lib", + "//library/jni:envoy_jni_lib", "//test/common/integration:test_server_interface_lib", "//test/common/integration:xds_test_server_interface_lib", ], @@ -63,7 +63,7 @@ cc_library( testonly = True, deps = [ ":server_envoy_jni_lib", - "//library/common/jni:envoy_jni_lib", + "//library/jni:envoy_jni_lib", "@envoy//source/common/listener_manager:listener_manager_lib", ], ) @@ -90,7 +90,7 @@ cc_library( "jni_helper_test.cc", ], deps = [ - "//library/common/jni:jni_helper_lib", + "//library/jni:jni_helper_lib", ], alwayslink = True, ) @@ -110,7 +110,7 @@ cc_library( "jni_utility_test.cc", ], deps = [ - "//library/common/jni:jni_utility_lib", + "//library/jni:jni_utility_lib", ], alwayslink = True, ) diff --git a/mobile/test/common/jni/jni_helper_test.cc b/mobile/test/jni/jni_helper_test.cc similarity index 99% rename from mobile/test/common/jni/jni_helper_test.cc rename to mobile/test/jni/jni_helper_test.cc index 1ab5c3699dcde..2d76984b3d03e 100644 --- a/mobile/test/common/jni/jni_helper_test.cc +++ b/mobile/test/jni/jni_helper_test.cc @@ -1,6 +1,6 @@ #include -#include "library/common/jni/jni_helper.h" +#include "library/jni/jni_helper.h" // NOLINT(namespace-envoy) diff --git a/mobile/test/common/jni/jni_utility_test.cc b/mobile/test/jni/jni_utility_test.cc similarity index 93% rename from mobile/test/common/jni/jni_utility_test.cc rename to mobile/test/jni/jni_utility_test.cc index e81dc108727b2..96a26eafd21e8 100644 --- a/mobile/test/common/jni/jni_utility_test.cc +++ b/mobile/test/jni/jni_utility_test.cc @@ -1,6 +1,6 @@ #include -#include "library/common/jni/jni_utility.h" +#include "library/jni/jni_utility.h" // NOLINT(namespace-envoy) diff --git a/mobile/test/common/jni/test_jni_impl.cc b/mobile/test/jni/test_jni_impl.cc similarity index 99% rename from mobile/test/common/jni/test_jni_impl.cc rename to mobile/test/jni/test_jni_impl.cc index 5f6e8ad135f99..455665ac3b454 100644 --- a/mobile/test/common/jni/test_jni_impl.cc +++ b/mobile/test/jni/test_jni_impl.cc @@ -4,7 +4,7 @@ #include "test/common/integration/xds_test_server_interface.h" #include "test/test_common/utility.h" -#include "library/common/jni/jni_support.h" +#include "library/jni/jni_support.h" // NOLINT(namespace-envoy) diff --git a/mobile/test/kotlin/apps/baseline/MainActivity.kt b/mobile/test/kotlin/apps/baseline/MainActivity.kt index ebadd21327c07..2e9fae1a331fb 100644 --- a/mobile/test/kotlin/apps/baseline/MainActivity.kt +++ b/mobile/test/kotlin/apps/baseline/MainActivity.kt @@ -60,7 +60,7 @@ class MainActivity : Activity() { Log.d("MainActivity", "Event emitted: ${entry.key}, ${entry.value}") } }) - .setLogger { Log.d("MainActivity", it) } + .setLogger { _, message -> Log.d("MainActivity", message) } .build() recyclerView = findViewById(R.id.recycler_view) as RecyclerView diff --git a/mobile/test/kotlin/apps/experimental/MainActivity.kt b/mobile/test/kotlin/apps/experimental/MainActivity.kt index a50c69a635770..673fbefc88649 100644 --- a/mobile/test/kotlin/apps/experimental/MainActivity.kt +++ b/mobile/test/kotlin/apps/experimental/MainActivity.kt @@ -75,7 +75,7 @@ class MainActivity : Activity() { Log.d("MainActivity", "Event emitted: ${entry.key}, ${entry.value}") } }) - .setLogger { Log.d("MainActivity", it) } + .setLogger { _, message -> Log.d("MainActivity", message) } .build() recyclerView = findViewById(R.id.recycler_view) as RecyclerView diff --git a/mobile/test/kotlin/integration/BUILD b/mobile/test/kotlin/integration/BUILD index f26d908b847dc..3fadd88c5c992 100644 --- a/mobile/test/kotlin/integration/BUILD +++ b/mobile/test/kotlin/integration/BUILD @@ -12,10 +12,10 @@ envoy_mobile_jni_kt_test( "EnvoyEngineSimpleIntegrationTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -31,10 +31,10 @@ envoy_mobile_jni_kt_test( "EngineApiTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -50,10 +50,10 @@ envoy_mobile_jni_kt_test( "KeyValueStoreTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -69,10 +69,10 @@ envoy_mobile_jni_kt_test( "SetEventTrackerTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -88,10 +88,10 @@ envoy_mobile_jni_kt_test( "SetLoggerTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -107,10 +107,10 @@ envoy_mobile_jni_kt_test( "CancelStreamTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -126,10 +126,10 @@ envoy_mobile_jni_kt_test( "StreamIdleTimeoutTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -145,10 +145,10 @@ envoy_mobile_jni_kt_test( "CancelGRPCStreamTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -164,10 +164,10 @@ envoy_mobile_jni_kt_test( "ResetConnectivityStateTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -183,10 +183,10 @@ envoy_mobile_jni_kt_test( "GRPCReceiveErrorTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -206,10 +206,10 @@ envoy_mobile_jni_kt_test( "sandboxNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -225,10 +225,10 @@ envoy_mobile_jni_kt_test( "ReceiveErrorTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -244,10 +244,10 @@ envoy_mobile_android_test( "SendDataTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -264,10 +264,10 @@ envoy_mobile_jni_kt_test( "SendHeadersTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -283,10 +283,10 @@ envoy_mobile_jni_kt_test( "SendTrailersTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -302,10 +302,10 @@ envoy_mobile_jni_kt_test( "ReceiveTrailersTest.kt", ], native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -326,10 +326,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), @@ -347,10 +347,10 @@ envoy_mobile_android_test( ], native_deps = [ "@envoy//test/config/integration/certs", - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/kotlin/integration/SetLoggerTest.kt b/mobile/test/kotlin/integration/SetLoggerTest.kt index 0e3b9f9804887..bed9c3557fb5a 100644 --- a/mobile/test/kotlin/integration/SetLoggerTest.kt +++ b/mobile/test/kotlin/integration/SetLoggerTest.kt @@ -29,7 +29,7 @@ class SetLoggerTest { "test_logger", "{\"@type\":\"type.googleapis.com/envoymobile.extensions.filters.http.test_logger.TestLogger\"}" ) - .setLogger { msg -> + .setLogger { _, msg -> if (msg.contains("starting main dispatch loop")) { countDownLatch.countDown() } diff --git a/mobile/test/kotlin/integration/proxying/BUILD b/mobile/test/kotlin/integration/proxying/BUILD index 9c14b6adfb186..5e06812b1646f 100644 --- a/mobile/test/kotlin/integration/proxying/BUILD +++ b/mobile/test/kotlin/integration/proxying/BUILD @@ -16,10 +16,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions.so", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", ], "//conditions:default": [], }), @@ -42,10 +42,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions.so", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", ], "//conditions:default": [], }), @@ -68,10 +68,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions.so", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", ], "//conditions:default": [], }), @@ -94,10 +94,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions.so", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", ], "//conditions:default": [], }), @@ -120,10 +120,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions.so", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", ], "//conditions:default": [], }), @@ -146,10 +146,10 @@ envoy_mobile_android_test( "dockerNetwork": "standard", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions.so", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_and_listener_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/kotlin/io/envoyproxy/envoymobile/BUILD b/mobile/test/kotlin/io/envoyproxy/envoymobile/BUILD index 39aa8ecb62567..aae53613f0535 100644 --- a/mobile/test/kotlin/io/envoyproxy/envoymobile/BUILD +++ b/mobile/test/kotlin/io/envoyproxy/envoymobile/BUILD @@ -15,10 +15,10 @@ envoy_mobile_jni_kt_test( "sandboxAllowed": "False", }, native_deps = [ - "//test/common/jni:libenvoy_jni_with_test_extensions.so", + "//test/jni:libenvoy_jni_with_test_extensions.so", ] + select({ "@platforms//os:macos": [ - "//test/common/jni:libenvoy_jni_with_test_extensions_jnilib", + "//test/jni:libenvoy_jni_with_test_extensions_jnilib", ], "//conditions:default": [], }), diff --git a/mobile/test/non_hermetic/BUILD b/mobile/test/non_hermetic/BUILD index 98c0db304e5a5..5f7583b1a086a 100644 --- a/mobile/test/non_hermetic/BUILD +++ b/mobile/test/non_hermetic/BUILD @@ -25,7 +25,7 @@ envoy_cc_test_binary( ], repository = "@envoy", deps = [ - "//library/common:envoy_main_interface_lib_no_stamp", + "//library/common:internal_engine_lib_no_stamp", "//library/common/data:utility_lib", "//library/common/types:c_types_lib", "//test/common/integration:base_client_integration_test_lib", diff --git a/mobile/test/performance/BUILD b/mobile/test/performance/BUILD index b77bc54c243d6..d9ec65104bfdb 100644 --- a/mobile/test/performance/BUILD +++ b/mobile/test/performance/BUILD @@ -9,5 +9,5 @@ envoy_cc_binary( srcs = ["test_binary_size.cc"], repository = "@envoy", stamped = True, - deps = ["//library/common:envoy_main_interface_lib"], + deps = ["//library/common:internal_engine_lib"], ) diff --git a/mobile/test/performance/test_binary_size.cc b/mobile/test/performance/test_binary_size.cc index c660c9f253877..68f660941e8f7 100644 --- a/mobile/test/performance/test_binary_size.cc +++ b/mobile/test/performance/test_binary_size.cc @@ -1,9 +1,8 @@ -#include "library/common/engine.h" -#include "library/common/main_interface.h" +#include "library/common/internal_engine.h" // NOLINT(namespace-envoy) // This binary is used to perform stripped down binary size investigations of the Envoy codebase. // Please refer to the development docs for more information: // https://envoymobile.io/docs/envoy-mobile/latest/development/performance/binary_size.html -int main() { return reinterpret_cast(0)->run(nullptr, nullptr); } +int main() { return reinterpret_cast(0)->run(nullptr, nullptr); } diff --git a/mobile/test/swift/integration/SetLoggerTest.swift b/mobile/test/swift/integration/SetLoggerTest.swift index 0c6fa988c6e03..fb71c81d3815d 100644 --- a/mobile/test/swift/integration/SetLoggerTest.swift +++ b/mobile/test/swift/integration/SetLoggerTest.swift @@ -71,7 +71,7 @@ static_resources: let engine = EngineBuilder(yaml: config) .addLogLevel(.debug) - .setLogger { msg in + .setLogger { _, msg in if msg.contains("starting main dispatch loop") { loggingExpectation.fulfill() } diff --git a/source/common/access_log/access_log_impl.cc b/source/common/access_log/access_log_impl.cc index 24972a34d3252..fd72e00b1a743 100644 --- a/source/common/access_log/access_log_impl.cc +++ b/source/common/access_log/access_log_impl.cc @@ -215,20 +215,34 @@ bool HeaderFilter::evaluate(const Formatter::HttpFormatterContext& context, } ResponseFlagFilter::ResponseFlagFilter( - const envoy::config::accesslog::v3::ResponseFlagFilter& config) { + const envoy::config::accesslog::v3::ResponseFlagFilter& config) + : has_configured_flags_(!config.flags().empty()) { + + // Preallocate the vector to avoid frequent heap allocations. + configured_flags_.resize(StreamInfo::ResponseFlagUtils::responseFlagsVec().size(), false); for (int i = 0; i < config.flags_size(); i++) { - absl::optional response_flag = - StreamInfo::ResponseFlagUtils::toResponseFlag(config.flags(i)); + auto response_flag = StreamInfo::ResponseFlagUtils::toResponseFlag(config.flags(i)); // The config has been validated. Therefore, every flag in the config will have a mapping. ASSERT(response_flag.has_value()); - configured_flags_ |= response_flag.value(); + + // The vector is allocated with the size of the response flags vec. Therefore, the index + // should always be valid. + ASSERT(response_flag.value().value() < configured_flags_.size()); + + configured_flags_[response_flag.value().value()] = true; } } bool ResponseFlagFilter::evaluate(const Formatter::HttpFormatterContext&, const StreamInfo::StreamInfo& info) const { - if (configured_flags_ != 0) { - return info.intersectResponseFlags(configured_flags_); + if (has_configured_flags_) { + for (const auto flag : info.responseFlags()) { + ASSERT(flag.value() < configured_flags_.size()); + if (configured_flags_[flag.value()]) { + return true; + } + } + return false; } return info.hasAnyResponseFlag(); } diff --git a/source/common/access_log/access_log_impl.h b/source/common/access_log/access_log_impl.h index 298b481cbd2ed..6572fcefd5ecc 100644 --- a/source/common/access_log/access_log_impl.h +++ b/source/common/access_log/access_log_impl.h @@ -188,7 +188,8 @@ class ResponseFlagFilter : public Filter { const StreamInfo::StreamInfo& info) const override; private: - uint64_t configured_flags_{}; + const bool has_configured_flags_{}; + std::vector configured_flags_{}; }; /** diff --git a/source/common/buffer/watermark_buffer.cc b/source/common/buffer/watermark_buffer.cc index f2b6208a663aa..bc9d6629c5e69 100644 --- a/source/common/buffer/watermark_buffer.cc +++ b/source/common/buffer/watermark_buffer.cc @@ -1,5 +1,4 @@ #include "source/common/buffer/watermark_buffer.h" -#include "watermark_buffer.h" #include #include diff --git a/source/common/common/BUILD b/source/common/common/BUILD index f1fb01081e22d..aa0edac5aa61b 100644 --- a/source/common/common/BUILD +++ b/source/common/common/BUILD @@ -373,8 +373,10 @@ envoy_cc_library( name = "scope_tracker", hdrs = ["scope_tracker.h"], deps = [ + "//envoy/common:execution_context", "//envoy/common:scope_tracker_interface", "//envoy/event:dispatcher_interface", + "//source/common/runtime:runtime_features_lib", ], ) @@ -382,6 +384,7 @@ envoy_cc_library( name = "scope_tracked_object_stack", hdrs = ["scope_tracked_object_stack.h"], deps = [ + "//envoy/common:execution_context", "//envoy/common:scope_tracker_interface", ], ) diff --git a/source/common/common/perf_tracing.cc b/source/common/common/perf_tracing.cc index ef08e6aee2562..46d2ca8a9b887 100644 --- a/source/common/common/perf_tracing.cc +++ b/source/common/common/perf_tracing.cc @@ -1,6 +1,6 @@ #ifdef ENVOY_PERFETTO -#include "perf_tracing.h" +#include "source/common/common/perf_tracing.h" // NOLINT(namespace-envoy) diff --git a/source/common/common/scope_tracked_object_stack.h b/source/common/common/scope_tracked_object_stack.h index 8e6ee276084e8..fbdcf7db38eef 100644 --- a/source/common/common/scope_tracked_object_stack.h +++ b/source/common/common/scope_tracked_object_stack.h @@ -3,6 +3,7 @@ #include #include +#include "envoy/common/execution_context.h" #include "envoy/common/scope_tracker.h" namespace Envoy { diff --git a/source/common/common/scope_tracker.h b/source/common/common/scope_tracker.h index eb2690a273255..dfe9947042452 100644 --- a/source/common/common/scope_tracker.h +++ b/source/common/common/scope_tracker.h @@ -1,9 +1,11 @@ #pragma once +#include "envoy/common/execution_context.h" #include "envoy/common/scope_tracker.h" #include "envoy/event/dispatcher.h" #include "source/common/common/assert.h" +#include "source/common/runtime/runtime_features.h" namespace Envoy { @@ -16,7 +18,9 @@ namespace Envoy { class ScopeTrackerScopeState { public: ScopeTrackerScopeState(const ScopeTrackedObject* object, Event::ScopeTracker& tracker) - : registered_object_(object), tracker_(tracker) { + : registered_object_(object), + scoped_execution_context_(executionContextEnabled() ? object->executionContext() : nullptr), + tracker_(tracker) { tracker_.pushTrackedObject(registered_object_); } @@ -31,7 +35,14 @@ class ScopeTrackerScopeState { void* operator new(std::size_t) = delete; private: + friend class ScopeTrackerScopeStateTest; + static bool& executionContextEnabled() { + static bool enabled = + Runtime::runtimeFeatureEnabled("envoy.restart_features.enable_execution_context"); + return enabled; + } const ScopeTrackedObject* registered_object_; + ScopedExecutionContext scoped_execution_context_; Event::ScopeTracker& tracker_; }; diff --git a/source/common/config/config_provider_impl.h b/source/common/config/config_provider_impl.h index b4a04faaaecc9..e346780031b71 100644 --- a/source/common/config/config_provider_impl.h +++ b/source/common/config/config_provider_impl.h @@ -211,7 +211,7 @@ class ConfigSubscriptionCommonBase : protected Logger::Loggable void { start(); }); diff --git a/source/common/config/subscription_factory_impl.cc b/source/common/config/subscription_factory_impl.cc index c06588a1300e9..4e11b27da8b50 100644 --- a/source/common/config/subscription_factory_impl.cc +++ b/source/common/config/subscription_factory_impl.cc @@ -27,7 +27,7 @@ SubscriptionPtr SubscriptionFactoryImpl::subscriptionFromConfigSource( const envoy::config::core::v3::ConfigSource& config, absl::string_view type_url, Stats::Scope& scope, SubscriptionCallbacks& callbacks, OpaqueResourceDecoderSharedPtr resource_decoder, const SubscriptionOptions& options) { - Config::Utility::checkLocalInfo(type_url, local_info_); + THROW_IF_NOT_OK(Config::Utility::checkLocalInfo(type_url, local_info_)); SubscriptionStats stats = Utility::generateStats(scope); std::string subscription_type = ""; @@ -50,19 +50,20 @@ SubscriptionPtr SubscriptionFactoryImpl::subscriptionFromConfigSource( switch (config.config_source_specifier_case()) { case envoy::config::core::v3::ConfigSource::ConfigSourceSpecifierCase::kPath: { - Utility::checkFilesystemSubscriptionBackingPath(config.path(), api_); + THROW_IF_NOT_OK(Utility::checkFilesystemSubscriptionBackingPath(config.path(), api_)); subscription_type = "envoy.config_subscription.filesystem"; break; } case envoy::config::core::v3::ConfigSource::ConfigSourceSpecifierCase::kPathConfigSource: { - Utility::checkFilesystemSubscriptionBackingPath(config.path_config_source().path(), api_); + THROW_IF_NOT_OK( + Utility::checkFilesystemSubscriptionBackingPath(config.path_config_source().path(), api_)); subscription_type = "envoy.config_subscription.filesystem"; break; } case envoy::config::core::v3::ConfigSource::ConfigSourceSpecifierCase::kApiConfigSource: { const envoy::config::core::v3::ApiConfigSource& api_config_source = config.api_config_source(); - Utility::checkApiConfigSourceSubscriptionBackingCluster(cm_.primaryClusters(), - api_config_source); + THROW_IF_NOT_OK(Utility::checkApiConfigSourceSubscriptionBackingCluster(cm_.primaryClusters(), + api_config_source)); THROW_IF_NOT_OK(Utility::checkTransportVersion(api_config_source)); switch (api_config_source.api_type()) { PANIC_ON_PROTO_ENUM_SENTINEL_VALUES; @@ -147,7 +148,7 @@ SubscriptionPtr SubscriptionFactoryImpl::collectionSubscriptionFromUrl( switch (collection_locator.scheme()) { case xds::core::v3::ResourceLocator::FILE: { const std::string path = Http::Utility::localPathFromFilePath(collection_locator.id()); - Utility::checkFilesystemSubscriptionBackingPath(path, api_); + THROW_IF_NOT_OK(Utility::checkFilesystemSubscriptionBackingPath(path, api_)); factory_config.set_path(path); return createFromFactoryOrThrow(data, "envoy.config_subscription.filesystem_collection"); } @@ -161,8 +162,8 @@ SubscriptionPtr SubscriptionFactoryImpl::collectionSubscriptionFromUrl( case envoy::config::core::v3::ConfigSource::ConfigSourceSpecifierCase::kApiConfigSource: { const envoy::config::core::v3::ApiConfigSource& api_config_source = config.api_config_source(); - Utility::checkApiConfigSourceSubscriptionBackingCluster(cm_.primaryClusters(), - api_config_source); + THROW_IF_NOT_OK(Utility::checkApiConfigSourceSubscriptionBackingCluster(cm_.primaryClusters(), + api_config_source)); // All Envoy collections currently are xDS resource graph roots and require node context // parameters. options.add_xdstp_node_context_params_ = true; diff --git a/source/common/config/utility.cc b/source/common/config/utility.cc index c1db95c678e7b..eff142670f253 100644 --- a/source/common/config/utility.cc +++ b/source/common/config/utility.cc @@ -27,107 +27,106 @@ std::string Utility::truncateGrpcStatusMessage(absl::string_view error_message) error_message.length() > kProtobufErrMsgLen ? "...(truncated)" : ""); } -Upstream::ClusterConstOptRef Utility::checkCluster(absl::string_view error_prefix, - absl::string_view cluster_name, - Upstream::ClusterManager& cm, - bool allow_added_via_api) { +absl::StatusOr Utility::checkCluster(absl::string_view error_prefix, + absl::string_view cluster_name, + Upstream::ClusterManager& cm, + bool allow_added_via_api) { const auto cluster = cm.clusters().getCluster(cluster_name); if (!cluster.has_value()) { - throwEnvoyExceptionOrPanic(fmt::format("{}: unknown cluster '{}'", error_prefix, cluster_name)); + return absl::InvalidArgumentError( + fmt::format("{}: unknown cluster '{}'", error_prefix, cluster_name)); } if (!allow_added_via_api && cluster->get().info()->addedViaApi()) { - throwEnvoyExceptionOrPanic(fmt::format( + return absl::InvalidArgumentError(fmt::format( "{}: invalid cluster '{}': currently only static (non-CDS) clusters are supported", error_prefix, cluster_name)); } return cluster; } -Upstream::ClusterConstOptRef -Utility::checkClusterAndLocalInfo(absl::string_view error_prefix, absl::string_view cluster_name, - Upstream::ClusterManager& cm, - const LocalInfo::LocalInfo& local_info) { - checkLocalInfo(error_prefix, local_info); - return checkCluster(error_prefix, cluster_name, cm); -} - -void Utility::checkLocalInfo(absl::string_view error_prefix, - const LocalInfo::LocalInfo& local_info) { +absl::Status Utility::checkLocalInfo(absl::string_view error_prefix, + const LocalInfo::LocalInfo& local_info) { if (local_info.clusterName().empty() || local_info.nodeName().empty()) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( fmt::format("{}: node 'id' and 'cluster' are required. Set it either in 'node' config or " "via --service-node and --service-cluster options.", error_prefix, local_info.node().DebugString())); } + return absl::OkStatus(); } -void Utility::checkFilesystemSubscriptionBackingPath(const std::string& path, Api::Api& api) { +absl::Status Utility::checkFilesystemSubscriptionBackingPath(const std::string& path, + Api::Api& api) { // TODO(junr03): the file might be deleted between this check and the // watch addition. if (!api.fileSystem().fileExists(path)) { - throwEnvoyExceptionOrPanic(fmt::format( + return absl::InvalidArgumentError(fmt::format( "paths must refer to an existing path in the system: '{}' does not exist", path)); } + return absl::OkStatus(); } namespace { /** * Check the grpc_services and cluster_names for API config sanity. Throws on error. * @param api_config_source the config source to validate. - * @throws EnvoyException when an API config has the wrong number of gRPC + * @return an invalid status when an API config has the wrong number of gRPC * services or cluster names, depending on expectations set by its API type. */ -void checkApiConfigSourceNames(const envoy::config::core::v3::ApiConfigSource& api_config_source) { +absl::Status +checkApiConfigSourceNames(const envoy::config::core::v3::ApiConfigSource& api_config_source) { const bool is_grpc = (api_config_source.api_type() == envoy::config::core::v3::ApiConfigSource::GRPC || api_config_source.api_type() == envoy::config::core::v3::ApiConfigSource::DELTA_GRPC); if (api_config_source.cluster_names().empty() && api_config_source.grpc_services().empty()) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( fmt::format("API configs must have either a gRPC service or a cluster name defined: {}", api_config_source.DebugString())); } if (is_grpc) { if (!api_config_source.cluster_names().empty()) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( fmt::format("{}::(DELTA_)GRPC must not have a cluster name specified: {}", api_config_source.GetTypeName(), api_config_source.DebugString())); } if (api_config_source.grpc_services().size() > 1) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( fmt::format("{}::(DELTA_)GRPC must have a single gRPC service specified: {}", api_config_source.GetTypeName(), api_config_source.DebugString())); } } else { if (!api_config_source.grpc_services().empty()) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( fmt::format("{}, if not a gRPC type, must not have a gRPC service specified: {}", api_config_source.GetTypeName(), api_config_source.DebugString())); } if (api_config_source.cluster_names().size() != 1) { - throwEnvoyExceptionOrPanic(fmt::format("{} must have a singleton cluster name specified: {}", - api_config_source.GetTypeName(), - api_config_source.DebugString())); + return absl::InvalidArgumentError( + fmt::format("{} must have a singleton cluster name specified: {}", + api_config_source.GetTypeName(), api_config_source.DebugString())); } } + return absl::OkStatus(); } } // namespace -void Utility::validateClusterName(const Upstream::ClusterManager::ClusterSet& primary_clusters, - const std::string& cluster_name, - const std::string& config_source) { +absl::Status +Utility::validateClusterName(const Upstream::ClusterManager::ClusterSet& primary_clusters, + const std::string& cluster_name, const std::string& config_source) { const auto& it = primary_clusters.find(cluster_name); if (it == primary_clusters.end()) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( fmt::format("{} must have a statically defined non-EDS cluster: '{}' does " "not exist, was added via api, or is an EDS cluster", config_source, cluster_name)); } + return absl::OkStatus(); } -void Utility::checkApiConfigSourceSubscriptionBackingCluster( +absl::Status Utility::checkApiConfigSourceSubscriptionBackingCluster( const Upstream::ClusterManager::ClusterSet& primary_clusters, const envoy::config::core::v3::ApiConfigSource& api_config_source) { // We don't need to check backing sources for ADS sources, the backing cluster must be verified in @@ -135,9 +134,9 @@ void Utility::checkApiConfigSourceSubscriptionBackingCluster( if (api_config_source.api_type() == envoy::config::core::v3::ApiConfigSource::AGGREGATED_GRPC || api_config_source.api_type() == envoy::config::core::v3::ApiConfigSource::AGGREGATED_DELTA_GRPC) { - return; + return absl::OkStatus(); } - checkApiConfigSourceNames(api_config_source); + RETURN_IF_NOT_OK(checkApiConfigSourceNames(api_config_source)); const bool is_grpc = (api_config_source.api_type() == envoy::config::core::v3::ApiConfigSource::GRPC); @@ -146,19 +145,20 @@ void Utility::checkApiConfigSourceSubscriptionBackingCluster( // All API configs of type REST and UNSUPPORTED_REST_LEGACY should have cluster names. // Additionally, some gRPC API configs might have a cluster name set instead // of an envoy gRPC. - Utility::validateClusterName(primary_clusters, api_config_source.cluster_names()[0], - api_config_source.GetTypeName()); + RETURN_IF_NOT_OK(Utility::validateClusterName( + primary_clusters, api_config_source.cluster_names()[0], api_config_source.GetTypeName())); } else if (is_grpc) { // Some ApiConfigSources of type GRPC won't have a cluster name, such as if // they've been configured with google_grpc. if (api_config_source.grpc_services()[0].has_envoy_grpc()) { // If an Envoy gRPC exists, we take its cluster name. - Utility::validateClusterName(primary_clusters, - api_config_source.grpc_services()[0].envoy_grpc().cluster_name(), - api_config_source.GetTypeName()); + RETURN_IF_NOT_OK(Utility::validateClusterName( + primary_clusters, api_config_source.grpc_services()[0].envoy_grpc().cluster_name(), + api_config_source.GetTypeName())); } } // Otherwise, there is no cluster name to validate. + return absl::OkStatus(); } absl::optional @@ -177,22 +177,6 @@ Utility::getGrpcControlPlane(const envoy::config::core::v3::ApiConfigSource& api return absl::nullopt; } -std::chrono::milliseconds Utility::apiConfigSourceRefreshDelay( - const envoy::config::core::v3::ApiConfigSource& api_config_source) { - if (!api_config_source.has_refresh_delay()) { - throwEnvoyExceptionOrPanic("refresh_delay is required for REST API configuration sources"); - } - - return std::chrono::milliseconds( - DurationUtil::durationToMilliseconds(api_config_source.refresh_delay())); -} - -std::chrono::milliseconds Utility::apiConfigSourceRequestTimeout( - const envoy::config::core::v3::ApiConfigSource& api_config_source) { - return std::chrono::milliseconds( - PROTOBUF_GET_MS_OR_DEFAULT(api_config_source, request_timeout, 1000)); -} - std::chrono::milliseconds Utility::configSourceInitialFetchTimeout( const envoy::config::core::v3::ConfigSource& config_source) { return std::chrono::milliseconds( @@ -220,28 +204,17 @@ Utility::createTagProducer(const envoy::config::bootstrap::v3::Bootstrap& bootst return std::make_unique(bootstrap.stats_config(), cli_tags); } -Stats::StatsMatcherPtr -Utility::createStatsMatcher(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, - Stats::SymbolTable& symbol_table) { - return std::make_unique(bootstrap.stats_config(), symbol_table); -} - -Stats::HistogramSettingsConstPtr -Utility::createHistogramSettings(const envoy::config::bootstrap::v3::Bootstrap& bootstrap) { - return std::make_unique(bootstrap.stats_config()); -} - -Grpc::AsyncClientFactoryPtr Utility::factoryForGrpcApiConfigSource( +absl::StatusOr Utility::factoryForGrpcApiConfigSource( Grpc::AsyncClientManager& async_client_manager, const envoy::config::core::v3::ApiConfigSource& api_config_source, Stats::Scope& scope, bool skip_cluster_check) { - checkApiConfigSourceNames(api_config_source); + RETURN_IF_NOT_OK(checkApiConfigSourceNames(api_config_source)); if (api_config_source.api_type() != envoy::config::core::v3::ApiConfigSource::GRPC && api_config_source.api_type() != envoy::config::core::v3::ApiConfigSource::DELTA_GRPC) { - throwEnvoyExceptionOrPanic(fmt::format("{} type must be gRPC: {}", - api_config_source.GetTypeName(), - api_config_source.DebugString())); + return absl::InvalidArgumentError(fmt::format("{} type must be gRPC: {}", + api_config_source.GetTypeName(), + api_config_source.DebugString())); } envoy::config::core::v3::GrpcService grpc_service; @@ -309,7 +282,8 @@ void Utility::translateOpaqueConfig(const ProtobufWkt::Any& typed_config, } } -JitteredExponentialBackOffStrategyPtr Utility::buildJitteredExponentialBackOffStrategy( +absl::StatusOr +Utility::buildJitteredExponentialBackOffStrategy( absl::optional backoff, Random::RandomGenerator& random, const uint32_t default_base_interval_ms, absl::optional default_max_interval_ms) { @@ -320,7 +294,8 @@ JitteredExponentialBackOffStrategyPtr Utility::buildJitteredExponentialBackOffSt PROTOBUF_GET_MS_OR_DEFAULT(backoff.value(), max_interval, base_interval_ms * 10); if (max_interval_ms < base_interval_ms) { - throwEnvoyExceptionOrPanic("max_interval must be greater than or equal to the base_interval"); + return absl::InvalidArgumentError( + "max_interval must be greater than or equal to the base_interval"); } return std::make_unique(base_interval_ms, max_interval_ms, random); @@ -328,13 +303,13 @@ JitteredExponentialBackOffStrategyPtr Utility::buildJitteredExponentialBackOffSt // default_base_interval_ms must be greater than zero if (default_base_interval_ms == 0) { - throwEnvoyExceptionOrPanic("default_base_interval_ms must be greater than zero"); + return absl::InvalidArgumentError("default_base_interval_ms must be greater than zero"); } // default maximum interval is specified if (default_max_interval_ms != absl::nullopt) { if (default_max_interval_ms.value() < default_base_interval_ms) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( "default_max_interval_ms must be greater than or equal to the default_base_interval_ms"); } return std::make_unique( diff --git a/source/common/config/utility.h b/source/common/config/utility.h index 8b8bb3be7ce95..5dfa959b1f5ed 100644 --- a/source/common/config/utility.h +++ b/source/common/config/utility.h @@ -84,21 +84,6 @@ class Utility { return std::make_pair("hash_" + Hex::uint64ToHex(hash), hash); } - /** - * Extract refresh_delay as a std::chrono::milliseconds from - * envoy::config::core::v3::ApiConfigSource. - */ - static std::chrono::milliseconds - apiConfigSourceRefreshDelay(const envoy::config::core::v3::ApiConfigSource& api_config_source); - - /** - * Extract request_timeout as a std::chrono::milliseconds from - * envoy::config::core::v3::ApiConfigSource. If request_timeout isn't set in the config source, a - * default value of 1s will be returned. - */ - static std::chrono::milliseconds - apiConfigSourceRequestTimeout(const envoy::config::core::v3::ApiConfigSource& api_config_source); - /** * Extract initial_fetch_timeout as a std::chrono::milliseconds from * envoy::config::core::v3::ApiConfigSource. If request_timeout isn't set in the config source, a @@ -108,64 +93,54 @@ class Utility { configSourceInitialFetchTimeout(const envoy::config::core::v3::ConfigSource& config_source); /** - * Check cluster info for API config sanity. Throws on error. + * Check cluster info for API config sanity. * @param error_prefix supplies the prefix to use in error messages. * @param cluster_name supplies the cluster name to check. * @param cm supplies the cluster manager. * @param allow_added_via_api indicates whether a cluster is allowed to be added via api * rather than be a static resource from the bootstrap config. - * @return the main thread cluster if it exists. - */ - static Upstream::ClusterConstOptRef checkCluster(absl::string_view error_prefix, - absl::string_view cluster_name, - Upstream::ClusterManager& cm, - bool allow_added_via_api = false); - - /** - * Check cluster/local info for API config sanity. Throws on error. - * @param error_prefix supplies the prefix to use in error messages. - * @param cluster_name supplies the cluster name to check. - * @param cm supplies the cluster manager. - * @param local_info supplies the local info. - * @return the main thread cluster if it exists. + * @return the main thread cluster if it exists, or an error status if problematic. */ - static Upstream::ClusterConstOptRef - checkClusterAndLocalInfo(absl::string_view error_prefix, absl::string_view cluster_name, - Upstream::ClusterManager& cm, const LocalInfo::LocalInfo& local_info); + static absl::StatusOr + checkCluster(absl::string_view error_prefix, absl::string_view cluster_name, + Upstream::ClusterManager& cm, bool allow_added_via_api = false); /** - * Check local info for API config sanity. Throws on error. + * Check local info for API config sanity. * @param error_prefix supplies the prefix to use in error messages. * @param local_info supplies the local info. + * @return a status indicating if the config is sane. */ - static void checkLocalInfo(absl::string_view error_prefix, - const LocalInfo::LocalInfo& local_info); + static absl::Status checkLocalInfo(absl::string_view error_prefix, + const LocalInfo::LocalInfo& local_info); /** - * Check the existence of a path for a filesystem subscription. Throws on error. + * Check the existence of a path for a filesystem subscription. * @param path the path to validate. * @param api reference to the Api object + * @return a status indicating if the path exists. */ - static void checkFilesystemSubscriptionBackingPath(const std::string& path, Api::Api& api); + static absl::Status checkFilesystemSubscriptionBackingPath(const std::string& path, + Api::Api& api); /** * Check the validity of a cluster backing an api config source. Throws on error. * @param primary_clusters the API config source eligible clusters. * @param cluster_name the cluster name to validate. * @param config_source the config source typed name. - * @throws EnvoyException when an API config doesn't have a statically defined non-EDS cluster. + * @returns failure when an API config doesn't have a statically defined non-EDS cluster. */ - static void validateClusterName(const Upstream::ClusterManager::ClusterSet& primary_clusters, - const std::string& cluster_name, - const std::string& config_source); + static absl::Status + validateClusterName(const Upstream::ClusterManager::ClusterSet& primary_clusters, + const std::string& cluster_name, const std::string& config_source); /** * Potentially calls Utility::validateClusterName, if a cluster name can be found. * @param primary_clusters the API config source eligible clusters. * @param api_config_source the config source to validate. - * @throws EnvoyException when an API config doesn't have a statically defined non-EDS cluster. + * @return a status indicating if config is valid. */ - static void checkApiConfigSourceSubscriptionBackingCluster( + static absl::Status checkApiConfigSourceSubscriptionBackingCluster( const Upstream::ClusterManager::ClusterSet& primary_clusters, const envoy::config::core::v3::ApiConfigSource& api_config_source); @@ -427,19 +402,6 @@ class Utility { createTagProducer(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, const Stats::TagVector& cli_tags); - /** - * Create StatsMatcher instance. - */ - static Stats::StatsMatcherPtr - createStatsMatcher(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, - Stats::SymbolTable& symbol_table); - - /** - * Create HistogramSettings instance. - */ - static Stats::HistogramSettingsConstPtr - createHistogramSettings(const envoy::config::bootstrap::v3::Bootstrap& bootstrap); - /** * Obtain gRPC async client factory from a envoy::config::core::v3::ApiConfigSource. * @param async_client_manager gRPC async client manager. @@ -447,7 +409,7 @@ class Utility { * @param skip_cluster_check whether to skip cluster validation. * @return Grpc::AsyncClientFactoryPtr gRPC async client factory. */ - static Grpc::AsyncClientFactoryPtr + static absl::StatusOr factoryForGrpcApiConfigSource(Grpc::AsyncClientManager& async_client_manager, const envoy::config::core::v3::ApiConfigSource& api_config_source, Stats::Scope& scope, bool skip_cluster_check); @@ -523,7 +485,8 @@ class Utility { * found in the config or 2. default base interval and default maximum interval is specified or 3. * max interval is set to 10*default base interval */ - static JitteredExponentialBackOffStrategyPtr prepareJitteredExponentialBackOffStrategy( + static absl::StatusOr + prepareJitteredExponentialBackOffStrategy( const envoy::config::core::v3::ApiConfigSource& api_config_source, Random::RandomGenerator& random, const uint32_t default_base_interval_ms, absl::optional default_max_interval_ms) { @@ -548,7 +511,8 @@ class Utility { * default max interval is set to 10*default base interval */ template - static JitteredExponentialBackOffStrategyPtr prepareJitteredExponentialBackOffStrategy( + static absl::StatusOr + prepareJitteredExponentialBackOffStrategy( const T& config, Random::RandomGenerator& random, const uint32_t default_base_interval_ms, absl::optional default_max_interval_ms) { // If RetryPolicy containing backoff values is found in config @@ -573,7 +537,8 @@ class Utility { * specified or 2. default base interval and default maximum interval is specified or 3. * max interval is set to 10*default base interval */ - static JitteredExponentialBackOffStrategyPtr buildJitteredExponentialBackOffStrategy( + static absl::StatusOr + buildJitteredExponentialBackOffStrategy( absl::optional backoff, Random::RandomGenerator& random, const uint32_t default_base_interval_ms, absl::optional default_max_interval_ms); diff --git a/source/common/event/timer_impl.h b/source/common/event/timer_impl.h index 20641db7e29a1..d5612f37e20f6 100644 --- a/source/common/event/timer_impl.h +++ b/source/common/event/timer_impl.h @@ -23,15 +23,17 @@ class TimerUtils { * before doing any conversions. When the passed in duration exceeds INT32_MAX max seconds, the * output will be clipped to yield INT32_MAX seconds and 0 microseconds for the * output argument. We clip to INT32_MAX to guard against overflowing the timeval structure. - * Throws an EnvoyException on negative duration input. + * ENVOY_BUGs if the duration is negative. * @tparam Duration std::chrono duration type, e.g. seconds, milliseconds, ... * @param d duration value * @param tv output parameter that will be updated */ template static void durationToTimeval(const Duration& d, timeval& tv) { if (d.count() < 0) { - ExceptionUtil::throwEnvoyException( - fmt::format("Negative duration passed to durationToTimeval(): {}", d.count())); + IS_ENVOY_BUG(fmt::format("Negative duration passed to durationToTimeval(): {}", d.count())); + tv.tv_sec = 0; + tv.tv_usec = 500000; + return; }; constexpr int64_t clip_to = INT32_MAX; // 136.102208 years auto secs = std::chrono::duration_cast(d); diff --git a/source/common/formatter/stream_info_formatter.cc b/source/common/formatter/stream_info_formatter.cc index 7d72800f3aaae..29003ab607f4d 100644 --- a/source/common/formatter/stream_info_formatter.cc +++ b/source/common/formatter/stream_info_formatter.cc @@ -884,6 +884,19 @@ const StreamInfoFormatterProviderLookupTable& getKnownStreamInfoFormatterProvide return nullptr; }); }}}, + {"UPSTREAM_CONNECTION_ID", + {CommandSyntaxChecker::COMMAND_ONLY, + [](const std::string&, absl::optional) { + return std::make_unique( + [](const StreamInfo::StreamInfo& stream_info) { + uint64_t upstream_connection_id = 0; + if (stream_info.upstreamInfo().has_value()) { + upstream_connection_id = + stream_info.upstreamInfo()->upstreamConnectionId().value_or(0); + } + return upstream_connection_id; + }); + }}}, {"UPSTREAM_CLUSTER", {CommandSyntaxChecker::COMMAND_ONLY, [](const std::string&, absl::optional) { diff --git a/source/common/http/BUILD b/source/common/http/BUILD index d1ee13a01bf45..58ca10e930a3e 100644 --- a/source/common/http/BUILD +++ b/source/common/http/BUILD @@ -365,6 +365,7 @@ envoy_cc_library( "//source/common/http/http1:codec_lib", "//source/common/http/http2:codec_lib", "//source/common/http/match_delegate:config", + "//source/common/network:common_connection_filter_states_lib", "//source/common/network:proxy_protocol_filter_state_lib", "//source/common/network:utility_lib", "//source/common/quic:quic_server_factory_stub_lib", diff --git a/source/common/http/codec_client.cc b/source/common/http/codec_client.cc index 61cad323553ce..3cb1ffbd60f8c 100644 --- a/source/common/http/codec_client.cc +++ b/source/common/http/codec_client.cc @@ -114,7 +114,8 @@ void CodecClient::onEvent(Network::ConnectionEvent event) { reason = StreamResetReason::ConnectionTermination; if (protocol_error_) { reason = StreamResetReason::ProtocolError; - connection_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamProtocolError); + connection_->streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::UpstreamProtocolError); } } while (!active_requests_.empty()) { diff --git a/source/common/http/conn_manager_impl.cc b/source/common/http/conn_manager_impl.cc index c219d9699c474..47e7631c13095 100644 --- a/source/common/http/conn_manager_impl.cc +++ b/source/common/http/conn_manager_impl.cc @@ -254,13 +254,13 @@ void ConnectionManagerImpl::doEndStream(ActiveStream& stream, bool check_for_def // communicated via CONNECT_ERROR if (requestWasConnect(stream.request_headers_, codec_->protocol()) && (stream.filter_manager_.streamInfo().hasResponseFlag( - StreamInfo::ResponseFlag::UpstreamConnectionFailure) || + StreamInfo::CoreResponseFlag::UpstreamConnectionFailure) || stream.filter_manager_.streamInfo().hasResponseFlag( - StreamInfo::ResponseFlag::UpstreamConnectionTermination))) { + StreamInfo::CoreResponseFlag::UpstreamConnectionTermination))) { stream.response_encoder_->getStream().resetStream(StreamResetReason::ConnectError); } else { if (stream.filter_manager_.streamInfo().hasResponseFlag( - StreamInfo::ResponseFlag::UpstreamProtocolError)) { + StreamInfo::CoreResponseFlag::UpstreamProtocolError)) { stream.response_encoder_->getStream().resetStream(StreamResetReason::ProtocolError); } else { stream.response_encoder_->getStream().resetStream(StreamResetReason::LocalReset); @@ -435,7 +435,7 @@ RequestDecoder& ConnectionManagerImpl::newStream(ResponseEncoder& response_encod } void ConnectionManagerImpl::handleCodecErrorImpl(absl::string_view error, absl::string_view details, - StreamInfo::ResponseFlag response_flag) { + StreamInfo::CoreResponseFlag response_flag) { ENVOY_CONN_LOG(debug, "dispatch error: {}", read_callbacks_->connection(), error); read_callbacks_->connection().streamInfo().setResponseFlag(response_flag); @@ -446,13 +446,13 @@ void ConnectionManagerImpl::handleCodecErrorImpl(absl::string_view error, absl:: void ConnectionManagerImpl::handleCodecError(absl::string_view error) { handleCodecErrorImpl(error, absl::StrCat("codec_error:", StringUtil::replaceAllEmptySpace(error)), - StreamInfo::ResponseFlag::DownstreamProtocolError); + StreamInfo::CoreResponseFlag::DownstreamProtocolError); } void ConnectionManagerImpl::handleCodecOverloadError(absl::string_view error) { handleCodecErrorImpl(error, absl::StrCat("overload_error:", StringUtil::replaceAllEmptySpace(error)), - StreamInfo::ResponseFlag::OverloadManager); + StreamInfo::CoreResponseFlag::OverloadManager); } void ConnectionManagerImpl::createCodec(Buffer::Instance& data) { @@ -542,8 +542,8 @@ Network::FilterStatus ConnectionManagerImpl::onNewConnection() { return Network::FilterStatus::StopIteration; } -void ConnectionManagerImpl::resetAllStreams(absl::optional response_flag, - absl::string_view details) { +void ConnectionManagerImpl::resetAllStreams( + absl::optional response_flag, absl::string_view details) { while (!streams_.empty()) { // Mimic a downstream reset in this case. We must also remove callbacks here. Though we are // about to close the connection and will disable further reads, it is possible that flushing @@ -604,7 +604,7 @@ void ConnectionManagerImpl::onEvent(Network::ConnectionEvent event) { void ConnectionManagerImpl::doConnectionClose( absl::optional close_type, - absl::optional response_flag, absl::string_view details) { + absl::optional response_flag, absl::string_view details) { if (connection_idle_timer_) { connection_idle_timer_->disableTimer(); connection_idle_timer_.reset(); @@ -723,7 +723,7 @@ void ConnectionManagerImpl::onConnectionDurationTimeout() { if (!codec_) { // Attempt to write out buffered data one last time and issue a local close if successful. doConnectionClose(Network::ConnectionCloseType::FlushWrite, - StreamInfo::ResponseFlag::DurationTimeout, + StreamInfo::CoreResponseFlag::DurationTimeout, StreamInfo::ResponseCodeDetails::get().DurationTimeout); } else if (drain_state_ == DrainState::NotDraining) { startDrainSequence(); @@ -951,7 +951,7 @@ void ConnectionManagerImpl::ActiveStream::completeRequest() { filter_manager_.streamInfo().setResponseCodeDetails( StreamInfo::ResponseCodeDetails::get().DownstreamRemoteDisconnect); filter_manager_.streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::DownstreamConnectionTermination); + StreamInfo::CoreResponseFlag::DownstreamConnectionTermination); } connection_manager_.stats_.named_.downstream_rq_active_.dec(); if (filter_manager_.streamInfo().healthCheck()) { @@ -980,7 +980,7 @@ void ConnectionManagerImpl::ActiveStream::resetIdleTimer() { void ConnectionManagerImpl::ActiveStream::onIdleTimeout() { connection_manager_.stats_.named_.downstream_rq_idle_timeout_.inc(); - filter_manager_.streamInfo().setResponseFlag(StreamInfo::ResponseFlag::StreamIdleTimeout); + filter_manager_.streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::StreamIdleTimeout); sendLocalReply(Http::Utility::maybeRequestTimeoutCode(filter_manager_.remoteDecodeComplete()), "stream timeout", nullptr, absl::nullopt, StreamInfo::ResponseCodeDetails::get().StreamIdleTimeout); @@ -1942,7 +1942,8 @@ void ConnectionManagerImpl::ActiveStream::onResetStream(StreamResetReason reset_ // If the codec sets its responseDetails() for a reason other than peer reset, set a // DownstreamProtocolError. Either way, propagate details. if (!encoder_details.empty() && reset_reason == StreamResetReason::LocalReset) { - filter_manager_.streamInfo().setResponseFlag(StreamInfo::ResponseFlag::DownstreamProtocolError); + filter_manager_.streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::DownstreamProtocolError); } if (!encoder_details.empty()) { filter_manager_.streamInfo().setResponseCodeDetails(encoder_details); @@ -1951,7 +1952,7 @@ void ConnectionManagerImpl::ActiveStream::onResetStream(StreamResetReason reset_ // Check if we're in the overload manager reset case. // encoder_details should be empty in this case as we don't have a codec error. if (encoder_details.empty() && reset_reason == StreamResetReason::OverloadManager) { - filter_manager_.streamInfo().setResponseFlag(StreamInfo::ResponseFlag::OverloadManager); + filter_manager_.streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::OverloadManager); filter_manager_.streamInfo().setResponseCodeDetails( StreamInfo::ResponseCodeDetails::get().Overload); } diff --git a/source/common/http/conn_manager_impl.h b/source/common/http/conn_manager_impl.h index 9c97f9eb6350a..aac42af4b34a3 100644 --- a/source/common/http/conn_manager_impl.h +++ b/source/common/http/conn_manager_impl.h @@ -44,6 +44,7 @@ #include "source/common/http/user_agent.h" #include "source/common/http/utility.h" #include "source/common/local_reply/local_reply.h" +#include "source/common/network/common_connection_filter_states.h" #include "source/common/network/proxy_protocol_filter_state.h" #include "source/common/router/scoped_rds.h" #include "source/common/stream_info/stream_info_impl.h" @@ -180,6 +181,13 @@ class ConnectionManagerImpl : Logger::Loggable, public DownstreamStreamFilterCallbacks { ActiveStream(ConnectionManagerImpl& connection_manager, uint32_t buffer_limit, Buffer::BufferMemoryAccountSharedPtr account); + + // Event::DeferredDeletable + void deleteIsPending() override { + // The stream should not be accessed once deferred delete has been called. + still_alive_.reset(); + } + void completeRequest(); const Network::Connection* connection(); @@ -228,6 +236,10 @@ class ConnectionManagerImpl : Logger::Loggable, } // ScopeTrackedObject + ExecutionContext* executionContext() const override { + return getConnectionExecutionContext(connection_manager_.read_callbacks_->connection()); + } + void dumpState(std::ostream& os, int indent_level = 0) const override { const char* spaces = spacesForLevel(indent_level); os << spaces << "ActiveStream " << this << DUMP_MEMBER(stream_id_); @@ -575,7 +587,7 @@ class ConnectionManagerImpl : Logger::Loggable, */ void doEndStream(ActiveStream& stream, bool check_for_deferred_close = true); - void resetAllStreams(absl::optional response_flag, + void resetAllStreams(absl::optional response_flag, absl::string_view details); void onIdleTimeout(); void onConnectionDurationTimeout(); @@ -583,11 +595,11 @@ class ConnectionManagerImpl : Logger::Loggable, void startDrainSequence(); Tracing::Tracer& tracer() { return *config_.tracer(); } void handleCodecErrorImpl(absl::string_view error, absl::string_view details, - StreamInfo::ResponseFlag response_flag); + StreamInfo::CoreResponseFlag response_flag); void handleCodecError(absl::string_view error); void handleCodecOverloadError(absl::string_view error); void doConnectionClose(absl::optional close_type, - absl::optional response_flag, + absl::optional response_flag, absl::string_view details); // Returns true if a RST_STREAM for the given stream is premature. Premature // means the RST_STREAM arrived before response headers were sent and than diff --git a/source/common/http/conn_pool_grid.cc b/source/common/http/conn_pool_grid.cc index 3b031fb41fd03..ba51e7eee7e12 100644 --- a/source/common/http/conn_pool_grid.cc +++ b/source/common/http/conn_pool_grid.cc @@ -90,7 +90,7 @@ void ConnectivityGrid::WrapperCallbacks::onConnectionAttemptFailed( } // If the next connection attempt does not immediately fail, let it proceed. - if (tryAnotherConnection()) { + if (tryAnotherConnection().has_value()) { return; } @@ -189,19 +189,19 @@ void ConnectivityGrid::WrapperCallbacks::cancelAllPendingAttempts( connection_attempts_.clear(); } -bool ConnectivityGrid::WrapperCallbacks::tryAnotherConnection() { +absl::optional +ConnectivityGrid::WrapperCallbacks::tryAnotherConnection() { absl::optional next_pool = grid_.nextPool(current_); if (!next_pool.has_value()) { - // If there are no other pools to try, return false. - return false; + // If there are no other pools to try, return an empty optional. + return {}; } // Create a new connection attempt for the next pool. If we reach this point // return true regardless of if newStream resulted in an immediate result or // an async call, as either way the attempt will result in success/failure // callbacks. current_ = next_pool.value(); - newStream(); - return true; + return newStream(); } ConnectivityGrid::ConnectivityGrid( @@ -213,15 +213,15 @@ ConnectivityGrid::ConnectivityGrid( HttpServerPropertiesCacheSharedPtr alternate_protocols, ConnectivityOptions connectivity_options, Quic::QuicStatNames& quic_stat_names, Stats::Scope& scope, Http::PersistentQuicInfo& quic_info) - : dispatcher_(dispatcher), random_generator_(random_generator), host_(host), - priority_(priority), options_(options), transport_socket_options_(transport_socket_options), - state_(state), next_attempt_duration_(std::chrono::milliseconds(kDefaultTimeoutMs)), + : dispatcher_(dispatcher), random_generator_(random_generator), host_(host), options_(options), + transport_socket_options_(transport_socket_options), state_(state), + next_attempt_duration_(std::chrono::milliseconds(kDefaultTimeoutMs)), time_source_(time_source), alternate_protocols_(alternate_protocols), quic_stat_names_(quic_stat_names), scope_(scope), // TODO(RyanTheOptimist): Figure out how scheme gets plumbed in here. origin_("https", getSni(transport_socket_options, host_->transportSocketFactory()), host_->address()->ip()->port()), - quic_info_(quic_info) { + quic_info_(quic_info), priority_(priority) { // ProdClusterManagerFactory::allocateConnPool verifies the protocols are HTTP/1, HTTP/2 and // HTTP/3. ASSERT(connectivity_options.protocols_.size() == 3); @@ -327,7 +327,12 @@ ConnectionPool::Cancellable* ConnectivityGrid::newStream(Http::ResponseDecoder& } if (!delay_tcp_attempt) { // Immediately start TCP attempt if HTTP/3 failed recently. - wrapped_callbacks_.front()->tryAnotherConnection(); + absl::optional result = + wrapped_callbacks_.front()->tryAnotherConnection(); + if (result.has_value() && result.value() == StreamCreationResult::ImmediateResult) { + // As above, if we have an immediate success, return nullptr. + return nullptr; + } } return ret; } diff --git a/source/common/http/conn_pool_grid.h b/source/common/http/conn_pool_grid.h index feaa9ac8963c8..b5b9bb059662a 100644 --- a/source/common/http/conn_pool_grid.h +++ b/source/common/http/conn_pool_grid.h @@ -80,9 +80,9 @@ class ConnectivityGrid : public ConnectionPool::Instance, StreamCreationResult newStream(); // Called on pool failure or timeout to kick off another connection attempt. - // Returns true if there is a failover pool and a connection has been - // attempted, false if all pools have been tried. - bool tryAnotherConnection(); + // Returns the StreamCreationResult if there is a failover pool and a + // connection has been attempted, an empty optional otherwise. + absl::optional tryAnotherConnection(); // Called by a ConnectionAttempt when the underlying pool fails. void onConnectionAttemptFailed(ConnectionAttemptCallbacks* attempt, @@ -205,7 +205,6 @@ class ConnectivityGrid : public ConnectionPool::Instance, Event::Dispatcher& dispatcher_; Random::RandomGenerator& random_generator_; Upstream::HostConstSharedPtr host_; - Upstream::ResourcePriority priority_; const Network::ConnectionSocket::OptionsSharedPtr options_; const Network::TransportSocketOptionsConstSharedPtr transport_socket_options_; Upstream::ClusterConnectivityState& state_; @@ -213,10 +212,6 @@ class ConnectivityGrid : public ConnectionPool::Instance, TimeSource& time_source_; HttpServerPropertiesCacheSharedPtr alternate_protocols_; - // True iff this pool is draining. No new streams or connections should be created - // in this state. - bool draining_{false}; - // Tracks the callbacks to be called on drain completion. std::list idle_callbacks_; @@ -224,23 +219,31 @@ class ConnectivityGrid : public ConnectionPool::Instance, // desired use. std::list pools_; - // True iff under the stack of the destructor, to avoid calling drain - // callbacks on deletion. - bool destroying_{}; - - // True iff this pool is being being defer deleted. - bool deferred_deleting_{}; - // Wrapped callbacks are stashed in the wrapped_callbacks_ for ownership. std::list wrapped_callbacks_; Quic::QuicStatNames& quic_stat_names_; + Stats::Scope& scope_; + // The origin for this pool. // Note the host name here is based off of the host name used for SNI, which // may be from the cluster config, or the request headers for auto-sni. HttpServerPropertiesCache::Origin origin_; + Http::PersistentQuicInfo& quic_info_; + Upstream::ResourcePriority priority_; + + // True iff this pool is draining. No new streams or connections should be created + // in this state. + bool draining_{false}; + + // True iff under the stack of the destructor, to avoid calling drain + // callbacks on deletion. + bool destroying_{}; + + // True iff this pool is being deferred deleted. + bool deferred_deleting_{}; }; } // namespace Http diff --git a/source/common/http/date_provider_impl.h b/source/common/http/date_provider_impl.h index a4adf4b87d87f..ae61e984bfc5c 100644 --- a/source/common/http/date_provider_impl.h +++ b/source/common/http/date_provider_impl.h @@ -8,8 +8,7 @@ #include "envoy/thread_local/thread_local.h" #include "source/common/common/utility.h" - -#include "date_provider.h" +#include "source/common/http/date_provider.h" namespace Envoy { namespace Http { diff --git a/source/common/http/filter_chain_helper.h b/source/common/http/filter_chain_helper.h index 39d6ce6dd6afd..51852499317c2 100644 --- a/source/common/http/filter_chain_helper.h +++ b/source/common/http/filter_chain_helper.h @@ -26,7 +26,8 @@ using UpstreamFilterConfigProviderManager = class MissingConfigFilter : public Http::PassThroughDecoderFilter { public: Http::FilterHeadersStatus decodeHeaders(Http::RequestHeaderMap&, bool) override { - decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoFilterConfigFound); + decoder_callbacks_->streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::NoFilterConfigFound); decoder_callbacks_->sendLocalReply(Http::Code::InternalServerError, EMPTY_STRING, nullptr, absl::nullopt, EMPTY_STRING); return Http::FilterHeadersStatus::StopIteration; diff --git a/source/common/http/http1/BUILD b/source/common/http/http1/BUILD index bdd794dc0723d..b2d52f504d660 100644 --- a/source/common/http/http1/BUILD +++ b/source/common/http/http1/BUILD @@ -60,6 +60,7 @@ envoy_cc_library( "//source/common/http:headers_lib", "//source/common/http:status_lib", "//source/common/http:utility_lib", + "//source/common/network:common_connection_filter_states_lib", "//source/common/runtime:runtime_features_lib", "@envoy_api//envoy/config/core/v3:pkg_cc_proto", ], diff --git a/source/common/http/http1/codec_impl.cc b/source/common/http/http1/codec_impl.cc index c0c5f9a1599bb..fcd62e1150245 100644 --- a/source/common/http/http1/codec_impl.cc +++ b/source/common/http/http1/codec_impl.cc @@ -24,6 +24,7 @@ #include "source/common/http/http1/header_formatter.h" #include "source/common/http/http1/legacy_parser_impl.h" #include "source/common/http/utility.h" +#include "source/common/network/common_connection_filter_states.h" #include "source/common/runtime/runtime_features.h" #include "absl/container/fixed_array.h" @@ -130,11 +131,8 @@ void StreamEncoderImpl::encodeFormattedHeader(absl::string_view key, absl::strin void ResponseEncoderImpl::encode1xxHeaders(const ResponseHeaderMap& headers) { ASSERT(HeaderUtility::isSpecial1xx(headers)); encodeHeaders(headers, false); - if (Runtime::runtimeFeatureEnabled( - "envoy.reloadable_features.http1_allow_codec_error_response_after_1xx_headers")) { - // Don't consider 100-continue responses as the actual response. - started_response_ = false; - } + // Don't consider 100-continue responses as the actual response. + started_response_ = false; } void StreamEncoderImpl::encodeHeadersBase(const RequestOrResponseHeaderMap& headers, @@ -978,6 +976,10 @@ void ConnectionImpl::onResetStreamBase(StreamResetReason reason) { onResetStream(reason); } +ExecutionContext* ConnectionImpl::executionContext() const { + return getConnectionExecutionContext(connection_); +} + void ConnectionImpl::dumpState(std::ostream& os, int indent_level) const { const char* spaces = spacesForLevel(indent_level); os << spaces << "Http1::ConnectionImpl " << this << DUMP_MEMBER(dispatching_) @@ -1140,12 +1142,7 @@ Status ServerConnectionImpl::handlePath(RequestHeaderMap& headers, absl::string_ // Add the scheme and validate to ensure no https:// // requests are accepted over unencrypted connections by front-line Envoys. if (!is_connect) { - if (Runtime::runtimeFeatureEnabled( - "envoy.reloadable_features.allow_absolute_url_with_mixed_scheme")) { - headers.setScheme(absl::AsciiStrToLower(absolute_url.scheme())); - } else { - headers.setScheme(absolute_url.scheme()); - } + headers.setScheme(absl::AsciiStrToLower(absolute_url.scheme())); if (!Utility::schemeIsValid(headers.getSchemeValue())) { RETURN_IF_ERROR(sendProtocolError(Http1ResponseCodeDetails::get().InvalidScheme)); return codecProtocolError("http/1.1 protocol error: invalid scheme"); diff --git a/source/common/http/http1/codec_impl.h b/source/common/http/http1/codec_impl.h index b59e1931a7855..59ba6bfd8e996 100644 --- a/source/common/http/http1/codec_impl.h +++ b/source/common/http/http1/codec_impl.h @@ -272,6 +272,7 @@ class ConnectionImpl : public virtual Connection, Envoy::Http::Status codec_status_; // ScopeTrackedObject + ExecutionContext* executionContext() const override; void dumpState(std::ostream& os, int indent_level) const override; protected: diff --git a/source/common/http/http2/BUILD b/source/common/http/http2/BUILD index ffcdfabf6687f..89f6a87f93454 100644 --- a/source/common/http/http2/BUILD +++ b/source/common/http/http2/BUILD @@ -59,6 +59,7 @@ envoy_cc_library( "//source/common/http:headers_lib", "//source/common/http:status_lib", "//source/common/http:utility_lib", + "//source/common/network:common_connection_filter_states_lib", "//source/common/runtime:runtime_features_lib", "@envoy_api//envoy/config/core/v3:pkg_cc_proto", ], diff --git a/source/common/http/http2/codec_impl.cc b/source/common/http/http2/codec_impl.cc index fb2963d6076ae..aa9a75b8216de 100644 --- a/source/common/http/http2/codec_impl.cc +++ b/source/common/http/http2/codec_impl.cc @@ -25,6 +25,7 @@ #include "source/common/http/headers.h" #include "source/common/http/http2/codec_stats.h" #include "source/common/http/utility.h" +#include "source/common/network/common_connection_filter_states.h" #include "source/common/runtime/runtime_features.h" #include "absl/cleanup/cleanup.h" @@ -86,10 +87,11 @@ int reasonToReset(StreamResetReason reason) { using Http2ResponseCodeDetails = ConstSingleton; -ReceivedSettingsImpl::ReceivedSettingsImpl(const nghttp2_settings& settings) { - for (uint32_t i = 0; i < settings.niv; ++i) { - if (settings.iv[i].settings_id == NGHTTP2_SETTINGS_MAX_CONCURRENT_STREAMS) { - concurrent_stream_limit_ = settings.iv[i].value; +ReceivedSettingsImpl::ReceivedSettingsImpl( + absl::Span settings) { + for (const auto& [id, value] : settings) { + if (id == NGHTTP2_SETTINGS_MAX_CONCURRENT_STREAMS) { + concurrent_stream_limit_ = value; break; } } @@ -200,30 +202,6 @@ void ConnectionImpl::ServerStreamImpl::destroy() { StreamImpl::destroy(); } -static void insertHeader(std::vector& headers, const HeaderEntry& header) { - uint8_t flags = 0; - if (header.key().isReference()) { - flags |= NGHTTP2_NV_FLAG_NO_COPY_NAME; - } - if (header.value().isReference()) { - flags |= NGHTTP2_NV_FLAG_NO_COPY_VALUE; - } - const absl::string_view header_key = header.key().getStringView(); - const absl::string_view header_value = header.value().getStringView(); - headers.push_back({removeConst(header_key.data()), - removeConst(header_value.data()), header_key.size(), - header_value.size(), flags}); -} - -void ConnectionImpl::StreamImpl::buildHeaders(std::vector& final_headers, - const HeaderMap& headers) { - final_headers.reserve(headers.size()); - headers.iterate([&final_headers](const HeaderEntry& header) -> HeaderMap::Iterate { - insertHeader(final_headers, header); - return HeaderMap::Iterate::Continue; - }); -} - http2::adapter::HeaderRep getRep(const HeaderString& str) { if (str.isReference()) { return str.getStringView(); @@ -698,6 +676,20 @@ void ConnectionImpl::ClientStreamImpl::submitHeaders(const HeaderMap& headers, b ASSERT(stream_id_ > 0); } +Status ConnectionImpl::ClientStreamImpl::onBeginHeaders() { + if (headers_state_ == HeadersState::Headers) { + allocTrailers(); + } + + return okStatus(); +} + +void ConnectionImpl::ClientStreamImpl::advanceHeadersState() { + RELEASE_ASSERT( + headers_state_ == HeadersState::Response || headers_state_ == HeadersState::Headers, ""); + headers_state_ = HeadersState::Headers; +} + void ConnectionImpl::ServerStreamImpl::submitHeaders(const HeaderMap& headers, bool end_stream) { ASSERT(stream_id_ != -1); parent_.adapter_->SubmitResponse(stream_id_, buildHeaders(headers), @@ -705,6 +697,23 @@ void ConnectionImpl::ServerStreamImpl::submitHeaders(const HeaderMap& headers, b : std::make_unique(*this)); } +Status ConnectionImpl::ServerStreamImpl::onBeginHeaders() { + if (headers_state_ != HeadersState::Request) { + parent_.stats_.trailers_.inc(); + ASSERT(headers_state_ == HeadersState::Headers); + + allocTrailers(); + } + + return okStatus(); +} + +void ConnectionImpl::ServerStreamImpl::advanceHeadersState() { + RELEASE_ASSERT(headers_state_ == HeadersState::Request || headers_state_ == HeadersState::Headers, + ""); + headers_state_ = HeadersState::Headers; +} + void ConnectionImpl::StreamImpl::onPendingFlushTimer() { ENVOY_CONN_LOG(debug, "pending stream flush timeout", parent_.connection_); MultiplexedStreamImplBase::onPendingFlushTimer(); @@ -1063,11 +1072,24 @@ Status ConnectionImpl::onBeforeFrameReceived(int32_t stream_id, size_t length, u ASSERT(connection_.state() == Network::Connection::State::Open); current_stream_id_ = stream_id; + if (type == NGHTTP2_PING && (flags & NGHTTP2_FLAG_ACK)) { + return okStatus(); + } + + // In slow networks, HOL blocking can prevent the ping response from coming in a reasonable + // amount of time. To avoid HOL blocking influence, if we receive *any* frame extend the + // timeout for another timeout period. This will still timeout the connection if there is no + // activity, but if there is frame activity we assume the connection is still healthy and the + // PING ACK may be delayed behind other frames. + if (keepalive_timeout_timer_ != nullptr && keepalive_timeout_timer_->enabled()) { + keepalive_timeout_timer_->enableTimer(keepalive_timeout_); + } + // Track all the frames without padding here, since this is the only callback we receive // for some of them (e.g. CONTINUATION frame, frames sent on closed streams, etc.). - // HEADERS frame is tracked in onBeginHeaders(), DATA frame is tracked in onFrameReceived(). + // DATA frame is tracked in onFrameReceived(). auto status = okStatus(); - if (type != NGHTTP2_HEADERS && type != NGHTTP2_DATA) { + if (type != NGHTTP2_DATA) { status = trackInboundFrames(stream_id, length, type, flags, 0); } @@ -1084,116 +1106,151 @@ enum GoAwayErrorCode ngHttp2ErrorCodeToErrorCode(uint32_t code) noexcept { } } -Status ConnectionImpl::onFrameReceived(const nghttp2_frame* frame) { - ENVOY_CONN_LOG(trace, "recv frame type={}", connection_, static_cast(frame->hd.type)); - ASSERT(connection_.state() == Network::Connection::State::Open); +Status ConnectionImpl::onPing(uint64_t opaque_data, bool is_ack) { + if (is_ack) { + ENVOY_CONN_LOG(trace, "recv PING ACK {}", connection_, opaque_data); - // onFrameReceived() is called with a complete HEADERS frame assembled from all the HEADERS - // and CONTINUATION frames, but we track them separately: HEADERS frames in onBeginHeaders() - // and CONTINUATION frames in onBeforeFrameReceived(). - ASSERT(frame->hd.type != NGHTTP2_CONTINUATION); + onKeepaliveResponse(); + } + return okStatus(); +} - if ((frame->hd.type == NGHTTP2_PING) && (frame->ping.hd.flags & NGHTTP2_FLAG_ACK)) { - // The ``opaque_data`` should be exactly what was sent in the ping, which is - // was the current time when the ping was sent. This can be useful while debugging - // to match the ping and ack. - uint64_t data; - safeMemcpy(&data, &(frame->ping.opaque_data)); - ENVOY_CONN_LOG(trace, "recv PING ACK {}", connection_, data); +Status ConnectionImpl::onBeginData(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, + size_t padding) { + RETURN_IF_ERROR(trackInboundFrames(stream_id, length, type, flags, padding)); - onKeepaliveResponse(); + StreamImpl* stream = getStreamUnchecked(stream_id); + if (!stream) { return okStatus(); } - // In slow networks, HOL blocking can prevent the ping response from coming in a reasonable - // amount of time. To avoid HOL blocking influence, if we receive *any* frame extend the - // timeout for another timeout period. This will still timeout the connection if there is no - // activity, but if there is frame activity we assume the connection is still healthy and the - // PING ACK may be delayed behind other frames. - if (keepalive_timeout_timer_ != nullptr && keepalive_timeout_timer_->enabled()) { - keepalive_timeout_timer_->enableTimer(keepalive_timeout_); - } + // Track bytes received. + stream->bytes_meter_->addWireBytesReceived(length + H2_FRAME_HEADER_SIZE); - if (frame->hd.type == NGHTTP2_DATA) { - RETURN_IF_ERROR(trackInboundFrames(frame->hd.stream_id, frame->hd.length, frame->hd.type, - frame->hd.flags, frame->data.padlen)); - } + stream->remote_end_stream_ = flags & NGHTTP2_FLAG_END_STREAM; + stream->decodeData(); + return okStatus(); +} +Status ConnectionImpl::onGoAway(uint32_t error_code) { // Only raise GOAWAY once, since we don't currently expose stream information. Shutdown // notifications are the same as a normal GOAWAY. // TODO: handle multiple GOAWAY frames. - if (frame->hd.type == NGHTTP2_GOAWAY && !raised_goaway_) { - ASSERT(frame->hd.stream_id == 0); + if (!raised_goaway_) { raised_goaway_ = true; - callbacks().onGoAway(ngHttp2ErrorCodeToErrorCode(frame->goaway.error_code)); - return okStatus(); - } - - if (frame->hd.type == NGHTTP2_SETTINGS && frame->hd.flags == NGHTTP2_FLAG_NONE) { - onSettings(frame->settings); + callbacks().onGoAway(ngHttp2ErrorCodeToErrorCode(error_code)); } + return okStatus(); +} - StreamImpl* stream = getStreamUnchecked(frame->hd.stream_id); +Status ConnectionImpl::onHeaders(int32_t stream_id, size_t length, uint8_t flags) { + StreamImpl* stream = getStreamUnchecked(stream_id); if (!stream) { return okStatus(); } + // Track bytes received. + stream->bytes_meter_->addWireBytesReceived(length + H2_FRAME_HEADER_SIZE); + stream->bytes_meter_->addHeaderBytesReceived(length + H2_FRAME_HEADER_SIZE); - // Track bytes sent and received. - if (frame->hd.type != METADATA_FRAME_TYPE) { - stream->bytes_meter_->addWireBytesReceived(frame->hd.length + H2_FRAME_HEADER_SIZE); + stream->remote_end_stream_ = flags & NGHTTP2_FLAG_END_STREAM; + if (!stream->cookies_.empty()) { + HeaderString key(Headers::get().Cookie); + stream->headers().addViaMove(std::move(key), std::move(stream->cookies_)); } - if (frame->hd.type == NGHTTP2_HEADERS || frame->hd.type == NGHTTP2_CONTINUATION) { - stream->bytes_meter_->addHeaderBytesReceived(frame->hd.length + H2_FRAME_HEADER_SIZE); + + StreamImpl::HeadersState headers_state = stream->headersState(); + switch (headers_state) { + case StreamImpl::HeadersState::Response: + case StreamImpl::HeadersState::Request: { + stream->decodeHeaders(); + break; } - switch (frame->hd.type) { - case NGHTTP2_HEADERS: { - stream->remote_end_stream_ = frame->hd.flags & NGHTTP2_FLAG_END_STREAM; - if (!stream->cookies_.empty()) { - HeaderString key(Headers::get().Cookie); - stream->headers().addViaMove(std::move(key), std::move(stream->cookies_)); + case StreamImpl::HeadersState::Headers: { + // It's possible that we are waiting to send a deferred reset, so only raise headers/trailers + // if local is not complete. + if (!stream->deferred_reset_) { + if (adapter_->IsServerSession() || stream->received_noninformational_headers_) { + ASSERT(stream->remote_end_stream_); + stream->decodeTrailers(); + } else { + // We're a client session and still waiting for non-informational headers. + stream->decodeHeaders(); + } } + break; + } - switch (frame->headers.cat) { - case NGHTTP2_HCAT_RESPONSE: - case NGHTTP2_HCAT_REQUEST: { - stream->decodeHeaders(); - break; - } + default: + // We do not currently support push. + ENVOY_BUG(false, "push not supported"); + } - case NGHTTP2_HCAT_HEADERS: { - // It's possible that we are waiting to send a deferred reset, so only raise headers/trailers - // if local is not complete. - if (!stream->deferred_reset_) { - if (adapter_->IsServerSession() || stream->received_noninformational_headers_) { - ASSERT(stream->remote_end_stream_); - stream->decodeTrailers(); - } else { - // We're a client session and still waiting for non-informational headers. - stream->decodeHeaders(); - } - } - break; - } + stream->advanceHeadersState(); + return okStatus(); +} - default: - // We do not currently support push. - ENVOY_BUG(false, "push not supported"); - } +Status ConnectionImpl::onRstStream(int32_t stream_id, uint32_t error_code) { + ENVOY_CONN_LOG(trace, "remote reset: {} {}", connection_, stream_id, error_code); + StreamImpl* stream = getStreamUnchecked(stream_id); + if (!stream) { + return okStatus(); + } + // Track bytes received. + stream->bytes_meter_->addWireBytesReceived(/*frame_length=*/4 + H2_FRAME_HEADER_SIZE); + stream->remote_rst_ = true; + stats_.rx_reset_.inc(); + return okStatus(); +} - break; +Status ConnectionImpl::onFrameReceived(const nghttp2_frame* frame) { + ENVOY_CONN_LOG(trace, "recv frame type={}", connection_, static_cast(frame->hd.type)); + ASSERT(connection_.state() == Network::Connection::State::Open); + + // onFrameReceived() is called with a complete HEADERS frame assembled from all the HEADERS + // and CONTINUATION frames, but we track them separately: HEADERS frames in onBeginHeaders() + // and CONTINUATION frames in onBeforeFrameReceived(). + ASSERT(frame->hd.type != NGHTTP2_CONTINUATION); + + if (frame->hd.type == NGHTTP2_PING) { + // The ``opaque_data`` should be exactly what was sent in the ping, which is + // was the current time when the ping was sent. This can be useful while debugging + // to match the ping and ack. + uint64_t data; + safeMemcpy(&data, &(frame->ping.opaque_data)); + return onPing(data, frame->ping.hd.flags & NGHTTP2_FLAG_ACK); } - case NGHTTP2_DATA: { - stream->remote_end_stream_ = frame->hd.flags & NGHTTP2_FLAG_END_STREAM; - stream->decodeData(); - break; + if (frame->hd.type == NGHTTP2_DATA) { + return onBeginData(frame->hd.stream_id, frame->hd.length, frame->hd.type, frame->hd.flags, + frame->data.padlen); } - case NGHTTP2_RST_STREAM: { - ENVOY_CONN_LOG(trace, "remote reset: {}", connection_, frame->rst_stream.error_code); - stream->remote_rst_ = true; - stats_.rx_reset_.inc(); - break; + if (frame->hd.type == NGHTTP2_GOAWAY) { + ASSERT(frame->hd.stream_id == 0); + return onGoAway(frame->goaway.error_code); + } + if (frame->hd.type == NGHTTP2_SETTINGS) { + if (frame->hd.flags == NGHTTP2_FLAG_NONE) { + std::vector settings; + settings.reserve(frame->settings.niv); + for (const nghttp2_settings_entry& entry : + absl::MakeSpan(frame->settings.iv, frame->settings.niv)) { + settings.push_back( + {static_cast(entry.settings_id), entry.value}); + } + onSettings(settings); + } + return okStatus(); + } + if (frame->hd.type == NGHTTP2_HEADERS) { + return onHeaders(frame->hd.stream_id, frame->hd.length, frame->hd.flags); } + if (frame->hd.type == NGHTTP2_RST_STREAM) { + return onRstStream(frame->hd.stream_id, frame->rst_stream.error_code); + } + StreamImpl* stream = getStreamUnchecked(frame->hd.stream_id); + if (stream != nullptr && frame->hd.type != METADATA_FRAME_TYPE) { + // Track bytes received. + stream->bytes_meter_->addWireBytesReceived(frame->hd.length + H2_FRAME_HEADER_SIZE); } return okStatus(); @@ -1334,6 +1391,32 @@ void ConnectionImpl::addOutboundFrameFragment(Buffer::OwnedImpl& output, const u output.addDrainTracker(releasor); } +Status ConnectionImpl::trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, + uint8_t flags, uint32_t padding_length) { + Status result; + ENVOY_CONN_LOG(trace, "track inbound frame type={} flags={} length={} padding_length={}", + connection_, static_cast(type), static_cast(flags), + static_cast(length), padding_length); + + const bool end_stream = + (type == NGHTTP2_DATA || type == NGHTTP2_HEADERS) && (flags & NGHTTP2_FLAG_END_STREAM); + const bool is_empty = (length - padding_length) == 0; + result = protocol_constraints_.trackInboundFrame(type, end_stream, is_empty); + if (!result.ok()) { + ENVOY_CONN_LOG(trace, "error reading frame: {} received in this HTTP/2 session.", connection_, + result.message()); + if (isInboundFramesWithEmptyPayloadError(result)) { + ConnectionImpl::StreamImpl* stream = getStreamUnchecked(stream_id); + if (stream) { + stream->setDetails(Http2ResponseCodeDetails::get().inbound_empty_frame_flood); + } + // Above if is defensive, because the stream has just been created and therefore always + // exists. + } + } + return result; +} + ssize_t ConnectionImpl::onSend(const uint8_t* data, size_t length) { ENVOY_CONN_LOG(trace, "send data: bytes={}", connection_, length); Buffer::OwnedImpl buffer; @@ -1470,9 +1553,8 @@ int ConnectionImpl::onMetadataFrameComplete(int32_t stream_id, bool end_metadata return result ? 0 : NGHTTP2_ERR_CALLBACK_FAILURE; } -int ConnectionImpl::saveHeader(const nghttp2_frame* frame, HeaderString&& name, - HeaderString&& value) { - StreamImpl* stream = getStreamUnchecked(frame->hd.stream_id); +int ConnectionImpl::saveHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value) { + StreamImpl* stream = getStreamUnchecked(stream_id); if (!stream) { // We have seen 1 or 2 crashes where we get a headers callback but there is no associated // stream data. I honestly am not sure how this can happen. However, from reading the nghttp2 @@ -1670,7 +1752,7 @@ ConnectionImpl::Http2Callbacks::Http2Callbacks() { nghttp2_session_callbacks_set_on_begin_headers_callback( callbacks_, [](nghttp2_session*, const nghttp2_frame* frame, void* user_data) -> int { - auto status = static_cast(user_data)->onBeginHeaders(frame); + auto status = static_cast(user_data)->onBeginHeaders(frame->hd.stream_id); return static_cast(user_data)->setAndCheckCodecCallbackStatus( std::move(status)); }); @@ -1684,8 +1766,8 @@ ConnectionImpl::Http2Callbacks::Http2Callbacks() { name.setCopy(reinterpret_cast(raw_name), name_length); HeaderString value; value.setCopy(reinterpret_cast(raw_value), value_length); - return static_cast(user_data)->onHeader(frame, std::move(name), - std::move(value)); + return static_cast(user_data)->onHeader(frame->hd.stream_id, + std::move(name), std::move(value)); }); nghttp2_session_callbacks_set_on_data_chunk_recv_callback( @@ -1844,6 +1926,10 @@ ConnectionImpl::ClientHttp2Options::ClientHttp2Options( options_, ::Envoy::Http2::Utility::OptionsLimits::DEFAULT_MAX_CONCURRENT_STREAMS); } +ExecutionContext* ConnectionImpl::executionContext() const { + return getConnectionExecutionContext(connection_); +} + void ConnectionImpl::dumpState(std::ostream& os, int indent_level) const { const char* spaces = spacesForLevel(indent_level); os << spaces << "Http2::ConnectionImpl " << this << DUMP_MEMBER(max_headers_kb_) @@ -2004,57 +2090,18 @@ RequestEncoder& ClientConnectionImpl::newStream(ResponseDecoder& decoder) { return stream_ref; } -Status ClientConnectionImpl::onBeginHeaders(const nghttp2_frame* frame) { - // The client code explicitly does not currently support push promise. - RELEASE_ASSERT(frame->hd.type == NGHTTP2_HEADERS, ""); - RELEASE_ASSERT(frame->headers.cat == NGHTTP2_HCAT_RESPONSE || - frame->headers.cat == NGHTTP2_HCAT_HEADERS, - ""); - RETURN_IF_ERROR(trackInboundFrames(frame->hd.stream_id, frame->hd.length, frame->hd.type, - frame->hd.flags, frame->headers.padlen)); - if (frame->headers.cat == NGHTTP2_HCAT_HEADERS) { - StreamImpl* stream = getStream(frame->hd.stream_id); - stream->allocTrailers(); - } - - return okStatus(); +Status ClientConnectionImpl::onBeginHeaders(int32_t stream_id) { + StreamImpl* stream = getStream(stream_id); + return stream->onBeginHeaders(); } -int ClientConnectionImpl::onHeader(const nghttp2_frame* frame, HeaderString&& name, - HeaderString&& value) { - // The client code explicitly does not currently support push promise. - ASSERT(frame->hd.type == NGHTTP2_HEADERS); - ASSERT(frame->headers.cat == NGHTTP2_HCAT_RESPONSE || frame->headers.cat == NGHTTP2_HCAT_HEADERS); +int ClientConnectionImpl::onHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value) { ASSERT(connection_.state() == Network::Connection::State::Open); - return saveHeader(frame, std::move(name), std::move(value)); -} - -// TODO(yanavlasov): move to the base class once the runtime flag is removed. -Status ClientConnectionImpl::trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, - uint8_t flags, uint32_t padding_length) { - Status result; - ENVOY_CONN_LOG(trace, "track inbound frame type={} flags={} length={} padding_length={}", - connection_, static_cast(type), static_cast(flags), - static_cast(length), padding_length); - - result = protocol_constraints_.trackInboundFrames(length, type, flags, padding_length); - if (!result.ok()) { - ENVOY_CONN_LOG(trace, "error reading frame: {} received in this HTTP/2 session.", connection_, - result.message()); - if (isInboundFramesWithEmptyPayloadError(result)) { - ConnectionImpl::StreamImpl* stream = getStreamUnchecked(stream_id); - if (stream) { - stream->setDetails(Http2ResponseCodeDetails::get().inbound_empty_frame_flood); - } - // Above if is defensive, because the stream has just been created and therefore always - // exists. - } - } - return result; + return saveHeader(stream_id, std::move(name), std::move(value)); } StreamResetReason ClientConnectionImpl::getMessagingErrorResetReason() const { - connection_.streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamProtocolError); + connection_.streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamProtocolError); return StreamResetReason::ProtocolError; } @@ -2096,41 +2143,28 @@ ServerConnectionImpl::ServerConnectionImpl( allow_metadata_ = http2_options.allow_metadata(); } -Status ServerConnectionImpl::onBeginHeaders(const nghttp2_frame* frame) { - // For a server connection, we should never get push promise frames. - ASSERT(frame->hd.type == NGHTTP2_HEADERS); +Status ServerConnectionImpl::onBeginHeaders(int32_t stream_id) { ASSERT(connection_.state() == Network::Connection::State::Open); - RETURN_IF_ERROR(trackInboundFrames(frame->hd.stream_id, frame->hd.length, frame->hd.type, - frame->hd.flags, frame->headers.padlen)); - if (frame->headers.cat != NGHTTP2_HCAT_REQUEST) { - stats_.trailers_.inc(); - ASSERT(frame->headers.cat == NGHTTP2_HCAT_HEADERS); - - StreamImpl* stream = getStream(frame->hd.stream_id); - stream->allocTrailers(); - return okStatus(); + StreamImpl* stream_ptr = getStream(stream_id); + if (stream_ptr != nullptr) { + return stream_ptr->onBeginHeaders(); } - ServerStreamImplPtr stream(new ServerStreamImpl(*this, per_stream_buffer_limit_)); if (connection_.aboveHighWatermark()) { stream->runHighWatermarkCallbacks(); } stream->setRequestDecoder(callbacks_.newStream(*stream)); - stream->stream_id_ = frame->hd.stream_id; + stream->stream_id_ = stream_id; LinkedList::moveIntoList(std::move(stream), active_streams_); - adapter_->SetStreamUserData(frame->hd.stream_id, active_streams_.front().get()); + adapter_->SetStreamUserData(stream_id, active_streams_.front().get()); protocol_constraints_.incrementOpenedStreamCount(); - return okStatus(); + return active_streams_.front()->onBeginHeaders(); } -int ServerConnectionImpl::onHeader(const nghttp2_frame* frame, HeaderString&& name, - HeaderString&& value) { - // For a server connection, we should never get push promise frames. - ASSERT(frame->hd.type == NGHTTP2_HEADERS); - ASSERT(frame->headers.cat == NGHTTP2_HCAT_REQUEST || frame->headers.cat == NGHTTP2_HCAT_HEADERS); +int ServerConnectionImpl::onHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value) { if (Runtime::runtimeFeatureEnabled("envoy.reloadable_features.http2_discard_host_header")) { - StreamImpl* stream = getStreamUnchecked(frame->hd.stream_id); + StreamImpl* stream = getStreamUnchecked(stream_id); if (stream && name == static_cast(Http::Headers::get().HostLegacy)) { // Check if there is already the :authority header const auto result = stream->headers().get(Http::Headers::get().Host); @@ -2141,29 +2175,7 @@ int ServerConnectionImpl::onHeader(const nghttp2_frame* frame, HeaderString&& na // Otherwise use host value as :authority } } - return saveHeader(frame, std::move(name), std::move(value)); -} - -Status ServerConnectionImpl::trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, - uint8_t flags, uint32_t padding_length) { - ENVOY_CONN_LOG(trace, "track inbound frame type={} flags={} length={} padding_length={}", - connection_, static_cast(type), static_cast(flags), - static_cast(length), padding_length); - - auto result = protocol_constraints_.trackInboundFrames(length, type, flags, padding_length); - if (!result.ok()) { - ENVOY_CONN_LOG(trace, "error reading frame: {} received in this HTTP/2 session.", connection_, - result.message()); - if (isInboundFramesWithEmptyPayloadError(result)) { - ConnectionImpl::StreamImpl* stream = getStreamUnchecked(stream_id); - if (stream) { - stream->setDetails(Http2ResponseCodeDetails::get().inbound_empty_frame_flood); - } - // Above if is defensive, because the stream has just been created and therefore always - // exists. - } - } - return result; + return saveHeader(stream_id, std::move(name), std::move(value)); } Http::Status ServerConnectionImpl::dispatch(Buffer::Instance& data) { diff --git a/source/common/http/http2/codec_impl.h b/source/common/http/http2/codec_impl.h index 042ecf03dff09..5e75729703785 100644 --- a/source/common/http/http2/codec_impl.h +++ b/source/common/http/http2/codec_impl.h @@ -33,8 +33,10 @@ #include "source/common/http/utility.h" #include "absl/types/optional.h" +#include "absl/types/span.h" #include "nghttp2/nghttp2.h" #include "quiche/http2/adapter/http2_adapter.h" +#include "quiche/http2/adapter/http2_protocol.h" #include "quiche/http2/adapter/oghttp2_adapter.h" namespace Envoy { @@ -50,7 +52,7 @@ constexpr uint64_t H2_FRAME_HEADER_SIZE = 9; class ReceivedSettingsImpl : public ReceivedSettings { public: - explicit ReceivedSettingsImpl(const nghttp2_settings& settings); + explicit ReceivedSettingsImpl(absl::Span settings); // ReceivedSettings const absl::optional& maxConcurrentStreams() const override { @@ -154,6 +156,7 @@ class ConnectionImpl : public virtual Connection, } // ScopeTrackedObject + ExecutionContext* executionContext() const override; void dumpState(std::ostream& os, int indent_level) const override; protected: @@ -204,6 +207,11 @@ class ConnectionImpl : public virtual Connection, public Event::DeferredDeletable, public Http::MultiplexedStreamImplBase, public ScopeTrackedObject { + enum class HeadersState { + Request, + Response, + Headers, // Signifies additional headers after the initial request/response set. + }; StreamImpl(ConnectionImpl& parent, uint32_t buffer_limit); @@ -218,8 +226,10 @@ class ConnectionImpl : public virtual Connection, StreamImpl* base() { return this; } void resetStreamWorker(StreamResetReason reason); - static void buildHeaders(std::vector& final_headers, const HeaderMap& headers); static std::vector buildHeaders(const HeaderMap& headers); + virtual Status onBeginHeaders() PURE; + virtual void advanceHeadersState() PURE; + virtual HeadersState headersState() const PURE; void saveHeader(HeaderString&& name, HeaderString&& value); void encodeHeadersBase(const HeaderMap& headers, bool end_stream); virtual void submitHeaders(const HeaderMap& headers, bool end_stream) PURE; @@ -451,6 +461,9 @@ class ConnectionImpl : public virtual Connection, } // StreamImpl void submitHeaders(const HeaderMap& headers, bool end_stream) override; + Status onBeginHeaders() override; + void advanceHeadersState() override; + HeadersState headersState() const override { return headers_state_; } // Do not use deferred reset on upstream connections. bool useDeferredReset() const override { return false; } StreamDecoder& decoder() override { return response_decoder_; } @@ -491,6 +504,7 @@ class ConnectionImpl : public virtual Connection, ResponseDecoder& response_decoder_; absl::variant headers_or_trailers_; std::string upgrade_type_; + HeadersState headers_state_ = HeadersState::Response; }; using ClientStreamImplPtr = std::unique_ptr; @@ -507,6 +521,9 @@ class ConnectionImpl : public virtual Connection, // StreamImpl void destroy() override; void submitHeaders(const HeaderMap& headers, bool end_stream) override; + Status onBeginHeaders() override; + void advanceHeadersState() override; + HeadersState headersState() const override { return headers_state_; } // Enable deferred reset on downstream connections so outbound HTTP internal error replies are // written out before force resetting the stream, assuming there is enough H2 connection flow // control window is available. @@ -553,6 +570,7 @@ class ConnectionImpl : public virtual Connection, private: RequestDecoder* request_decoder_{}; + HeadersState headers_state_ = HeadersState::Request; }; using ServerStreamImplPtr = std::unique_ptr; @@ -566,7 +584,7 @@ class ConnectionImpl : public virtual Connection, // Same as getStream, but without the ASSERT. const StreamImpl* getStreamUnchecked(int32_t stream_id) const; StreamImpl* getStreamUnchecked(int32_t stream_id); - int saveHeader(const nghttp2_frame* frame, HeaderString&& name, HeaderString&& value); + int saveHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value); /** * Copies any frames pending internally by nghttp2 into outbound buffer. @@ -593,10 +611,8 @@ class ConnectionImpl : public virtual Connection, bool disable_push); void sendSettingsHelper(const envoy::config::core::v3::Http2ProtocolOptions& http2_options, bool disable_push); - void sendSettingsHelperOld(const envoy::config::core::v3::Http2ProtocolOptions& http2_options, - bool disable_push); // Callback triggered when the peer's SETTINGS frame is received. - virtual void onSettings(const nghttp2_settings& settings) { + virtual void onSettings(absl::Span settings) { ReceivedSettingsImpl received_settings(settings); callbacks().onSettings(received_settings); } @@ -688,15 +704,20 @@ class ConnectionImpl : public virtual Connection, friend class Http2CodecImplTestFixture; virtual ConnectionCallbacks& callbacks() PURE; - virtual Status onBeginHeaders(const nghttp2_frame* frame) PURE; + virtual Status onBeginHeaders(int32_t stream_id) PURE; int onData(int32_t stream_id, const uint8_t* data, size_t len); Status onBeforeFrameReceived(int32_t stream_id, size_t length, uint8_t type, uint8_t flags); + Status onPing(uint64_t opaque_data, bool is_ack); + Status onBeginData(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, size_t padding); + Status onGoAway(uint32_t error_code); + Status onHeaders(int32_t stream_id, size_t length, uint8_t flags); + Status onRstStream(int32_t stream_id, uint32_t error_code); Status onFrameReceived(const nghttp2_frame* frame); int onBeforeFrameSend(int32_t stream_id, size_t length, uint8_t type, uint8_t flags); int onFrameSend(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, uint32_t error_code); int onError(absl::string_view error); - virtual int onHeader(const nghttp2_frame* frame, HeaderString&& name, HeaderString&& value) PURE; + virtual int onHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value) PURE; int onInvalidFrame(int32_t stream_id, int error_code); // Pass through invoking with the actual stream. Status onStreamClose(int32_t stream_id, uint32_t error_code); @@ -708,8 +729,8 @@ class ConnectionImpl : public virtual Connection, // Adds buffer fragment for a new outbound frame to the supplied Buffer::OwnedImpl. void addOutboundFrameFragment(Buffer::OwnedImpl& output, const uint8_t* data, size_t length); - virtual Status trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, - uint32_t padding_length) PURE; + Status trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, + uint32_t padding_length); void onKeepaliveResponse(); void onKeepaliveResponseTimeout(); bool slowContainsStreamId(int32_t stream_id) const; @@ -753,10 +774,8 @@ class ClientConnectionImpl : public ClientConnection, public ConnectionImpl { private: // ConnectionImpl ConnectionCallbacks& callbacks() override { return callbacks_; } - Status onBeginHeaders(const nghttp2_frame* frame) override; - int onHeader(const nghttp2_frame* frame, HeaderString&& name, HeaderString&& value) override; - Status trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, - uint32_t) override; + Status onBeginHeaders(int32_t stream_id) override; + int onHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value) override; void dumpStreams(std::ostream& os, int indent_level) const override; StreamResetReason getMessagingErrorResetReason() const override; Http::ConnectionCallbacks& callbacks_; @@ -780,10 +799,8 @@ class ServerConnectionImpl : public ServerConnection, public ConnectionImpl { private: // ConnectionImpl ConnectionCallbacks& callbacks() override { return callbacks_; } - Status onBeginHeaders(const nghttp2_frame* frame) override; - int onHeader(const nghttp2_frame* frame, HeaderString&& name, HeaderString&& value) override; - Status trackInboundFrames(int32_t stream_id, size_t length, uint8_t type, uint8_t flags, - uint32_t padding_length) override; + Status onBeginHeaders(int32_t stream_id) override; + int onHeader(int32_t stream_id, HeaderString&& name, HeaderString&& value) override; absl::optional checkHeaderNameForUnderscores(absl::string_view header_name) override; StreamResetReason getMessagingErrorResetReason() const override { return StreamResetReason::LocalReset; diff --git a/source/common/http/http2/protocol_constraints.cc b/source/common/http/http2/protocol_constraints.cc index cc4b7c49dd9cb..30348af10f890 100644 --- a/source/common/http/http2/protocol_constraints.cc +++ b/source/common/http/http2/protocol_constraints.cc @@ -62,14 +62,13 @@ Status ProtocolConstraints::checkOutboundFrameLimits() { return okStatus(); } -Status ProtocolConstraints::trackInboundFrames(size_t length, uint8_t type, uint8_t flags, - uint32_t padding_length) { +Status ProtocolConstraints::trackInboundFrame(uint8_t type, bool end_stream, bool is_empty) { switch (type) { case NGHTTP2_HEADERS: case NGHTTP2_CONTINUATION: case NGHTTP2_DATA: // Track frames with an empty payload and no end stream flag. - if (length - padding_length == 0 && !(flags & NGHTTP2_FLAG_END_STREAM)) { + if (is_empty && !end_stream) { consecutive_inbound_frames_with_empty_payload_++; } else { consecutive_inbound_frames_with_empty_payload_ = 0; diff --git a/source/common/http/http2/protocol_constraints.h b/source/common/http/http2/protocol_constraints.h index 36c75b0b3474e..28d9eb557bbc6 100644 --- a/source/common/http/http2/protocol_constraints.h +++ b/source/common/http/http2/protocol_constraints.h @@ -47,7 +47,7 @@ class ProtocolConstraints : public ScopeTrackedObject { // Track received frames of various types. // Return an error status if inbound frame constraints were violated. - Status trackInboundFrames(size_t length, uint8_t type, uint8_t flags, uint32_t padding_length); + Status trackInboundFrame(uint8_t type, bool end_stream, bool is_empty); // Increment the number of DATA frames sent to the peer. void incrementOutboundDataFrameCount() { ++outbound_data_frames_; } void incrementOpenedStreamCount() { ++opened_streams_; } diff --git a/source/common/http/http_server_properties_cache_impl.cc b/source/common/http/http_server_properties_cache_impl.cc index 8a3018044f4fc..06b35c8d45b7a 100644 --- a/source/common/http/http_server_properties_cache_impl.cc +++ b/source/common/http/http_server_properties_cache_impl.cc @@ -3,8 +3,8 @@ #include #include "source/common/common/logger.h" +#include "source/common/http/http3_status_tracker_impl.h" -#include "http3_status_tracker_impl.h" #include "quiche/spdy/core/spdy_alt_svc_wire_format.h" #include "re2/re2.h" diff --git a/source/common/http/match_delegate/config.cc b/source/common/http/match_delegate/config.cc index a96f4a1cea589..86cd4fe380c00 100644 --- a/source/common/http/match_delegate/config.cc +++ b/source/common/http/match_delegate/config.cc @@ -1,4 +1,3 @@ -#include "config.h" #include "source/common/http/match_delegate/config.h" #include diff --git a/source/common/http/null_route_impl.cc b/source/common/http/null_route_impl.cc index e562829c084c1..3c5e328644005 100644 --- a/source/common/http/null_route_impl.cc +++ b/source/common/http/null_route_impl.cc @@ -1,4 +1,4 @@ -#include "null_route_impl.h" +#include "source/common/http/null_route_impl.h" #include diff --git a/source/common/http/utility.cc b/source/common/http/utility.cc index 558ba87c8b2be..14be4b296129d 100644 --- a/source/common/http/utility.cc +++ b/source/common/http/utility.cc @@ -102,8 +102,8 @@ struct SettingsEntryEquals { } }; -void validateCustomSettingsParameters( - const envoy::config::core::v3::Http2ProtocolOptions& options) { +absl::Status +validateCustomSettingsParameters(const envoy::config::core::v3::Http2ProtocolOptions& options) { std::vector parameter_collisions, custom_parameter_collisions; absl::node_hash_set custom_parameters; // User defined and named parameters with the same SETTINGS identifier can not both be set. @@ -122,7 +122,7 @@ void validateCustomSettingsParameters( switch (it.identifier().value()) { case http2::adapter::ENABLE_PUSH: if (it.value().value() == 1) { - throwEnvoyExceptionOrPanic( + return absl::InvalidArgumentError( "server push is not supported by Envoy and can not be enabled via a " "SETTINGS parameter."); } @@ -130,8 +130,9 @@ void validateCustomSettingsParameters( case http2::adapter::ENABLE_CONNECT_PROTOCOL: // An exception is made for `allow_connect` which can't be checked for presence due to the // use of a primitive type (bool). - throwEnvoyExceptionOrPanic("the \"allow_connect\" SETTINGS parameter must only be configured " - "through the named field"); + return absl::InvalidArgumentError( + "the \"allow_connect\" SETTINGS parameter must only be configured " + "through the named field"); case http2::adapter::HEADER_TABLE_SIZE: if (options.has_hpack_table_size()) { parameter_collisions.push_back("hpack_table_size"); @@ -154,16 +155,17 @@ void validateCustomSettingsParameters( } if (!custom_parameter_collisions.empty()) { - throwEnvoyExceptionOrPanic(fmt::format( + return absl::InvalidArgumentError(fmt::format( "inconsistent HTTP/2 custom SETTINGS parameter(s) detected; identifiers = {{{}}}", absl::StrJoin(custom_parameter_collisions, ","))); } if (!parameter_collisions.empty()) { - throwEnvoyExceptionOrPanic(fmt::format( + return absl::InvalidArgumentError(fmt::format( "the {{{}}} HTTP/2 SETTINGS parameter(s) can not be configured through both named and " "custom parameters", absl::StrJoin(parameter_collisions, ","))); } + return absl::OkStatus(); } } // namespace @@ -186,23 +188,23 @@ const uint32_t OptionsLimits::DEFAULT_MAX_CONSECUTIVE_INBOUND_FRAMES_WITH_EMPTY_ const uint32_t OptionsLimits::DEFAULT_MAX_INBOUND_PRIORITY_FRAMES_PER_STREAM; const uint32_t OptionsLimits::DEFAULT_MAX_INBOUND_WINDOW_UPDATE_FRAMES_PER_DATA_FRAME_SENT; -envoy::config::core::v3::Http2ProtocolOptions +absl::StatusOr initializeAndValidateOptions(const envoy::config::core::v3::Http2ProtocolOptions& options, bool hcm_stream_error_set, const ProtobufWkt::BoolValue& hcm_stream_error) { auto ret = initializeAndValidateOptions(options); - if (!options.has_override_stream_error_on_invalid_http_message() && hcm_stream_error_set) { - ret.mutable_override_stream_error_on_invalid_http_message()->set_value( + if (ret.status().ok() && !options.has_override_stream_error_on_invalid_http_message() && + hcm_stream_error_set) { + ret->mutable_override_stream_error_on_invalid_http_message()->set_value( hcm_stream_error.value()); } return ret; } -envoy::config::core::v3::Http2ProtocolOptions +absl::StatusOr initializeAndValidateOptions(const envoy::config::core::v3::Http2ProtocolOptions& options) { envoy::config::core::v3::Http2ProtocolOptions options_clone(options); - // This will throw an exception when a custom parameter and a named parameter collide. - validateCustomSettingsParameters(options); + RETURN_IF_NOT_OK(validateCustomSettingsParameters(options)); if (!options.has_override_stream_error_on_invalid_http_message()) { options_clone.mutable_override_stream_error_on_invalid_http_message()->set_value( @@ -465,22 +467,16 @@ void Utility::updateAuthority(RequestHeaderMap& headers, absl::string_view hostn const bool append_xfh) { const auto host = headers.getHostValue(); - if (Runtime::runtimeFeatureEnabled("envoy.reloadable_features.append_xfh_idempotent")) { - // Only append to x-forwarded-host if the value was not the last value appended. - const auto xfh = headers.getForwardedHostValue(); + // Only append to x-forwarded-host if the value was not the last value appended. + const auto xfh = headers.getForwardedHostValue(); - if (append_xfh && !host.empty()) { - if (!xfh.empty()) { - const auto xfh_split = StringUtil::splitToken(xfh, ","); - if (!xfh_split.empty() && xfh_split.back() != host) { - headers.appendForwardedHost(host, ","); - } - } else { + if (append_xfh && !host.empty()) { + if (!xfh.empty()) { + const auto xfh_split = StringUtil::splitToken(xfh, ","); + if (!xfh_split.empty() && xfh_split.back() != host) { headers.appendForwardedHost(host, ","); } - } - } else { - if (append_xfh && !host.empty()) { + } else { headers.appendForwardedHost(host, ","); } } diff --git a/source/common/http/utility.h b/source/common/http/utility.h index dc92518fb86d1..6a05a5ea589c7 100644 --- a/source/common/http/utility.h +++ b/source/common/http/utility.h @@ -97,10 +97,10 @@ struct OptionsLimits { * Validates settings/options already set in |options| and initializes any remaining fields with * defaults. */ -envoy::config::core::v3::Http2ProtocolOptions +absl::StatusOr initializeAndValidateOptions(const envoy::config::core::v3::Http2ProtocolOptions& options); -envoy::config::core::v3::Http2ProtocolOptions +absl::StatusOr initializeAndValidateOptions(const envoy::config::core::v3::Http2ProtocolOptions& options, bool hcm_stream_error_set, const ProtobufWkt::BoolValue& hcm_stream_error); diff --git a/source/common/listener_manager/active_stream_listener_base.cc b/source/common/listener_manager/active_stream_listener_base.cc index 42a6f413da586..4995bec8b2d57 100644 --- a/source/common/listener_manager/active_stream_listener_base.cc +++ b/source/common/listener_manager/active_stream_listener_base.cc @@ -44,7 +44,7 @@ void ActiveStreamListenerBase::newConnection(Network::ConnectionSocketPtr&& sock ENVOY_LOG(debug, "closing connection from {}: no matching filter chain found", socket->connectionInfoProvider().remoteAddress()->asString()); stats_.no_filter_chain_match_.inc(); - stream_info->setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + stream_info->setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); stream_info->setResponseCodeDetails(StreamInfo::ResponseCodeDetails::get().FilterChainNotFound); emitLogs(*config_, *stream_info); socket->close(); diff --git a/source/common/listener_manager/listener_impl.cc b/source/common/listener_manager/listener_impl.cc index 1c4034620a3fc..12428d8860e12 100644 --- a/source/common/listener_manager/listener_impl.cc +++ b/source/common/listener_manager/listener_impl.cc @@ -509,12 +509,25 @@ void ListenerImpl::buildInternalListener(const envoy::config::listener::v3::List parent_.server_.singletonManager().getTyped( "internal_listener_registry_singleton"); if (internal_listener_registry == nullptr) { - throw EnvoyException(fmt::format( - "error adding listener named '{}': internal listener registry is not initialized.", - name_)); + // The internal listener registry may be uninitialized when in Validate mode. + // Hence we check the configuration directly to ensure the bootstrap extension + // InternalListener is present. + if (absl::c_none_of( + listener_factory_context_->serverFactoryContext().bootstrap().bootstrap_extensions(), + [=](const auto& extension) { + return extension.typed_config().type_url() == + "type.googleapis.com/" + "envoy.extensions.bootstrap.internal_listener.v3.InternalListener"; + })) { + throw EnvoyException(fmt::format( + "error adding listener named '{}': InternalListener bootstrap extension is mandatory", + name_)); + } + internal_listener_config_ = nullptr; + } else { + internal_listener_config_ = + std::make_unique(*internal_listener_registry); } - internal_listener_config_ = - std::make_unique(*internal_listener_registry); } else if (config.address().has_envoy_internal_address() || std::any_of(config.additional_addresses().begin(), config.additional_addresses().end(), [](const envoy::config::listener::v3::AdditionalAddress& proto_address) { diff --git a/source/common/network/BUILD b/source/common/network/BUILD index f91ba321c8792..6524045963650 100644 --- a/source/common/network/BUILD +++ b/source/common/network/BUILD @@ -79,6 +79,7 @@ envoy_cc_library( srcs = ["connection_impl_base.cc"], hdrs = ["connection_impl_base.h"], deps = [ + ":common_connection_filter_states_lib", ":connection_socket_lib", ":filter_manager_lib", "//envoy/common:scope_tracker_interface", @@ -134,6 +135,7 @@ envoy_cc_library( ":connection_lib", ":multi_connection_base_impl_lib", "//envoy/upstream:upstream_interface", + "@envoy_api//envoy/config/cluster/v3:pkg_cc_proto", ], ) @@ -602,3 +604,14 @@ envoy_cc_library( "//envoy/network:filter_interface", ], ) + +envoy_cc_library( + name = "common_connection_filter_states_lib", + srcs = ["common_connection_filter_states.cc"], + hdrs = ["common_connection_filter_states.h"], + deps = [ + "//envoy/common:execution_context", + "//envoy/network:connection_interface", + "//envoy/stream_info:filter_state_interface", + ], +) diff --git a/source/common/network/common_connection_filter_states.cc b/source/common/network/common_connection_filter_states.cc new file mode 100644 index 0000000000000..6aef205ac184e --- /dev/null +++ b/source/common/network/common_connection_filter_states.cc @@ -0,0 +1,14 @@ +#include "source/common/network/common_connection_filter_states.h" + +namespace Envoy { +namespace Network { + +ExecutionContext* getConnectionExecutionContext(const Network::Connection& connection) { + const ConnectionExecutionContextFilterState* filter_state = + connection.streamInfo().filterState().getDataReadOnly( + kConnectionExecutionContextFilterStateName); + return filter_state == nullptr ? nullptr : filter_state->executionContext(); +} + +} // namespace Network +} // namespace Envoy diff --git a/source/common/network/common_connection_filter_states.h b/source/common/network/common_connection_filter_states.h new file mode 100644 index 0000000000000..4de4e97647d1c --- /dev/null +++ b/source/common/network/common_connection_filter_states.h @@ -0,0 +1,34 @@ +#pragma once + +#include "envoy/common/execution_context.h" +#include "envoy/network/connection.h" +#include "envoy/stream_info/filter_state.h" + +namespace Envoy { +namespace Network { + +static constexpr absl::string_view kConnectionExecutionContextFilterStateName = + "envoy.network.connection_execution_context"; + +// ConnectionExecutionContextFilterState is an optional connection-level filter state that goes by +// the name kConnectionExecutionContextFilterStateName. It owns a ExecutionContext, whose +// activate/deactivate methods will be called when a thread starts/finishes running code on behalf +// of the corresponding connection. +class ConnectionExecutionContextFilterState : public Envoy::StreamInfo::FilterState::Object { +public: + // It is safe, although useless, to set execution_context to nullptr. + explicit ConnectionExecutionContextFilterState( + std::unique_ptr execution_context) + : execution_context_(std::move(execution_context)) {} + + ExecutionContext* executionContext() const { return execution_context_.get(); } + +private: + std::unique_ptr execution_context_; +}; + +// Returns the ExecutionContext of a connection, if any. Or nullptr if not found. +ExecutionContext* getConnectionExecutionContext(const Network::Connection& connection); + +} // namespace Network +} // namespace Envoy diff --git a/source/common/network/connection_impl.cc b/source/common/network/connection_impl.cc index b6858939f5172..0f23f22da1caf 100644 --- a/source/common/network/connection_impl.cc +++ b/source/common/network/connection_impl.cc @@ -292,12 +292,14 @@ void ConnectionImpl::closeSocket(ConnectionEvent close_type) { if (enable_rst_detect_send_ && (detected_close_type_ == DetectedCloseType::RemoteReset || detected_close_type_ == DetectedCloseType::LocalReset)) { +#if ENVOY_PLATFORM_ENABLE_SEND_RST const bool ok = Network::Socket::applyOptions( Network::SocketOptionFactory::buildZeroSoLingerOptions(), *socket_, envoy::config::core::v3::SocketOption::STATE_LISTENING); if (!ok) { ENVOY_LOG_EVERY_POW_2(error, "rst setting so_linger=0 failed on connection {}", id()); } +#endif } // It is safe to call close() since there is an IO handle check. diff --git a/source/common/network/connection_impl_base.cc b/source/common/network/connection_impl_base.cc index 7c3647c2d44b3..e0586db6a8321 100644 --- a/source/common/network/connection_impl_base.cc +++ b/source/common/network/connection_impl_base.cc @@ -1,5 +1,7 @@ #include "source/common/network/connection_impl_base.h" +#include "source/common/network/common_connection_filter_states.h" + namespace Envoy { namespace Network { @@ -40,6 +42,10 @@ void ConnectionImplBase::setDelayedCloseTimeout(std::chrono::milliseconds timeou delayed_close_timeout_ = timeout; } +ExecutionContext* ConnectionImplBase::executionContext() const { + return getConnectionExecutionContext(*this); +} + void ConnectionImplBase::initializeDelayedCloseTimer() { const auto timeout = delayed_close_timeout_.count(); ASSERT(delayed_close_timer_ == nullptr && timeout > 0); diff --git a/source/common/network/connection_impl_base.h b/source/common/network/connection_impl_base.h index 21ee7530a45d2..4b0104adbecd2 100644 --- a/source/common/network/connection_impl_base.h +++ b/source/common/network/connection_impl_base.h @@ -29,6 +29,8 @@ class ConnectionImplBase : public FilterManagerConnection, void setConnectionStats(const ConnectionStats& stats) override; void setDelayedCloseTimeout(std::chrono::milliseconds timeout) override; + ExecutionContext* executionContext() const override; + protected: void initializeDelayedCloseTimer(); diff --git a/source/common/network/happy_eyeballs_connection_impl.cc b/source/common/network/happy_eyeballs_connection_impl.cc index a268b58012894..a68392b05c3ba 100644 --- a/source/common/network/happy_eyeballs_connection_impl.cc +++ b/source/common/network/happy_eyeballs_connection_impl.cc @@ -1,5 +1,7 @@ #include "source/common/network/happy_eyeballs_connection_impl.h" +#include "envoy/network/address.h" + #include "source/common/network/connection_impl.h" namespace Envoy { @@ -12,8 +14,11 @@ HappyEyeballsConnectionProvider::HappyEyeballsConnectionProvider( UpstreamTransportSocketFactory& socket_factory, TransportSocketOptionsConstSharedPtr transport_socket_options, const Upstream::HostDescriptionConstSharedPtr& host, - const ConnectionSocket::OptionsSharedPtr options) - : dispatcher_(dispatcher), address_list_(sortAddresses(address_list)), + const ConnectionSocket::OptionsSharedPtr options, + const absl::optional + happy_eyeballs_config) + : dispatcher_(dispatcher), + address_list_(sortAddressesWithConfig(address_list, happy_eyeballs_config)), upstream_local_address_selector_(upstream_local_address_selector), socket_factory_(socket_factory), transport_socket_options_(transport_socket_options), host_(host), options_(options) {} @@ -53,6 +58,11 @@ bool hasMatchingAddressFamily(const Address::InstanceConstSharedPtr& a, a->ip()->version() == b->ip()->version()); } +bool hasMatchingIpVersion(const Address::IpVersion& ip_version, + const Address::InstanceConstSharedPtr& addr) { + return (addr->type() == Address::Type::Ip && addr->ip()->version() == ip_version); +} + } // namespace std::vector HappyEyeballsConnectionProvider::sortAddresses( @@ -84,5 +94,64 @@ std::vector HappyEyeballsConnectionProvider::so return address_list; } +std::vector +HappyEyeballsConnectionProvider::sortAddressesWithConfig( + const std::vector& in, + const absl::optional + happy_eyeballs_config) { + if (!happy_eyeballs_config.has_value()) { + return sortAddresses(in); + } + ENVOY_LOG_EVENT(debug, "happy_eyeballs_sort_address", "sort address with happy_eyeballs config."); + std::vector address_list; + address_list.reserve(in.size()); + + // First_family_ip_version defaults to the first valid ip version + // unless overwritten by happy_eyeballs_config. + Address::IpVersion first_family_ip_version = in[0].get()->ip()->version(); + + auto first_address_family_count = + PROTOBUF_GET_WRAPPED_OR_DEFAULT(happy_eyeballs_config.value(), first_address_family_count, 1); + switch (happy_eyeballs_config.value().first_address_family_version()) { + case envoy::config::cluster::v3::UpstreamConnectionOptions::DEFAULT: + break; + case envoy::config::cluster::v3::UpstreamConnectionOptions::V4: + first_family_ip_version = Address::IpVersion::v4; + break; + case envoy::config::cluster::v3::UpstreamConnectionOptions::V6: + first_family_ip_version = Address::IpVersion::v6; + break; + default: + break; + } + + auto first = std::find_if(in.begin(), in.end(), [&](const auto& val) { + return hasMatchingIpVersion(first_family_ip_version, val); + }); + auto other = std::find_if(in.begin(), in.end(), [&](const auto& val) { + return !hasMatchingIpVersion(first_family_ip_version, val); + }); + + // Address::IpVersion first_family_ip_version(Address::IpVersion::v4); + while (first != in.end() || other != in.end()) { + uint32_t count = 0; + while (first != in.end() && ++count <= first_address_family_count) { + address_list.push_back(*first); + first = std::find_if(first + 1, in.end(), [&](const auto& val) { + return hasMatchingIpVersion(first_family_ip_version, val); + }); + } + + if (other != in.end()) { + address_list.push_back(*other); + other = std::find_if(other + 1, in.end(), [&](const auto& val) { + return !hasMatchingIpVersion(first_family_ip_version, val); + }); + } + } + ASSERT(address_list.size() == in.size()); + return address_list; +} + } // namespace Network } // namespace Envoy diff --git a/source/common/network/happy_eyeballs_connection_impl.h b/source/common/network/happy_eyeballs_connection_impl.h index 1b9684d5a2d54..94d179147250c 100644 --- a/source/common/network/happy_eyeballs_connection_impl.h +++ b/source/common/network/happy_eyeballs_connection_impl.h @@ -1,5 +1,6 @@ #pragma once +#include "envoy/config/cluster/v3/cluster.pb.h" #include "envoy/upstream/upstream.h" #include "source/common/network/multi_connection_base_impl.h" @@ -23,7 +24,10 @@ class HappyEyeballsConnectionProvider : public ConnectionProvider, UpstreamTransportSocketFactory& socket_factory, TransportSocketOptionsConstSharedPtr transport_socket_options, const Upstream::HostDescriptionConstSharedPtr& host, - const ConnectionSocket::OptionsSharedPtr options); + const ConnectionSocket::OptionsSharedPtr options, + const absl::optional< + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig> + happy_eyeballs_config); bool hasNextConnection() override; ClientConnectionPtr createNextConnection(const uint64_t id) override; size_t nextConnection() override; @@ -35,6 +39,11 @@ class HappyEyeballsConnectionProvider : public ConnectionProvider, // and Apple DNS). static std::vector sortAddresses(const std::vector& address_list); + static std::vector sortAddressesWithConfig( + const std::vector& address_list, + const absl::optional< + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig> + happy_eyeballs_config); private: Event::Dispatcher& dispatcher_; @@ -69,18 +78,23 @@ class HappyEyeballsConnectionProvider : public ConnectionProvider, class HappyEyeballsConnectionImpl : public MultiConnectionBaseImpl, Logger::Loggable { public: - HappyEyeballsConnectionImpl(Event::Dispatcher& dispatcher, - const std::vector& address_list, - const std::shared_ptr& - upstream_local_address_selector, - UpstreamTransportSocketFactory& socket_factory, - TransportSocketOptionsConstSharedPtr transport_socket_options, - const Upstream::HostDescriptionConstSharedPtr& host, - const ConnectionSocket::OptionsSharedPtr options) + HappyEyeballsConnectionImpl( + Event::Dispatcher& dispatcher, + const std::vector& address_list, + const std::shared_ptr& + upstream_local_address_selector, + UpstreamTransportSocketFactory& socket_factory, + TransportSocketOptionsConstSharedPtr transport_socket_options, + const Upstream::HostDescriptionConstSharedPtr& host, + const ConnectionSocket::OptionsSharedPtr options, + const absl::optional< + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig> + happy_eyeballs_config) : MultiConnectionBaseImpl(dispatcher, std::make_unique( dispatcher, address_list, upstream_local_address_selector, - socket_factory, transport_socket_options, host, options)) {} + socket_factory, transport_socket_options, host, options, + happy_eyeballs_config)) {} }; } // namespace Network diff --git a/source/common/network/io_socket_handle_base_impl.cc b/source/common/network/io_socket_handle_base_impl.cc index 2432851479794..4e29c21703a0e 100644 --- a/source/common/network/io_socket_handle_base_impl.cc +++ b/source/common/network/io_socket_handle_base_impl.cc @@ -1,4 +1,4 @@ -#include "io_socket_handle_base_impl.h" +#include "source/common/network/io_socket_handle_base_impl.h" #include "envoy/buffer/buffer.h" #include "envoy/common/exception.h" diff --git a/source/common/network/resolver_impl.cc b/source/common/network/resolver_impl.cc index 63119deff8aec..66173b44758d3 100644 --- a/source/common/network/resolver_impl.cc +++ b/source/common/network/resolver_impl.cc @@ -47,7 +47,7 @@ absl::StatusOr resolveProtoAddress(const envoy::config::core::v3::Address& address) { switch (address.address_case()) { case envoy::config::core::v3::Address::AddressCase::ADDRESS_NOT_SET: - throwEnvoyExceptionOrPanic("Address must be set: " + address.DebugString()); + return absl::InvalidArgumentError("Address must be set: " + address.DebugString()); case envoy::config::core::v3::Address::AddressCase::kSocketAddress: return resolveProtoSocketAddress(address.socket_address()); case envoy::config::core::v3::Address::AddressCase::kPipe: @@ -64,7 +64,7 @@ resolveProtoAddress(const envoy::config::core::v3::Address& address) { break; } } - throwEnvoyExceptionOrPanic("Failed to resolve address:" + address.DebugString()); + return absl::InvalidArgumentError("Failed to resolve address:" + address.DebugString()); } absl::StatusOr @@ -78,10 +78,10 @@ resolveProtoSocketAddress(const envoy::config::core::v3::SocketAddress& socket_a resolver = Registry::FactoryRegistry::getFactory(resolver_name); } if (resolver == nullptr) { - throwEnvoyExceptionOrPanic(fmt::format("Unknown address resolver: {}", resolver_name)); + return absl::InvalidArgumentError(fmt::format("Unknown address resolver: {}", resolver_name)); } auto instance_or_error = resolver->resolve(socket_address); - THROW_IF_STATUS_NOT_OK(instance_or_error, throw); + RETURN_IF_STATUS_NOT_OK(instance_or_error); return std::move(instance_or_error.value()); } diff --git a/source/common/network/socket_impl.cc b/source/common/network/socket_impl.cc index 14d9d2c781e85..8b0c40a88ff70 100644 --- a/source/common/network/socket_impl.cc +++ b/source/common/network/socket_impl.cc @@ -68,9 +68,7 @@ Api::SysCallIntResult SocketImpl::bind(Network::Address::InstanceConstSharedPtr if (pipe->mode() != 0 && !abstract_namespace && bind_result.return_value_ == 0) { auto set_permissions = Api::OsSysCallsSingleton::get().chmod(pipe_sa->sun_path, pipe->mode()); if (set_permissions.return_value_ != 0) { - throwEnvoyExceptionOrPanic(fmt::format("Failed to create socket with mode {}: {}", - std::to_string(pipe->mode()), - errorDetails(set_permissions.errno_))); + return set_permissions; } } return bind_result; diff --git a/source/common/network/tcp_listener_impl.h b/source/common/network/tcp_listener_impl.h index d885276cc12d4..0ac18342d095c 100644 --- a/source/common/network/tcp_listener_impl.h +++ b/source/common/network/tcp_listener_impl.h @@ -4,9 +4,9 @@ #include "envoy/runtime/runtime.h" #include "source/common/common/interval_value.h" +#include "source/common/network/base_listener_impl.h" #include "absl/strings/string_view.h" -#include "base_listener_impl.h" namespace Envoy { namespace Network { diff --git a/source/common/quic/active_quic_listener.cc b/source/common/quic/active_quic_listener.cc index ccdc9897e8d03..685cc1f5eb3f7 100644 --- a/source/common/quic/active_quic_listener.cc +++ b/source/common/quic/active_quic_listener.cc @@ -234,6 +234,9 @@ ActiveQuicListenerFactory::ActiveQuicListenerFactory( : 20000; quic_config_.set_max_time_before_crypto_handshake(quic::QuicTime::Delta::FromMilliseconds( std::max(quic::kInitialIdleTimeoutSecs * 1000, max_time_before_crypto_handshake_ms))); + if (PROTOBUF_GET_WRAPPED_OR_DEFAULT(config, send_disable_active_migration, false)) { + quic_config_.SetDisableConnectionMigration(); + } convertQuicConfig(config.quic_protocol_options(), quic_config_); // Initialize crypto stream factory. diff --git a/source/common/quic/envoy_quic_client_session.cc b/source/common/quic/envoy_quic_client_session.cc index 69618a64cba5f..2f3cbd1a0ec8c 100644 --- a/source/common/quic/envoy_quic_client_session.cc +++ b/source/common/quic/envoy_quic_client_session.cc @@ -9,8 +9,7 @@ #include "source/common/event/dispatcher_impl.h" #include "source/common/quic/envoy_quic_proof_verifier.h" #include "source/common/quic/envoy_quic_utils.h" - -#include "quic_filter_manager_connection_impl.h" +#include "source/common/quic/quic_filter_manager_connection_impl.h" namespace Envoy { namespace Quic { diff --git a/source/common/quic/envoy_quic_server_session.cc b/source/common/quic/envoy_quic_server_session.cc index 00e1b56a9930b..f4a9d267f2995 100644 --- a/source/common/quic/envoy_quic_server_session.cc +++ b/source/common/quic/envoy_quic_server_session.cc @@ -7,8 +7,7 @@ #include "source/common/common/assert.h" #include "source/common/quic/envoy_quic_proof_source.h" #include "source/common/quic/envoy_quic_server_stream.h" - -#include "quic_filter_manager_connection_impl.h" +#include "source/common/quic/quic_filter_manager_connection_impl.h" namespace Envoy { namespace Quic { diff --git a/source/common/quic/quic_server_transport_socket_factory.cc b/source/common/quic/quic_server_transport_socket_factory.cc index 6be9342aa583e..8054a65ab3062 100644 --- a/source/common/quic/quic_server_transport_socket_factory.cc +++ b/source/common/quic/quic_server_transport_socket_factory.cc @@ -21,7 +21,7 @@ QuicServerTransportSocketConfigFactory::createTransportSocketFactory( quic_transport.downstream_tls_context(), context); // TODO(RyanTheOptimist): support TLS client authentication. if (server_config->requireClientCertificate()) { - throwEnvoyExceptionOrPanic("TLS Client Authentication is not supported over QUIC"); + throw EnvoyException("TLS Client Authentication is not supported over QUIC"); } auto factory = std::make_unique( diff --git a/source/common/rds/rds_route_config_subscription.cc b/source/common/rds/rds_route_config_subscription.cc index 44d2e15d59a64..4bda9ae928c59 100644 --- a/source/common/rds/rds_route_config_subscription.cc +++ b/source/common/rds/rds_route_config_subscription.cc @@ -85,13 +85,13 @@ absl::Status RdsRouteConfigSubscription::onConfigUpdate( stats_.config_reload_.inc(); stats_.config_reload_time_ms_.set(DateUtil::nowToMilliseconds(factory_context_.timeSource())); - beforeProviderUpdate(noop_init_manager, resume_rds); + RETURN_IF_NOT_OK(beforeProviderUpdate(noop_init_manager, resume_rds)); ENVOY_LOG(debug, "rds: loading new configuration: config_name={} hash={}", route_config_name_, config_update_info_->configHash()); if (route_config_provider_ != nullptr) { - THROW_IF_NOT_OK(route_config_provider_->onConfigUpdate()); + RETURN_IF_NOT_OK(route_config_provider_->onConfigUpdate()); } afterProviderUpdate(); diff --git a/source/common/rds/rds_route_config_subscription.h b/source/common/rds/rds_route_config_subscription.h index 205375cef14fa..525a22b3825b7 100644 --- a/source/common/rds/rds_route_config_subscription.h +++ b/source/common/rds/rds_route_config_subscription.h @@ -72,8 +72,10 @@ class RdsRouteConfigSubscription : Envoy::Config::SubscriptionCallbacks, void onConfigUpdateFailed(Envoy::Config::ConfigUpdateFailureReason reason, const EnvoyException*) override; - virtual void beforeProviderUpdate(std::unique_ptr&, - std::unique_ptr&) {} + virtual absl::Status beforeProviderUpdate(std::unique_ptr&, + std::unique_ptr&) { + return absl::OkStatus(); + } virtual void afterProviderUpdate() {} protected: diff --git a/source/common/router/rds_impl.cc b/source/common/router/rds_impl.cc index 18475ae48d06e..98abfb3d046ad 100644 --- a/source/common/router/rds_impl.cc +++ b/source/common/router/rds_impl.cc @@ -82,7 +82,7 @@ RdsRouteConfigSubscription::RdsRouteConfigSubscription( RdsRouteConfigSubscription::~RdsRouteConfigSubscription() { config_update_info_.release(); } -void RdsRouteConfigSubscription::beforeProviderUpdate( +absl::Status RdsRouteConfigSubscription::beforeProviderUpdate( std::unique_ptr& noop_init_manager, std::unique_ptr& resume_rds) { if (config_update_info_->protobufConfigurationCast().has_vhds() && config_update_info_->vhdsConfigurationChanged()) { @@ -92,11 +92,14 @@ void RdsRouteConfigSubscription::beforeProviderUpdate( ASSERT(config_update_info_->configInfo().has_value()); maybeCreateInitManager(routeConfigUpdate()->configInfo().value().version_, noop_init_manager, resume_rds); - vhds_subscription_ = std::make_unique(config_update_info_, factory_context_, - stat_prefix_, route_config_provider_); + auto subscription_or_error = VhdsSubscription::createVhdsSubscription( + config_update_info_, factory_context_, stat_prefix_, route_config_provider_); + RETURN_IF_STATUS_NOT_OK(subscription_or_error); + vhds_subscription_ = std::move(subscription_or_error.value()); vhds_subscription_->registerInitTargetWithInitManager( noop_init_manager == nullptr ? local_init_manager_ : *noop_init_manager); } + return absl::OkStatus(); } void RdsRouteConfigSubscription::afterProviderUpdate() { diff --git a/source/common/router/rds_impl.h b/source/common/router/rds_impl.h index 5d5eb826d5c71..fcd287d5451df 100644 --- a/source/common/router/rds_impl.h +++ b/source/common/router/rds_impl.h @@ -113,8 +113,8 @@ class RdsRouteConfigSubscription : public Rds::RdsRouteConfigSubscription { std::unique_ptr& resume_rds); private: - void beforeProviderUpdate(std::unique_ptr& noop_init_manager, - std::unique_ptr& resume_rds) override; + absl::Status beforeProviderUpdate(std::unique_ptr& noop_init_manager, + std::unique_ptr& resume_rds) override; void afterProviderUpdate() override; ABSL_MUST_USE_RESULT Common::CallbackHandlePtr addUpdateCallback(std::function callback) { diff --git a/source/common/router/router.cc b/source/common/router/router.cc index 7391c00bacf4d..37c7da0bc40e1 100644 --- a/source/common/router/router.cc +++ b/source/common/router/router.cc @@ -445,7 +445,7 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, stats_.no_route_.inc(); ENVOY_STREAM_LOG(debug, "no route match for URL '{}'", *callbacks_, headers.getPathValue()); - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); callbacks_->sendLocalReply(Http::Code::NotFound, "", modify_headers, absl::nullopt, StreamInfo::ResponseCodeDetails::get().RouteNotFound); return Http::FilterHeadersStatus::StopIteration; @@ -496,7 +496,7 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, stats_.no_cluster_.inc(); ENVOY_STREAM_LOG(debug, "unknown cluster '{}'", *callbacks_, route_entry_->clusterName()); - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoClusterFound); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoClusterFound); callbacks_->sendLocalReply(route_entry_->clusterNotFoundResponseCode(), "", modify_headers, absl::nullopt, StreamInfo::ResponseCodeDetails::get().ClusterNotFound); @@ -518,7 +518,7 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, const auto res = FilterUtility::StrictHeaderChecker::checkHeader(headers, header); if (!res.valid_) { callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::InvalidEnvoyRequestHeaders); + StreamInfo::CoreResponseFlag::InvalidEnvoyRequestHeaders); const std::string body = fmt::format("invalid header '{}' with value '{}'", std::string(res.entry_->key().getStringView()), std::string(res.entry_->value().getStringView())); @@ -540,7 +540,7 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, // See if we are supposed to immediately kill some percentage of this cluster's traffic. if (cluster_->maintenanceMode()) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); chargeUpstreamCode(Http::Code::ServiceUnavailable, nullptr, true); callbacks_->sendLocalReply( Http::Code::ServiceUnavailable, "maintenance mode", @@ -830,7 +830,7 @@ Filter::createConnPool(Upstream::ThreadLocalCluster& thread_local_cluster) { } void Filter::sendNoHealthyUpstreamResponse() { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream); chargeUpstreamCode(Http::Code::ServiceUnavailable, nullptr, false); callbacks_->sendLocalReply(Http::Code::ServiceUnavailable, "no healthy upstream", modify_headers_, absl::nullopt, @@ -1108,7 +1108,7 @@ void Filter::onResponseTimeout() { upstream_request->resetStream(); } - onUpstreamTimeoutAbort(StreamInfo::ResponseFlag::UpstreamRequestTimeout, + onUpstreamTimeoutAbort(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout, StreamInfo::ResponseCodeDetails::get().ResponseTimeout); } @@ -1141,10 +1141,10 @@ void Filter::onSoftPerTryTimeout(UpstreamRequest& upstream_request) { // TODO: cluster stat for hedge attempted. } else if (retry_status == RetryStatus::NoOverflow) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); } else if (retry_status == RetryStatus::NoRetryLimitExceeded) { callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded); + StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded); } } } @@ -1185,7 +1185,8 @@ void Filter::onPerTryTimeoutCommon(UpstreamRequest& upstream_request, Stats::Cou // Remove this upstream request from the list now that we're done with it. upstream_request.removeFromList(upstream_requests_); - onUpstreamTimeoutAbort(StreamInfo::ResponseFlag::UpstreamRequestTimeout, response_code_details); + onUpstreamTimeoutAbort(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout, + response_code_details); } void Filter::onStreamMaxDurationReached(UpstreamRequest& upstream_request) { @@ -1199,7 +1200,7 @@ void Filter::onStreamMaxDurationReached(UpstreamRequest& upstream_request) { cleanup(); callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UpstreamMaxStreamDurationReached); + StreamInfo::CoreResponseFlag::UpstreamMaxStreamDurationReached); // Grab the const ref to call the const method of StreamInfo. const auto& stream_info = callbacks_->streamInfo(); const bool downstream_decode_complete = @@ -1241,7 +1242,7 @@ void Filter::chargeUpstreamAbort(Http::Code code, bool dropped, UpstreamRequest& } } -void Filter::onUpstreamTimeoutAbort(StreamInfo::ResponseFlag response_flags, +void Filter::onUpstreamTimeoutAbort(StreamInfo::CoreResponseFlag response_flags, absl::string_view details) { Upstream::ClusterTimeoutBudgetStatsOptRef tb_stats = cluster()->timeoutBudgetStats(); if (tb_stats.has_value()) { @@ -1258,7 +1259,7 @@ void Filter::onUpstreamTimeoutAbort(StreamInfo::ResponseFlag response_flags, onUpstreamAbort(timeout_response_code_, response_flags, body, false, details); } -void Filter::onUpstreamAbort(Http::Code code, StreamInfo::ResponseFlag response_flags, +void Filter::onUpstreamAbort(Http::Code code, StreamInfo::CoreResponseFlag response_flags, absl::string_view body, bool dropped, absl::string_view details) { // If we have not yet sent anything downstream, send a response with an appropriate status code. // Otherwise just reset the ongoing response. @@ -1315,9 +1316,10 @@ bool Filter::maybeRetryReset(Http::StreamResetReason reset_reason, callbacks_->dispatcher().deferredDelete(std::move(request_ptr)); return true; } else if (retry_status == RetryStatus::NoOverflow) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); } else if (retry_status == RetryStatus::NoRetryLimitExceeded) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded); + callbacks_->streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded); } return false; @@ -1364,7 +1366,7 @@ void Filter::onUpstreamReset(Http::StreamResetReason reset_reason, return; } - const StreamInfo::ResponseFlag response_flags = streamResetReasonToResponseFlag(reset_reason); + const StreamInfo::CoreResponseFlag response_flags = streamResetReasonToResponseFlag(reset_reason); const std::string body = absl::StrCat("upstream connect error or disconnect/reset before headers. ", @@ -1405,28 +1407,28 @@ void Filter::onUpstreamHostSelected(Upstream::HostDescriptionConstSharedPtr host } } -StreamInfo::ResponseFlag +StreamInfo::CoreResponseFlag Filter::streamResetReasonToResponseFlag(Http::StreamResetReason reset_reason) { switch (reset_reason) { case Http::StreamResetReason::LocalConnectionFailure: case Http::StreamResetReason::RemoteConnectionFailure: case Http::StreamResetReason::ConnectionTimeout: - return StreamInfo::ResponseFlag::UpstreamConnectionFailure; + return StreamInfo::CoreResponseFlag::UpstreamConnectionFailure; case Http::StreamResetReason::ConnectionTermination: - return StreamInfo::ResponseFlag::UpstreamConnectionTermination; + return StreamInfo::CoreResponseFlag::UpstreamConnectionTermination; case Http::StreamResetReason::LocalReset: case Http::StreamResetReason::LocalRefusedStreamReset: - return StreamInfo::ResponseFlag::LocalReset; + return StreamInfo::CoreResponseFlag::LocalReset; case Http::StreamResetReason::Overflow: - return StreamInfo::ResponseFlag::UpstreamOverflow; + return StreamInfo::CoreResponseFlag::UpstreamOverflow; case Http::StreamResetReason::RemoteReset: case Http::StreamResetReason::RemoteRefusedStreamReset: case Http::StreamResetReason::ConnectError: - return StreamInfo::ResponseFlag::UpstreamRemoteReset; + return StreamInfo::CoreResponseFlag::UpstreamRemoteReset; case Http::StreamResetReason::ProtocolError: - return StreamInfo::ResponseFlag::UpstreamProtocolError; + return StreamInfo::CoreResponseFlag::UpstreamProtocolError; case Http::StreamResetReason::OverloadManager: - return StreamInfo::ResponseFlag::OverloadManager; + return StreamInfo::CoreResponseFlag::OverloadManager; } PANIC_DUE_TO_CORRUPT_ENUM; @@ -1565,11 +1567,11 @@ void Filter::onUpstreamHeaders(uint64_t response_code, Http::ResponseHeaderMapPt callbacks_->dispatcher().deferredDelete(std::move(request_ptr)); return; } else if (retry_status == RetryStatus::NoOverflow) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); could_not_retry = true; } else if (retry_status == RetryStatus::NoRetryLimitExceeded) { callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded); + StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded); could_not_retry = true; } } @@ -2031,7 +2033,7 @@ bool Filter::checkDropOverload(Upstream::ThreadLocalCluster& cluster, cluster.dropOverload().value()); if (config_.random_.bernoulli(cluster.dropOverload())) { ENVOY_STREAM_LOG(debug, "The request is dropped by DROP_OVERLOAD", *callbacks_); - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::DropOverLoad); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::DropOverLoad); chargeUpstreamCode(Http::Code::ServiceUnavailable, nullptr, true); callbacks_->sendLocalReply( Http::Code::ServiceUnavailable, "drop overload", diff --git a/source/common/router/router.h b/source/common/router/router.h index cd6f6c29d948d..701c72b10f515 100644 --- a/source/common/router/router.h +++ b/source/common/router/router.h @@ -305,7 +305,7 @@ class Filter : Logger::Loggable, ~Filter() override; - static StreamInfo::ResponseFlag + static StreamInfo::CoreResponseFlag streamResetReasonToResponseFlag(Http::StreamResetReason reset_reason); // Http::StreamFilterBase @@ -520,11 +520,12 @@ class Filter : Logger::Loggable, // Handle an upstream request aborted due to a local timeout. void onSoftPerTryTimeout(); void onSoftPerTryTimeout(UpstreamRequest& upstream_request); - void onUpstreamTimeoutAbort(StreamInfo::ResponseFlag response_flag, absl::string_view details); + void onUpstreamTimeoutAbort(StreamInfo::CoreResponseFlag response_flag, + absl::string_view details); // Handle an "aborted" upstream request, meaning we didn't see response // headers (e.g. due to a reset). Handles recording stats and responding // downstream if appropriate. - void onUpstreamAbort(Http::Code code, StreamInfo::ResponseFlag response_flag, + void onUpstreamAbort(Http::Code code, StreamInfo::CoreResponseFlag response_flag, absl::string_view body, bool dropped, absl::string_view details); void onUpstreamComplete(UpstreamRequest& upstream_request); // Reset all in-flight upstream requests. diff --git a/source/common/router/upstream_codec_filter.cc b/source/common/router/upstream_codec_filter.cc index 158d2b729713d..9882fda66eed0 100644 --- a/source/common/router/upstream_codec_filter.cc +++ b/source/common/router/upstream_codec_filter.cc @@ -68,7 +68,7 @@ Http::FilterHeadersStatus UpstreamCodecFilter::decodeHeaders(Http::RequestHeader deferred_reset_ = false; // It is possible that encodeHeaders() fails. This can happen if filters or other extensions // erroneously remove required headers. - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::DownstreamProtocolError); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::DownstreamProtocolError); const std::string details = absl::StrCat(StreamInfo::ResponseCodeDetails::get().FilterRemovedRequiredRequestHeaders, "{", StringUtil::replaceAllEmptySpace(status.message()), "}"); diff --git a/source/common/router/upstream_request.cc b/source/common/router/upstream_request.cc index 5a27efd3e11c7..5d4aef010a91e 100644 --- a/source/common/router/upstream_request.cc +++ b/source/common/router/upstream_request.cc @@ -510,7 +510,7 @@ void UpstreamRequest::setupPerTryTimeout() { void UpstreamRequest::onPerTryIdleTimeout() { ENVOY_STREAM_LOG(debug, "upstream per try idle timeout", *parent_.callbacks()); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::StreamIdleTimeout); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::StreamIdleTimeout); parent_.onPerTryIdleTimeout(*this); } @@ -520,7 +520,7 @@ void UpstreamRequest::onPerTryTimeout() { if (!parent_.downstreamResponseStarted()) { ENVOY_STREAM_LOG(debug, "upstream per try timeout", *parent_.callbacks()); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout); parent_.onPerTryTimeout(*this); } else { ENVOY_STREAM_LOG(debug, diff --git a/source/common/router/vhds.cc b/source/common/router/vhds.cc index 7f01399073372..a805597b08704 100644 --- a/source/common/router/vhds.cc +++ b/source/common/router/vhds.cc @@ -19,6 +19,23 @@ namespace Envoy { namespace Router { +absl::StatusOr VhdsSubscription::createVhdsSubscription( + RouteConfigUpdatePtr& config_update_info, + Server::Configuration::ServerFactoryContext& factory_context, const std::string& stat_prefix, + Rds::RouteConfigProvider* route_config_provider) { + const auto& config_source = config_update_info->protobufConfigurationCast() + .vhds() + .config_source() + .api_config_source() + .api_type(); + if (config_source != envoy::config::core::v3::ApiConfigSource::DELTA_GRPC) { + return absl::InvalidArgumentError("vhds: only 'DELTA_GRPC' is supported as an api_type."); + } + + return std::unique_ptr(new VhdsSubscription( + config_update_info, factory_context, stat_prefix, route_config_provider)); +} + // Implements callbacks to handle DeltaDiscovery protocol for VirtualHostDiscoveryService VhdsSubscription::VhdsSubscription(RouteConfigUpdatePtr& config_update_info, Server::Configuration::ServerFactoryContext& factory_context, @@ -37,14 +54,6 @@ VhdsSubscription::VhdsSubscription(RouteConfigUpdatePtr& config_update_info, {config_update_info_->protobufConfigurationCast().name()}); }), route_config_provider_(route_config_provider) { - const auto& config_source = config_update_info_->protobufConfigurationCast() - .vhds() - .config_source() - .api_config_source() - .api_type(); - if (config_source != envoy::config::core::v3::ApiConfigSource::DELTA_GRPC) { - throwEnvoyExceptionOrPanic("vhds: only 'DELTA_GRPC' is supported as an api_type."); - } const auto resource_name = getResourceName(); Envoy::Config::SubscriptionOptions options; options.use_namespace_matching_ = true; @@ -91,7 +100,7 @@ absl::Status VhdsSubscription::onConfigUpdate( config_update_info_->protobufConfigurationCast().name(), config_update_info_->configHash()); if (route_config_provider_ != nullptr) { - THROW_IF_NOT_OK(route_config_provider_->onConfigUpdate()); + RETURN_IF_NOT_OK(route_config_provider_->onConfigUpdate()); } } diff --git a/source/common/router/vhds.h b/source/common/router/vhds.h index 6e3f397b76a85..8b20961c72bc4 100644 --- a/source/common/router/vhds.h +++ b/source/common/router/vhds.h @@ -39,9 +39,11 @@ struct VhdsStats { class VhdsSubscription : Envoy::Config::SubscriptionBase, Logger::Loggable { public: - VhdsSubscription(RouteConfigUpdatePtr& config_update_info, - Server::Configuration::ServerFactoryContext& factory_context, - const std::string& stat_prefix, Rds::RouteConfigProvider* route_config_provider); + static absl::StatusOr> + createVhdsSubscription(RouteConfigUpdatePtr& config_update_info, + Server::Configuration::ServerFactoryContext& factory_context, + const std::string& stat_prefix, + Rds::RouteConfigProvider* route_config_provider); ~VhdsSubscription() override { init_target_.ready(); } @@ -57,6 +59,10 @@ class VhdsSubscription : Envoy::Config::SubscriptionBase&, const std::string&) override { diff --git a/source/common/runtime/runtime_features.cc b/source/common/runtime/runtime_features.cc index 3990f2a06e27b..593f6857027d3 100644 --- a/source/common/runtime/runtime_features.cc +++ b/source/common/runtime/runtime_features.cc @@ -30,32 +30,33 @@ // ASAP by filing a bug on github. Overriding non-buggy code is strongly discouraged to avoid the // problem of the bugs being found after the old code path has been removed. RUNTIME_GUARD(envoy_reloadable_features_abort_filter_chain_on_stream_reset); -RUNTIME_GUARD(envoy_reloadable_features_allow_absolute_url_with_mixed_scheme); -RUNTIME_GUARD(envoy_reloadable_features_append_xfh_idempotent); RUNTIME_GUARD(envoy_reloadable_features_avoid_zombie_streams); RUNTIME_GUARD(envoy_reloadable_features_check_mep_on_first_eject); RUNTIME_GUARD(envoy_reloadable_features_conn_pool_delete_when_idle); RUNTIME_GUARD(envoy_reloadable_features_convert_legacy_lb_config); RUNTIME_GUARD(envoy_reloadable_features_copy_response_code_to_downstream_stream_info); -RUNTIME_GUARD(envoy_reloadable_features_count_unused_mapped_pages_as_free); RUNTIME_GUARD(envoy_reloadable_features_defer_processing_backedup_streams); RUNTIME_GUARD(envoy_reloadable_features_detect_and_raise_rst_tcp_connection); RUNTIME_GUARD(envoy_reloadable_features_dfp_mixed_scheme); RUNTIME_GUARD(envoy_reloadable_features_dns_cache_set_first_resolve_complete); +RUNTIME_GUARD(envoy_reloadable_features_edf_lb_locality_scheduler_init_fix); RUNTIME_GUARD(envoy_reloadable_features_enable_aws_credentials_file); RUNTIME_GUARD(envoy_reloadable_features_enable_compression_bomb_protection); RUNTIME_GUARD(envoy_reloadable_features_enable_connect_udp_support); RUNTIME_GUARD(envoy_reloadable_features_enable_intermediate_ca); RUNTIME_GUARD(envoy_reloadable_features_enable_zone_routing_different_zone_counts); +RUNTIME_GUARD(envoy_reloadable_features_exclude_host_in_eds_status_draining); RUNTIME_GUARD(envoy_reloadable_features_ext_authz_http_send_original_xff); +RUNTIME_GUARD(envoy_reloadable_features_grpc_http1_reverse_bridge_change_http_status); RUNTIME_GUARD(envoy_reloadable_features_grpc_http1_reverse_bridge_handle_empty_response); RUNTIME_GUARD(envoy_reloadable_features_handle_uppercase_scheme); RUNTIME_GUARD(envoy_reloadable_features_hmac_base64_encoding_only); -RUNTIME_GUARD(envoy_reloadable_features_http1_allow_codec_error_response_after_1xx_headers); RUNTIME_GUARD(envoy_reloadable_features_http1_connection_close_header_in_redirect); +// Ignore the automated "remove this flag" issue: we should keep this for 1 year. RUNTIME_GUARD(envoy_reloadable_features_http1_use_balsa_parser); RUNTIME_GUARD(envoy_reloadable_features_http2_decode_metadata_with_quiche); RUNTIME_GUARD(envoy_reloadable_features_http2_discard_host_header); +// Ignore the automated "remove this flag" issue: we should keep this for 1 year. RUNTIME_GUARD(envoy_reloadable_features_http2_use_oghttp2); RUNTIME_GUARD(envoy_reloadable_features_http2_validate_authority_with_quiche); RUNTIME_GUARD(envoy_reloadable_features_http_allow_partial_urls_in_referer); @@ -64,7 +65,6 @@ RUNTIME_GUARD(envoy_reloadable_features_http_filter_avoid_reentrant_local_reply) RUNTIME_GUARD(envoy_reloadable_features_http_reject_path_with_fragment); RUNTIME_GUARD(envoy_reloadable_features_immediate_response_use_filter_mutation_rule); RUNTIME_GUARD(envoy_reloadable_features_initialize_upstream_filters); -RUNTIME_GUARD(envoy_reloadable_features_keep_endpoint_active_hc_status_on_locality_update); RUNTIME_GUARD(envoy_reloadable_features_locality_routing_use_new_routing_logic); RUNTIME_GUARD(envoy_reloadable_features_lowercase_scheme); RUNTIME_GUARD(envoy_reloadable_features_no_downgrade_to_canonical_name); @@ -75,7 +75,6 @@ RUNTIME_GUARD(envoy_reloadable_features_oauth_make_token_cookie_httponly); RUNTIME_GUARD(envoy_reloadable_features_oauth_use_standard_max_age_value); RUNTIME_GUARD(envoy_reloadable_features_oauth_use_url_encoding); RUNTIME_GUARD(envoy_reloadable_features_original_dst_rely_on_idle_timeout); -RUNTIME_GUARD(envoy_reloadable_features_overload_manager_error_unknown_action); RUNTIME_GUARD(envoy_reloadable_features_proxy_status_upstream_request_timeout); RUNTIME_GUARD(envoy_reloadable_features_quic_fix_filter_manager_uaf); RUNTIME_GUARD(envoy_reloadable_features_sanitize_te); @@ -99,7 +98,11 @@ RUNTIME_GUARD(envoy_reloadable_features_validate_upstream_headers); RUNTIME_GUARD(envoy_restart_features_send_goaway_for_premature_rst_streams); RUNTIME_GUARD(envoy_restart_features_udp_read_normalize_addresses); -// Begin false flags. These should come with a TODO to flip true. +// Begin false flags. Most of them should come with a TODO to flip true. + +// Execution context is optional and must be enabled explicitly. +// See https://github.com/envoyproxy/envoy/issues/32012. +FALSE_RUNTIME_GUARD(envoy_restart_features_enable_execution_context); // Sentinel and test flag. FALSE_RUNTIME_GUARD(envoy_reloadable_features_test_feature_false); // TODO(paul-r-gall) Make this enabled by default after additional soak time. @@ -135,6 +138,8 @@ FALSE_RUNTIME_GUARD(envoy_reloadable_features_enable_universal_header_validator) FALSE_RUNTIME_GUARD(envoy_reloadable_features_quic_defer_logging_to_ack_listener); // TODO(#31276): flip this to true after some test time. FALSE_RUNTIME_GUARD(envoy_restart_features_use_fast_protobuf_hash); +// TODO(panting): flip this to true after some test time. +FALSE_RUNTIME_GUARD(envoy_reloadable_features_use_config_in_happy_eyeballs); // Block of non-boolean flags. Use of int flags is deprecated. Do not add more. ABSL_FLAG(uint64_t, re2_max_program_size_error_level, 100, ""); // NOLINT diff --git a/source/common/secret/sds_api.cc b/source/common/secret/sds_api.cc index 8a0c3f43d2e19..5492fb92de287 100644 --- a/source/common/secret/sds_api.cc +++ b/source/common/secret/sds_api.cc @@ -120,7 +120,7 @@ absl::Status SdsApi::onConfigUpdate(const std::vectoraddWatch(absl::StrCat(result_or_error.value().directory_, "/"), Filesystem::Watcher::Events::MovedTo, [this](uint32_t) { onWatchUpdate(); }); diff --git a/source/common/secret/sds_api.h b/source/common/secret/sds_api.h index 1aee5f4a0b782..e01f30b139830 100644 --- a/source/common/secret/sds_api.h +++ b/source/common/secret/sds_api.h @@ -138,7 +138,8 @@ class TlsCertificateSdsApi : public SdsApi, public TlsCertificateConfigProvider // We need to do this early as we invoke the subscription factory during initialization, which // is too late to throw. auto& server_context = secret_provider_context.serverFactoryContext(); - Config::Utility::checkLocalInfo("TlsCertificateSdsApi", server_context.localInfo()); + THROW_IF_NOT_OK( + Config::Utility::checkLocalInfo("TlsCertificateSdsApi", server_context.localInfo())); return std::make_shared( sds_config, sds_config_name, secret_provider_context.clusterManager().subscriptionFactory(), server_context.mainThreadDispatcher().timeSource(), @@ -224,8 +225,8 @@ class CertificateValidationContextSdsApi : public SdsApi, // We need to do this early as we invoke the subscription factory during initialization, which // is too late to throw. auto& server_context = secret_provider_context.serverFactoryContext(); - Config::Utility::checkLocalInfo("CertificateValidationContextSdsApi", - server_context.localInfo()); + THROW_IF_NOT_OK(Config::Utility::checkLocalInfo("CertificateValidationContextSdsApi", + server_context.localInfo())); return std::make_shared( sds_config, sds_config_name, secret_provider_context.clusterManager().subscriptionFactory(), server_context.mainThreadDispatcher().timeSource(), @@ -322,7 +323,8 @@ class TlsSessionTicketKeysSdsApi : public SdsApi, public TlsSessionTicketKeysCon // We need to do this early as we invoke the subscription factory during initialization, which // is too late to throw. auto& server_context = secret_provider_context.serverFactoryContext(); - Config::Utility::checkLocalInfo("TlsSessionTicketKeysSdsApi", server_context.localInfo()); + THROW_IF_NOT_OK( + Config::Utility::checkLocalInfo("TlsSessionTicketKeysSdsApi", server_context.localInfo())); return std::make_shared( sds_config, sds_config_name, secret_provider_context.clusterManager().subscriptionFactory(), server_context.mainThreadDispatcher().timeSource(), @@ -395,7 +397,8 @@ class GenericSecretSdsApi : public SdsApi, public GenericSecretConfigProvider { // We need to do this early as we invoke the subscription factory during initialization, which // is too late to throw. auto& server_context = secret_provider_context.serverFactoryContext(); - Config::Utility::checkLocalInfo("GenericSecretSdsApi", server_context.localInfo()); + THROW_IF_NOT_OK( + Config::Utility::checkLocalInfo("GenericSecretSdsApi", server_context.localInfo())); return std::make_shared( sds_config, sds_config_name, secret_provider_context.clusterManager().subscriptionFactory(), server_context.mainThreadDispatcher().timeSource(), diff --git a/source/common/stream_info/BUILD b/source/common/stream_info/BUILD index 9acfe214baaf9..452ccb42d0123 100644 --- a/source/common/stream_info/BUILD +++ b/source/common/stream_info/BUILD @@ -14,6 +14,7 @@ envoy_cc_library( deps = [ ":filter_state_lib", ":stream_id_provider_lib", + ":utility_lib", "//envoy/http:request_id_extension_interface", "//envoy/stream_info:stream_info_interface", "//source/common/common:assert_lib", @@ -37,7 +38,10 @@ envoy_cc_library( name = "utility_lib", srcs = ["utility.cc"], hdrs = ["utility.h"], - external_deps = ["abseil_optional"], + external_deps = [ + "abseil_optional", + "abseil_node_hash_map", + ], deps = [ "//envoy/common:time_interface", "//envoy/http:codes_interface", diff --git a/source/common/stream_info/stream_info_impl.h b/source/common/stream_info/stream_info_impl.h index 5d1494640824d..fdbd250c75c77 100644 --- a/source/common/stream_info/stream_info_impl.h +++ b/source/common/stream_info/stream_info_impl.h @@ -21,6 +21,7 @@ #include "source/common/runtime/runtime_features.h" #include "source/common/stream_info/filter_state_impl.h" #include "source/common/stream_info/stream_id_provider_impl.h" +#include "source/common/stream_info/utility.h" #include "absl/strings/str_replace.h" @@ -231,17 +232,31 @@ struct StreamInfoImpl : public StreamInfo { uint64_t bytesSent() const override { return bytes_sent_; } - void setResponseFlag(ResponseFlag response_flag) override { response_flags_ |= response_flag; } + void setResponseFlag(ResponseFlag flag) override { + ASSERT(flag.value() < ResponseFlagUtils::responseFlagsVec().size()); + if (!hasResponseFlag(flag)) { + response_flags_.push_back(flag); + } + } - bool intersectResponseFlags(uint64_t response_flags) const override { - return (response_flags_ & response_flags) != 0; + bool hasResponseFlag(ResponseFlag flag) const override { + return std::find(response_flags_.begin(), response_flags_.end(), flag) != response_flags_.end(); } - bool hasResponseFlag(ResponseFlag flag) const override { return response_flags_ & flag; } + bool hasAnyResponseFlag() const override { return !response_flags_.empty(); } - bool hasAnyResponseFlag() const override { return response_flags_ != 0; } + absl::Span responseFlags() const override { return response_flags_; } - uint64_t responseFlags() const override { return response_flags_; } + uint64_t legacyResponseFlags() const override { + uint64_t legacy_flags = 0; + for (ResponseFlag flag : response_flags_) { + if (flag.value() <= static_cast(CoreResponseFlag::LastFlag)) { + ASSERT(flag.value() < 64, "Legacy response flag out of range"); + legacy_flags |= (1UL << flag.value()); + } + } + return legacy_flags; + } const std::string& getRouteName() const override { return route_ != nullptr ? route_->routeName() : EMPTY_STRING; @@ -374,7 +389,10 @@ struct StreamInfoImpl : public StreamInfo { // derive final time from other info's complete duration and start time. final_time_ = info.startTimeMonotonic() + info.requestComplete().value(); } - response_flags_ = info.responseFlags(); + response_flags_.clear(); + auto other_response_flags = info.responseFlags(); + response_flags_.insert(response_flags_.end(), other_response_flags.begin(), + other_response_flags.end()); health_check_request_ = info.healthCheck(); route_ = info.route(); metadata_ = info.dynamicMetadata(); @@ -423,7 +441,7 @@ struct StreamInfoImpl : public StreamInfo { public: absl::optional response_code_details_; absl::optional connection_termination_details_; - uint64_t response_flags_{}; + absl::InlinedVector response_flags_{}; bool health_check_request_{}; Router::RouteConstSharedPtr route_; envoy::config::core::v3::Metadata metadata_{}; diff --git a/source/common/stream_info/utility.cc b/source/common/stream_info/utility.cc index 61304c9ad94c4..4045a45981b60 100644 --- a/source/common/stream_info/utility.cc +++ b/source/common/stream_info/utility.cc @@ -12,6 +12,16 @@ namespace Envoy { namespace StreamInfo { +namespace { + +// This flag is used to ensure that the responseFlagsVec() contains all the flags and no +// any new custom flags are registered after the responseFlagsVec() is initialized. +// NOTE: we expect all registrations of custom flags to happen during static initialization +// before the first use of responseFlagsVec(). So no thread safety is needed here. +bool& responseFlagsVecInitialized() { MUTABLE_CONSTRUCT_ON_FIRST_USE(bool, false); } + +} // namespace + const std::string ResponseFlagUtils::toString(const StreamInfo& stream_info) { return toString(stream_info, true); } @@ -24,11 +34,14 @@ const std::string ResponseFlagUtils::toString(const StreamInfo& stream_info, boo // We don't expect more than 4 flags are set. Relax to 16 since the vector is allocated on stack // anyway. absl::InlinedVector flag_strings_vec; - for (const auto& [flag_strings, flag] : ALL_RESPONSE_STRINGS_FLAGS) { - if (stream_info.hasResponseFlag(flag)) { - flag_strings_vec.push_back(use_long_name ? flag_strings.long_string_ - : flag_strings.short_string_); - } + + const auto& all_flag_strings = responseFlagsVec(); + for (const auto flag : stream_info.responseFlags()) { + ASSERT(flag.value() < all_flag_strings.size(), "Flag value out of range"); + + const auto flag_strings = all_flag_strings[flag.value()]; + flag_strings_vec.push_back(use_long_name ? flag_strings.long_string_ + : flag_strings.short_string_); } if (flag_strings_vec.empty()) { return std::string(NONE); @@ -36,29 +49,84 @@ const std::string ResponseFlagUtils::toString(const StreamInfo& stream_info, boo return absl::StrJoin(flag_strings_vec, ","); } -absl::flat_hash_map ResponseFlagUtils::getFlagMap() { - static_assert(ResponseFlag::LastFlag == 0x8000000, - "A flag has been added. Add the new flag to ALL_RESPONSE_STRINGS_FLAGS."); - absl::flat_hash_map res; - for (auto [flag_strings, flag] : ResponseFlagUtils::ALL_RESPONSE_STRINGS_FLAGS) { - res.emplace(flag_strings.short_string_, flag); - } - return res; +ResponseFlagUtils::ResponseFlagsMapType& ResponseFlagUtils::mutableResponseFlagsMap() { + MUTABLE_CONSTRUCT_ON_FIRST_USE(ResponseFlagsMapType, []() { + ResponseFlagsMapType map; + // Initialize the map with the all core flags first to ensure no custom flags + // conflict with them. + RELEASE_ASSERT(CORE_RESPONSE_FLAGS.size() == CoreResponseFlag::LastFlag + 1, + "Not all inlined flags are contained by CORE_RESPONSE_FLAGS."); + + map.reserve(CORE_RESPONSE_FLAGS.size()); + for (const auto& flag : CORE_RESPONSE_FLAGS) { + map.emplace(flag.short_string_, FlagLongString{flag.flag_, std::string(flag.long_string_)}); + } + RELEASE_ASSERT(map.size() == CORE_RESPONSE_FLAGS.size(), + "Duplicate flags in CORE_RESPONSE_FLAGS"); + return map; + }()); +} + +ResponseFlag ResponseFlagUtils::registerCustomFlag(absl::string_view custom_flag, + absl::string_view custom_flag_long) { + auto& mutable_flags = mutableResponseFlagsMap(); + + RELEASE_ASSERT(!responseFlagsVecInitialized(), + "Cannot register custom flags after initialization"); + + RELEASE_ASSERT(!mutable_flags.contains(custom_flag), + fmt::format("Flag: {}/{} already registered", custom_flag, custom_flag_long)); + + const uint16_t next_flag = mutable_flags.size(); + + mutable_flags.emplace(custom_flag, FlagLongString{next_flag, std::string(custom_flag_long)}); + + return next_flag; +} + +const ResponseFlagUtils::ResponseFlagsVecType& ResponseFlagUtils::responseFlagsVec() { + CONSTRUCT_ON_FIRST_USE(ResponseFlagsVecType, []() { + static_assert(CoreResponseFlag::LastFlag == 27, + "A flag has been added. Add the new flag to CORE_RESPONSE_FLAGS."); + + responseFlagsVecInitialized() = true; + + ResponseFlagsVecType res; + + uint16_t max_flag = CoreResponseFlag::LastFlag; + for (const auto& flag : responseFlagsMap()) { + if (flag.second.flag_.value() > max_flag) { + max_flag = flag.second.flag_.value(); + } + } + + res.resize(max_flag + 1); + + for (const auto& flag : responseFlagsMap()) { + res[flag.second.flag_.value()] = {absl::string_view(flag.first), + absl::string_view(flag.second.long_string_), + flag.second.flag_}; + } + + return res; + }()); +} + +const ResponseFlagUtils::ResponseFlagsMapType& ResponseFlagUtils::responseFlagsMap() { + return mutableResponseFlagsMap(); } absl::optional ResponseFlagUtils::toResponseFlag(absl::string_view flag) { - // This `MapType` is introduce because CONSTRUCT_ON_FIRST_USE doesn't like template. - using MapType = absl::flat_hash_map; - const auto& flag_map = []() { - CONSTRUCT_ON_FIRST_USE(MapType, ResponseFlagUtils::getFlagMap()); - }(); - const auto& it = flag_map.find(flag); - if (it != flag_map.end()) { - return absl::make_optional(it->second); + const auto iter = responseFlagsMap().find(flag); + if (iter != responseFlagsMap().end()) { + return iter->second.flag_; } return absl::nullopt; } +CustomResponseFlag::CustomResponseFlag(absl::string_view flag, absl::string_view flag_long) + : flag_(ResponseFlagUtils::registerCustomFlag(flag, flag_long)) {} + OptRef getUpstreamTiming(const StreamInfo& stream_info) { OptRef info = stream_info.upstreamInfo(); if (!info.has_value()) { @@ -358,53 +426,53 @@ ProxyStatusUtils::proxyStatusErrorToString(const ProxyStatusError proxy_status) const absl::optional ProxyStatusUtils::fromStreamInfo(const StreamInfo& stream_info) { - // NB: This mapping from Envoy-specific ResponseFlag enum to Proxy-Status - // error enum is lossy, since ResponseFlag is really a bitset of many - // ResponseFlag enums. Here, we search the list of all known ResponseFlag values in + // NB: This mapping from Envoy-specific CoreResponseFlag enum to Proxy-Status + // error enum is lossy, since CoreResponseFlag is really a bitset of many + // CoreResponseFlag enums. Here, we search the list of all known CoreResponseFlag values in // enum order, returning the first matching ProxyStatusError. - if (stream_info.hasResponseFlag(ResponseFlag::FailedLocalHealthCheck)) { + if (stream_info.hasResponseFlag(CoreResponseFlag::FailedLocalHealthCheck)) { return ProxyStatusError::DestinationUnavailable; - } else if (stream_info.hasResponseFlag(ResponseFlag::NoHealthyUpstream)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::NoHealthyUpstream)) { return ProxyStatusError::DestinationUnavailable; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamRequestTimeout)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamRequestTimeout)) { if (!Runtime::runtimeFeatureEnabled( "envoy.reloadable_features.proxy_status_upstream_request_timeout")) { return ProxyStatusError::ConnectionTimeout; } return ProxyStatusError::HttpResponseTimeout; - } else if (stream_info.hasResponseFlag(ResponseFlag::LocalReset)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::LocalReset)) { return ProxyStatusError::ConnectionTimeout; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamRemoteReset)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamRemoteReset)) { return ProxyStatusError::ConnectionTerminated; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamConnectionFailure)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamConnectionFailure)) { return ProxyStatusError::ConnectionRefused; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamConnectionTermination)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamConnectionTermination)) { return ProxyStatusError::ConnectionTerminated; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamOverflow)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamOverflow)) { return ProxyStatusError::ConnectionLimitReached; - } else if (stream_info.hasResponseFlag(ResponseFlag::NoRouteFound)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::NoRouteFound)) { return ProxyStatusError::DestinationNotFound; - } else if (stream_info.hasResponseFlag(ResponseFlag::RateLimited)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::RateLimited)) { return ProxyStatusError::ConnectionLimitReached; - } else if (stream_info.hasResponseFlag(ResponseFlag::RateLimitServiceError)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::RateLimitServiceError)) { return ProxyStatusError::ConnectionLimitReached; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamRetryLimitExceeded)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamRetryLimitExceeded)) { return ProxyStatusError::DestinationUnavailable; - } else if (stream_info.hasResponseFlag(ResponseFlag::StreamIdleTimeout)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::StreamIdleTimeout)) { return ProxyStatusError::HttpResponseTimeout; - } else if (stream_info.hasResponseFlag(ResponseFlag::InvalidEnvoyRequestHeaders)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::InvalidEnvoyRequestHeaders)) { return ProxyStatusError::HttpRequestError; - } else if (stream_info.hasResponseFlag(ResponseFlag::DownstreamProtocolError)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::DownstreamProtocolError)) { return ProxyStatusError::HttpRequestError; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamMaxStreamDurationReached)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamMaxStreamDurationReached)) { return ProxyStatusError::HttpResponseTimeout; - } else if (stream_info.hasResponseFlag(ResponseFlag::NoFilterConfigFound)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::NoFilterConfigFound)) { return ProxyStatusError::ProxyConfigurationError; - } else if (stream_info.hasResponseFlag(ResponseFlag::UpstreamProtocolError)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::UpstreamProtocolError)) { return ProxyStatusError::HttpProtocolError; - } else if (stream_info.hasResponseFlag(ResponseFlag::NoClusterFound)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::NoClusterFound)) { return ProxyStatusError::DestinationUnavailable; - } else if (stream_info.hasResponseFlag(ResponseFlag::DnsResolutionFailed)) { + } else if (stream_info.hasResponseFlag(CoreResponseFlag::DnsResolutionFailed)) { return ProxyStatusError::DnsError; } else { return absl::nullopt; diff --git a/source/common/stream_info/utility.h b/source/common/stream_info/utility.h index e7794165b5003..a516bdae567e7 100644 --- a/source/common/stream_info/utility.h +++ b/source/common/stream_info/utility.h @@ -7,9 +7,43 @@ #include "envoy/http/codes.h" #include "envoy/stream_info/stream_info.h" +#include "absl/container/node_hash_map.h" + namespace Envoy { namespace StreamInfo { +class CustomResponseFlag { +public: + CustomResponseFlag(absl::string_view flag, absl::string_view flag_long); + ResponseFlag flag() const { return flag_; } + +private: + ResponseFlag flag_; +}; + +// Register a custom response flag by specifying the flag and the long name of the flag. +// This macro should only be used in source files to register a flag. +#define REGISTER_CUSTOM_RESPONSE_FLAG(flag_short_string, flag_long_string) \ + static CustomResponseFlag /* NOLINT(fuchsia-statically-constructed-objects) */ \ + registered_##flag_short_string{#flag_short_string, #flag_long_string}; + +// Get the registered flag value. This macro should only be used when calling the +// 'setResponseFlag' method in the StreamInfo class. +// NOTE: Never use this macro to initialize another static variable. +// Basically, this macro should only be used in the same source file where the flag is +// registered. +// If you want to use one flag in multiple files, you can declare a static function in +// the header file and define it in the source file to return the flag value. Here is an +// example (NOTE: this function should obey the same rule as the CUSTOM_RESPONSE_FLAG +// macro and cannot be used to initialize another static variable): +// +// // header.h +// ResponseFlag getRegisteredFlag(); +// // source.cc +// REGISTER_CUSTOM_RESPONSE_FLAG(CF, CustomFlag); +// ResponseFlag getRegisteredFlag() { return CUSTOM_RESPONSE_FLAG(CF); } +#define CUSTOM_RESPONSE_FLAG(flag_short_string) registered_##flag_short_string.flag() + /** * Util class for ResponseFlags. */ @@ -20,14 +54,26 @@ class ResponseFlagUtils { static absl::optional toResponseFlag(absl::string_view response_flag); struct FlagStrings { - const absl::string_view short_string_; - const absl::string_view long_string_; // PascalCase string + absl::string_view short_string_; + absl::string_view long_string_; // PascalCase string + ResponseFlag flag_; + }; + + struct FlagLongString { + ResponseFlag flag_; + std::string long_string_; // PascalCase string }; - using FlagStringsAndEnum = std::pair; + using ResponseFlagsVecType = std::vector; + // Node hash map is used to avoid the key/value pair pointer change of the string_view when the + // map is resized. And the performance is not a concern here because the map is only used when + // loading the config. + using ResponseFlagsMapType = absl::node_hash_map; + static const ResponseFlagsVecType& responseFlagsVec(); + static const ResponseFlagsMapType& responseFlagsMap(); // When adding a new flag, it's required to update the access log docs and the string - // mapping below - ``ALL_RESPONSE_STRINGS_FLAGS``. + // mapping below - ``CORE_RESPONSE_FLAGS``. constexpr static absl::string_view NONE = "-"; constexpr static absl::string_view DOWNSTREAM_CONNECTION_TERMINATION = "DC"; constexpr static absl::string_view FAILED_LOCAL_HEALTH_CHECK = "LH"; @@ -93,61 +139,69 @@ class ResponseFlagUtils { constexpr static absl::string_view DNS_FAIL_LONG = "DnsResolutionFailed"; constexpr static absl::string_view DROP_OVERLOAD_LONG = "DropOverload"; - static constexpr std::array ALL_RESPONSE_STRINGS_FLAGS{ - FlagStringsAndEnum{{FAILED_LOCAL_HEALTH_CHECK, FAILED_LOCAL_HEALTH_CHECK_LONG}, - ResponseFlag::FailedLocalHealthCheck}, - FlagStringsAndEnum{{NO_HEALTHY_UPSTREAM, NO_HEALTHY_UPSTREAM_LONG}, - ResponseFlag::NoHealthyUpstream}, - FlagStringsAndEnum{{UPSTREAM_REQUEST_TIMEOUT, UPSTREAM_REQUEST_TIMEOUT_LONG}, - ResponseFlag::UpstreamRequestTimeout}, - FlagStringsAndEnum{{LOCAL_RESET, LOCAL_RESET_LONG}, ResponseFlag::LocalReset}, - FlagStringsAndEnum{{UPSTREAM_REMOTE_RESET, UPSTREAM_REMOTE_RESET_LONG}, - ResponseFlag::UpstreamRemoteReset}, - FlagStringsAndEnum{{UPSTREAM_CONNECTION_FAILURE, UPSTREAM_CONNECTION_FAILURE_LONG}, - ResponseFlag::UpstreamConnectionFailure}, - FlagStringsAndEnum{{UPSTREAM_CONNECTION_TERMINATION, UPSTREAM_CONNECTION_TERMINATION_LONG}, - ResponseFlag::UpstreamConnectionTermination}, - FlagStringsAndEnum{{UPSTREAM_OVERFLOW, UPSTREAM_OVERFLOW_LONG}, - ResponseFlag::UpstreamOverflow}, - FlagStringsAndEnum{{NO_ROUTE_FOUND, NO_ROUTE_FOUND_LONG}, ResponseFlag::NoRouteFound}, - FlagStringsAndEnum{{DELAY_INJECTED, DELAY_INJECTED_LONG}, ResponseFlag::DelayInjected}, - FlagStringsAndEnum{{FAULT_INJECTED, FAULT_INJECTED_LONG}, ResponseFlag::FaultInjected}, - FlagStringsAndEnum{{RATE_LIMITED, RATE_LIMITED_LONG}, ResponseFlag::RateLimited}, - FlagStringsAndEnum{{UNAUTHORIZED_EXTERNAL_SERVICE, UNAUTHORIZED_EXTERNAL_SERVICE_LONG}, - ResponseFlag::UnauthorizedExternalService}, - FlagStringsAndEnum{{RATELIMIT_SERVICE_ERROR, RATELIMIT_SERVICE_ERROR_LONG}, - ResponseFlag::RateLimitServiceError}, - FlagStringsAndEnum{ - {DOWNSTREAM_CONNECTION_TERMINATION, DOWNSTREAM_CONNECTION_TERMINATION_LONG}, - ResponseFlag::DownstreamConnectionTermination}, - FlagStringsAndEnum{{UPSTREAM_RETRY_LIMIT_EXCEEDED, UPSTREAM_RETRY_LIMIT_EXCEEDED_LONG}, - ResponseFlag::UpstreamRetryLimitExceeded}, - FlagStringsAndEnum{{STREAM_IDLE_TIMEOUT, STREAM_IDLE_TIMEOUT_LONG}, - ResponseFlag::StreamIdleTimeout}, - FlagStringsAndEnum{{INVALID_ENVOY_REQUEST_HEADERS, INVALID_ENVOY_REQUEST_HEADERS_LONG}, - ResponseFlag::InvalidEnvoyRequestHeaders}, - FlagStringsAndEnum{{DOWNSTREAM_PROTOCOL_ERROR, DOWNSTREAM_PROTOCOL_ERROR_LONG}, - ResponseFlag::DownstreamProtocolError}, - FlagStringsAndEnum{ - {UPSTREAM_MAX_STREAM_DURATION_REACHED, UPSTREAM_MAX_STREAM_DURATION_REACHED_LONG}, - ResponseFlag::UpstreamMaxStreamDurationReached}, - FlagStringsAndEnum{{RESPONSE_FROM_CACHE_FILTER, RESPONSE_FROM_CACHE_FILTER_LONG}, - ResponseFlag::ResponseFromCacheFilter}, - FlagStringsAndEnum{{NO_FILTER_CONFIG_FOUND, NO_FILTER_CONFIG_FOUND_LONG}, - ResponseFlag::NoFilterConfigFound}, - FlagStringsAndEnum{{DURATION_TIMEOUT, DURATION_TIMEOUT_LONG}, ResponseFlag::DurationTimeout}, - FlagStringsAndEnum{{UPSTREAM_PROTOCOL_ERROR, UPSTREAM_PROTOCOL_ERROR_LONG}, - ResponseFlag::UpstreamProtocolError}, - FlagStringsAndEnum{{NO_CLUSTER_FOUND, NO_CLUSTER_FOUND_LONG}, ResponseFlag::NoClusterFound}, - FlagStringsAndEnum{{OVERLOAD_MANAGER, OVERLOAD_MANAGER_LONG}, ResponseFlag::OverloadManager}, - FlagStringsAndEnum{{DNS_FAIL, DNS_FAIL_LONG}, ResponseFlag::DnsResolutionFailed}, - FlagStringsAndEnum{{DROP_OVERLOAD, DROP_OVERLOAD_LONG}, ResponseFlag::DropOverLoad}, + static constexpr std::array CORE_RESPONSE_FLAGS{ + FlagStrings{FAILED_LOCAL_HEALTH_CHECK, FAILED_LOCAL_HEALTH_CHECK_LONG, + CoreResponseFlag::FailedLocalHealthCheck}, + FlagStrings{NO_HEALTHY_UPSTREAM, NO_HEALTHY_UPSTREAM_LONG, + CoreResponseFlag::NoHealthyUpstream}, + FlagStrings{UPSTREAM_REQUEST_TIMEOUT, UPSTREAM_REQUEST_TIMEOUT_LONG, + CoreResponseFlag::UpstreamRequestTimeout}, + FlagStrings{LOCAL_RESET, LOCAL_RESET_LONG, CoreResponseFlag::LocalReset}, + FlagStrings{UPSTREAM_REMOTE_RESET, UPSTREAM_REMOTE_RESET_LONG, + CoreResponseFlag::UpstreamRemoteReset}, + FlagStrings{UPSTREAM_CONNECTION_FAILURE, UPSTREAM_CONNECTION_FAILURE_LONG, + CoreResponseFlag::UpstreamConnectionFailure}, + FlagStrings{UPSTREAM_CONNECTION_TERMINATION, UPSTREAM_CONNECTION_TERMINATION_LONG, + CoreResponseFlag::UpstreamConnectionTermination}, + FlagStrings{UPSTREAM_OVERFLOW, UPSTREAM_OVERFLOW_LONG, CoreResponseFlag::UpstreamOverflow}, + FlagStrings{NO_ROUTE_FOUND, NO_ROUTE_FOUND_LONG, CoreResponseFlag::NoRouteFound}, + FlagStrings{DELAY_INJECTED, DELAY_INJECTED_LONG, CoreResponseFlag::DelayInjected}, + FlagStrings{FAULT_INJECTED, FAULT_INJECTED_LONG, CoreResponseFlag::FaultInjected}, + FlagStrings{RATE_LIMITED, RATE_LIMITED_LONG, CoreResponseFlag::RateLimited}, + FlagStrings{UNAUTHORIZED_EXTERNAL_SERVICE, UNAUTHORIZED_EXTERNAL_SERVICE_LONG, + CoreResponseFlag::UnauthorizedExternalService}, + FlagStrings{RATELIMIT_SERVICE_ERROR, RATELIMIT_SERVICE_ERROR_LONG, + CoreResponseFlag::RateLimitServiceError}, + FlagStrings{DOWNSTREAM_CONNECTION_TERMINATION, DOWNSTREAM_CONNECTION_TERMINATION_LONG, + CoreResponseFlag::DownstreamConnectionTermination}, + FlagStrings{UPSTREAM_RETRY_LIMIT_EXCEEDED, UPSTREAM_RETRY_LIMIT_EXCEEDED_LONG, + CoreResponseFlag::UpstreamRetryLimitExceeded}, + FlagStrings{STREAM_IDLE_TIMEOUT, STREAM_IDLE_TIMEOUT_LONG, + CoreResponseFlag::StreamIdleTimeout}, + FlagStrings{INVALID_ENVOY_REQUEST_HEADERS, INVALID_ENVOY_REQUEST_HEADERS_LONG, + CoreResponseFlag::InvalidEnvoyRequestHeaders}, + FlagStrings{DOWNSTREAM_PROTOCOL_ERROR, DOWNSTREAM_PROTOCOL_ERROR_LONG, + CoreResponseFlag::DownstreamProtocolError}, + FlagStrings{UPSTREAM_MAX_STREAM_DURATION_REACHED, UPSTREAM_MAX_STREAM_DURATION_REACHED_LONG, + CoreResponseFlag::UpstreamMaxStreamDurationReached}, + FlagStrings{RESPONSE_FROM_CACHE_FILTER, RESPONSE_FROM_CACHE_FILTER_LONG, + CoreResponseFlag::ResponseFromCacheFilter}, + FlagStrings{NO_FILTER_CONFIG_FOUND, NO_FILTER_CONFIG_FOUND_LONG, + CoreResponseFlag::NoFilterConfigFound}, + FlagStrings{DURATION_TIMEOUT, DURATION_TIMEOUT_LONG, CoreResponseFlag::DurationTimeout}, + FlagStrings{UPSTREAM_PROTOCOL_ERROR, UPSTREAM_PROTOCOL_ERROR_LONG, + CoreResponseFlag::UpstreamProtocolError}, + FlagStrings{NO_CLUSTER_FOUND, NO_CLUSTER_FOUND_LONG, CoreResponseFlag::NoClusterFound}, + FlagStrings{OVERLOAD_MANAGER, OVERLOAD_MANAGER_LONG, CoreResponseFlag::OverloadManager}, + FlagStrings{DNS_FAIL, DNS_FAIL_LONG, CoreResponseFlag::DnsResolutionFailed}, + FlagStrings{DROP_OVERLOAD, DROP_OVERLOAD_LONG, CoreResponseFlag::DropOverLoad}, }; private: - ResponseFlagUtils(); + friend class CustomResponseFlag; + static const std::string toString(const StreamInfo& stream_info, bool use_long_name); - static absl::flat_hash_map getFlagMap(); + + /** + * Register a custom response flag. + * @param flag supplies the flag to register. It should be an all upper case string with only + * multiple characters. + * @param flag_long supplies the long name of the flag to register. It should be PascalCase + * string. + * @return uint16_t the flag value. + */ + static ResponseFlag registerCustomFlag(absl::string_view flag, absl::string_view flag_long); + static ResponseFlagsMapType& mutableResponseFlagsMap(); }; class TimingUtility { diff --git a/source/common/tcp_proxy/tcp_proxy.cc b/source/common/tcp_proxy/tcp_proxy.cc index 15f24fe8d7431..4f87dd6ae37aa 100644 --- a/source/common/tcp_proxy/tcp_proxy.cc +++ b/source/common/tcp_proxy/tcp_proxy.cc @@ -417,7 +417,7 @@ Network::FilterStatus Filter::establishUpstreamConnection() { ENVOY_CONN_LOG(debug, "Cluster not found {} and no on demand cluster set.", read_callbacks_->connection(), cluster_name); config_->stats().downstream_cx_no_route_.inc(); - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoClusterFound); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoClusterFound); onInitFailure(UpstreamFailureReason::NoRoute); } else { ASSERT(!cluster_discovery_handle_); @@ -445,7 +445,7 @@ Network::FilterStatus Filter::establishUpstreamConnection() { // Check this here because the TCP conn pool will queue our request waiting for a connection that // will never be released. if (!cluster->resourceManager(Upstream::ResourcePriority::Default).connections().canCreate()) { - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); cluster->trafficStats()->upstream_cx_overflow_.inc(); onInitFailure(UpstreamFailureReason::ResourceLimitExceeded); return Network::FilterStatus::StopIteration; @@ -453,7 +453,7 @@ Network::FilterStatus Filter::establishUpstreamConnection() { const uint32_t max_connect_attempts = config_->maxConnectAttempts(); if (connect_attempts_ >= max_connect_attempts) { - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded); cluster->trafficStats()->upstream_cx_connect_attempts_exceeded_.inc(); onInitFailure(UpstreamFailureReason::ConnectFailed); return Network::FilterStatus::StopIteration; @@ -487,7 +487,7 @@ Network::FilterStatus Filter::establishUpstreamConnection() { if (!maybeTunnel(*thread_local_cluster)) { // Either cluster is unknown or there are no healthy hosts. tcpConnPool() increments // cluster->trafficStats()->upstream_cx_none_healthy in the latter case. - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream); onInitFailure(UpstreamFailureReason::NoHealthyUpstream); } return Network::FilterStatus::StopIteration; @@ -520,7 +520,7 @@ void Filter::onClusterDiscoveryCompletion(Upstream::ClusterDiscoveryStatus clust } // Failure path. config_->stats().downstream_cx_no_route_.inc(); - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoClusterFound); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoClusterFound); onInitFailure(UpstreamFailureReason::NoRoute); } @@ -667,7 +667,7 @@ void TunnelingConfigHelperImpl::propagateResponseHeaders( } filter_state->setData( TunnelResponseHeaders::key(), std::make_shared(std::move(headers)), - StreamInfo::FilterState::StateType::ReadOnly, StreamInfo::FilterState::LifeSpan::Connection); + StreamInfo::FilterState::StateType::Mutable, StreamInfo::FilterState::LifeSpan::Connection); } void TunnelingConfigHelperImpl::propagateResponseTrailers( @@ -685,7 +685,7 @@ void Filter::onConnectTimeout() { ENVOY_CONN_LOG(debug, "connect timeout", read_callbacks_->connection()); read_callbacks_->upstreamHost()->outlierDetector().putResult( Upstream::Outlier::Result::LocalOriginTimeout); - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); // Raise LocalClose, which will trigger a reconnect if needed/configured. upstream_callbacks_->onEvent(Network::ConnectionEvent::LocalClose); @@ -799,7 +799,7 @@ void Filter::onUpstreamEvent(Network::ConnectionEvent event) { if (connecting) { if (event == Network::ConnectionEvent::RemoteClose) { - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); read_callbacks_->upstreamHost()->outlierDetector().putResult( Upstream::Outlier::Result::LocalOriginConnectFailed); } @@ -864,7 +864,7 @@ void Filter::onIdleTimeout() { void Filter::onMaxDownstreamConnectionDuration() { ENVOY_CONN_LOG(debug, "max connection duration reached", read_callbacks_->connection()); - getStreamInfo().setResponseFlag(StreamInfo::ResponseFlag::DurationTimeout); + getStreamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::DurationTimeout); config_->stats().max_downstream_connection_duration_.inc(); read_callbacks_->connection().close( Network::ConnectionCloseType::NoFlush, diff --git a/source/common/upstream/cluster_manager_impl.cc b/source/common/upstream/cluster_manager_impl.cc index d5cf2c62dc7c1..4a2a4f076afa9 100644 --- a/source/common/upstream/cluster_manager_impl.cc +++ b/source/common/upstream/cluster_manager_impl.cc @@ -424,11 +424,12 @@ absl::Status ClusterManagerImpl::init(const envoy::config::bootstrap::v3::Bootst validation_context_.dynamicValidationVisitor(), server_, dyn_resources.ads_config().config_validators()); - JitteredExponentialBackOffStrategyPtr backoff_strategy = - Config::Utility::prepareJitteredExponentialBackOffStrategy( - dyn_resources.ads_config(), random_, - Envoy::Config::SubscriptionFactory::RetryInitialDelayMs, - Envoy::Config::SubscriptionFactory::RetryMaxDelayMs); + auto strategy_or_error = Config::Utility::prepareJitteredExponentialBackOffStrategy( + dyn_resources.ads_config(), random_, + Envoy::Config::SubscriptionFactory::RetryInitialDelayMs, + Envoy::Config::SubscriptionFactory::RetryMaxDelayMs); + THROW_IF_STATUS_NOT_OK(strategy_or_error, throw); + JitteredExponentialBackOffStrategyPtr backoff_strategy = std::move(strategy_or_error.value()); const bool use_eds_cache = Runtime::runtimeFeatureEnabled("envoy.restart_features.use_eds_cache_for_ads"); @@ -446,13 +447,14 @@ absl::Status ClusterManagerImpl::init(const envoy::config::bootstrap::v3::Bootst if (!factory) { return absl::InvalidArgumentError(fmt::format("{} not found", name)); } - ads_mux_ = factory->create( - Config::Utility::factoryForGrpcApiConfigSource( - *async_client_manager_, dyn_resources.ads_config(), *stats_.rootScope(), false) - ->createUncachedRawAsyncClient(), - dispatcher_, random_, *stats_.rootScope(), dyn_resources.ads_config(), local_info_, - std::move(custom_config_validators), std::move(backoff_strategy), - makeOptRefFromPtr(xds_config_tracker_.get()), {}, use_eds_cache); + auto factory_or_error = Config::Utility::factoryForGrpcApiConfigSource( + *async_client_manager_, dyn_resources.ads_config(), *stats_.rootScope(), false); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); + ads_mux_ = + factory->create(factory_or_error.value()->createUncachedRawAsyncClient(), dispatcher_, + random_, *stats_.rootScope(), dyn_resources.ads_config(), local_info_, + std::move(custom_config_validators), std::move(backoff_strategy), + makeOptRefFromPtr(xds_config_tracker_.get()), {}, use_eds_cache); } else { absl::Status status = Config::Utility::checkTransportVersion(dyn_resources.ads_config()); RETURN_IF_NOT_OK(status); @@ -468,11 +470,12 @@ absl::Status ClusterManagerImpl::init(const envoy::config::bootstrap::v3::Bootst if (!factory) { return absl::InvalidArgumentError(fmt::format("{} not found", name)); } + auto factory_or_error = Config::Utility::factoryForGrpcApiConfigSource( + *async_client_manager_, dyn_resources.ads_config(), *stats_.rootScope(), false); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); ads_mux_ = factory->create( - Config::Utility::factoryForGrpcApiConfigSource( - *async_client_manager_, dyn_resources.ads_config(), *stats_.rootScope(), false) - ->createUncachedRawAsyncClient(), - dispatcher_, random_, *stats_.rootScope(), dyn_resources.ads_config(), local_info_, + factory_or_error.value()->createUncachedRawAsyncClient(), dispatcher_, random_, + *stats_.rootScope(), dyn_resources.ads_config(), local_info_, std::move(custom_config_validators), std::move(backoff_strategy), makeOptRefFromPtr(xds_config_tracker_.get()), xds_delegate_opt_ref, use_eds_cache); } @@ -561,12 +564,12 @@ absl::Status ClusterManagerImpl::initializeSecondaryClusters( absl::Status status = Config::Utility::checkTransportVersion(load_stats_config); RETURN_IF_NOT_OK(status); + auto factory_or_error = Config::Utility::factoryForGrpcApiConfigSource( + *async_client_manager_, load_stats_config, *stats_.rootScope(), false); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); load_stats_reporter_ = std::make_unique( local_info_, *this, *stats_.rootScope(), - Config::Utility::factoryForGrpcApiConfigSource(*async_client_manager_, load_stats_config, - *stats_.rootScope(), false) - ->createUncachedRawAsyncClient(), - dispatcher_); + factory_or_error.value()->createUncachedRawAsyncClient(), dispatcher_); } return absl::OkStatus(); } @@ -1023,16 +1026,14 @@ void ClusterManagerImpl::updateClusterCounts() { init_helper_.state() == ClusterManagerInitHelper::State::AllClustersInitialized; if (all_clusters_initialized && ads_mux_) { const auto type_url = Config::getTypeUrl(); - if (last_recorded_warming_clusters_count_ == 0 && !warming_clusters_.empty()) { + if (resume_cds_ == nullptr && !warming_clusters_.empty()) { resume_cds_ = ads_mux_->pause(type_url); - } else if (last_recorded_warming_clusters_count_ > 0 && warming_clusters_.empty()) { - ASSERT(resume_cds_ != nullptr); + } else if (warming_clusters_.empty()) { resume_cds_.reset(); } } cm_stats_.active_clusters_.set(active_clusters_.size()); cm_stats_.warming_clusters_.set(warming_clusters_.size()); - last_recorded_warming_clusters_count_ = warming_clusters_.size(); } ThreadLocalCluster* ClusterManagerImpl::getThreadLocalCluster(absl::string_view cluster) { @@ -1535,13 +1536,13 @@ void ClusterManagerImpl::ThreadLocalClusterManagerImpl::ClusterEntry::updateHost const std::string& name, uint32_t priority, PrioritySet::UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, absl::optional weighted_priority_health, + const HostVector& hosts_removed, uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor, HostMapConstSharedPtr cross_priority_host_map) { ENVOY_LOG(debug, "membership update for TLS cluster {} added {} removed {}", name, hosts_added.size(), hosts_removed.size()); priority_set_.updateHosts(priority, std::move(update_hosts_params), std::move(locality_weights), - hosts_added, hosts_removed, weighted_priority_health, + hosts_added, hosts_removed, seed, weighted_priority_health, overprovisioning_factor, std::move(cross_priority_host_map)); // If an LB is thread aware, create a new worker local LB on membership changes. if (lb_factory_ != nullptr && lb_factory_->recreateOnHostChange()) { @@ -1832,8 +1833,8 @@ void ClusterManagerImpl::ThreadLocalClusterManagerImpl::updateClusterMembership( const auto& cluster_entry = thread_local_clusters_[name]; cluster_entry->updateHosts(name, priority, std::move(update_hosts_params), std::move(locality_weights), hosts_added, hosts_removed, - weighted_priority_health, overprovisioning_factor, - std::move(cross_priority_host_map)); + parent_.random_.random(), weighted_priority_health, + overprovisioning_factor, std::move(cross_priority_host_map)); } void ClusterManagerImpl::ThreadLocalClusterManagerImpl::onHostHealthFailure( diff --git a/source/common/upstream/cluster_manager_impl.h b/source/common/upstream/cluster_manager_impl.h index 3bac52e9aa9ca..0c0a0c857c879 100644 --- a/source/common/upstream/cluster_manager_impl.h +++ b/source/common/upstream/cluster_manager_impl.h @@ -601,7 +601,7 @@ class ClusterManagerImpl : public ClusterManager, PrioritySet::UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, const HostVector& hosts_removed, - absl::optional weighted_priority_health, + uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor, HostMapConstSharedPtr cross_priority_host_map); @@ -936,15 +936,6 @@ class ClusterManagerImpl : public ClusterManager, bool initialized_{}; bool ads_mux_initialized_{}; std::atomic shutdown_{}; - - // Records the last `warming_clusters_` map size from updateClusterCounts(). This variable is - // used for bookkeeping to run the `resume_cds_` cleanup that decrements the pause count and - // enables the resumption of DiscoveryRequests for the Cluster type url. - // - // The `warming_clusters` gauge is not suitable for this purpose, because different environments - // (e.g. mobile) may have different stats enabled, leading to the gauge not having a reliable - // previous warming clusters size value. - std::size_t last_recorded_warming_clusters_count_{0}; }; } // namespace Upstream diff --git a/source/common/upstream/edf_scheduler.h b/source/common/upstream/edf_scheduler.h index 57098be6b2f77..a625d72a98df4 100644 --- a/source/common/upstream/edf_scheduler.h +++ b/source/common/upstream/edf_scheduler.h @@ -27,6 +27,8 @@ namespace Upstream { // weights and an O(log n) pick time. template class EdfScheduler : public Scheduler { public: + EdfScheduler() {} + // See scheduler.h for an explanation of each public method. std::shared_ptr peekAgain(std::function calculate_weight) override { std::shared_ptr ret = popEntry(); @@ -64,7 +66,110 @@ template class EdfScheduler : public Scheduler { bool empty() const override { return queue_.empty(); } + // Creates an EdfScheduler with the given weights and their corresponding + // entries, and emulating a number of initial picks to be performed. Note that + // the internal state of the scheduler will be very similar to creating an empty + // scheduler, adding the entries one after the other, and then performing + // "picks" pickAndAdd operation without modifying the entries' weights. + // The only thing that may be different is that entries with the same weight + // may be chosen a bit differently (the order_offset_ values may be different). + // Breaking the ties of same weight entries will be kept in future picks from + // the scheduler. + static EdfScheduler createWithPicks(const std::vector>& entries, + std::function calculate_weight, + uint32_t picks) { + // Limiting the number of picks, as over 400M picks should be sufficient + // for most scenarios. + picks = picks % 429496729; // % UINT_MAX/10 + EDF_TRACE("Creating an EDF-scheduler with {} weights and {} pre-picks.", entries.size(), picks); + // Assume no non-positive weights. + ASSERT(std::none_of(entries.cbegin(), entries.cend(), + [&calculate_weight](const std::shared_ptr& entry) { + return calculate_weight(*entry) <= 0; + })); + + // Nothing to do if there are no entries. + if (entries.size() == 0) { + return EdfScheduler(); + } + + // Augment the weight computation to add some epsilon to each entry's + // weight to avoid cases where weights are multiplies of each other. For + // example if there are 2 weights: 25 and 75, and picks=23, then the + // floor_picks will be {5, 17} (respectively), and the deadlines will be + // {0.24000000000000002 and 0.24} (respectively). This small difference will + // cause a "wrong" pick compared to when starting from an empty scheduler + // and picking 23 times. Adding a small value to each weight circumvents + // this problem. This was added as a result of the following comment: + // https://github.com/envoyproxy/envoy/pull/31592#issuecomment-1877663769. + auto aug_calculate_weight = [&calculate_weight](const C& entry) -> double { + return calculate_weight(entry) + 1e-13; + }; + + // Let weights {w_1, w_2, ..., w_N} be the per-entry weight where (w_i > 0), + // W = sum(w_i), and P be the number of times to "pick" from the scheduler. + // Let p'_i = floor(P * w_i/W), then the number of times each entry is being + // picked is p_i >= p'_i. Note that 0 <= P - sum(p'_i) < N. + // + // The following code does P picks, by first emulating p'_i picks for each + // entry, and then executing the leftover P - sum(p'_i) picks. + double weights_sum = std::accumulate( + entries.cbegin(), entries.cend(), 0.0, + [&aug_calculate_weight](double sum_so_far, const std::shared_ptr& entry) { + return sum_so_far + aug_calculate_weight(*entry); + }); + std::vector floor_picks; + floor_picks.reserve(entries.size()); + std::transform(entries.cbegin(), entries.cend(), std::back_inserter(floor_picks), + [picks, weights_sum, &aug_calculate_weight](const std::shared_ptr& entry) { + // Getting the lower-bound by casting to an integer. + return static_cast(aug_calculate_weight(*entry) * picks / + weights_sum); + }); + + // Pre-compute the priority-queue entries to use an O(N) initialization c'tor. + std::vector scheduler_entries; + scheduler_entries.reserve(entries.size()); + uint32_t picks_so_far = 0; + double max_pick_time = 0.0; + // Emulate a per-entry addition to a deadline that is applicable to N picks. + for (size_t i = 0; i < entries.size(); ++i) { + // Add the entry with p'_i picks. As there were p'_i picks, the entry's + // next deadline is (p'_i + 1) / w_i. + const double weight = aug_calculate_weight(*entries[i]); + // While validating the algorithm there were a few cases where the math + // and floating-point arithmetic did not agree (specifically floor(A*B) + // was greater than A*B). The following if statement solves the problem by + // reducing floor-picks for the entry, which may result in more iterations + // in the code after the loop. + if ((floor_picks[i] > 0) && (floor_picks[i] / weight >= picks / weights_sum)) { + floor_picks[i]--; + } + const double pick_time = floor_picks[i] / weight; + const double deadline = (floor_picks[i] + 1) / weight; + EDF_TRACE("Insertion {} in queue with emualted {} picks, deadline {} and weight {}.", + static_cast(entries[i].get()), floor_picks[i], deadline, weight); + scheduler_entries.emplace_back(EdfEntry{deadline, i, entries[i]}); + max_pick_time = std::max(max_pick_time, pick_time); + picks_so_far += floor_picks[i]; + } + // The scheduler's current_time_ needs to be the largest time that some entry was picked. + EdfScheduler scheduler(std::move(scheduler_entries), max_pick_time, entries.size()); + ASSERT(scheduler.queue_.top().deadline_ >= scheduler.current_time_); + + // Left to do some picks, execute them one after the other. + EDF_TRACE("Emulated {} picks in init step, {} picks remaining for one after the other step", + picks_so_far, picks - picks_so_far); + while (picks_so_far < picks) { + scheduler.pickAndAdd(calculate_weight); + picks_so_far++; + } + return scheduler; + } + private: + friend class EdfSchedulerTest; + /** * Clears expired entries and pops the next unexpired entry in the queue. */ @@ -106,6 +211,11 @@ template class EdfScheduler : public Scheduler { } }; + EdfScheduler(std::vector&& scheduler_entries, double current_time, + uint32_t order_offset) + : current_time_(current_time), order_offset_(order_offset), + queue_(scheduler_entries.cbegin(), scheduler_entries.cend()) {} + // Current time in EDF scheduler. // TODO(htuch): Is it worth the small extra complexity to use integer time for performance // reasons? diff --git a/source/common/upstream/health_checker_event_logger.h b/source/common/upstream/health_checker_event_logger.h index a05d3a5f0196d..362e644d65c38 100644 --- a/source/common/upstream/health_checker_event_logger.h +++ b/source/common/upstream/health_checker_event_logger.h @@ -28,7 +28,6 @@ class HealthCheckEventLoggerImpl : public HealthCheckEventLogger { HealthCheckEventLoggerImpl(const envoy::config::core::v3::HealthCheck& health_check_config, Server::Configuration::HealthCheckerFactoryContext& context) : time_source_(context.serverFactoryContext().mainThreadDispatcher().timeSource()) { - // TODO(botengyao): Remove the file_ creation here into the file based health check // event sink. In this way you can remove the file_ based code from the createHealthCheckEvent if (!health_check_config.event_log_path().empty() /* deprecated */) { diff --git a/source/common/upstream/health_discovery_service.cc b/source/common/upstream/health_discovery_service.cc index 4db99e3361d0f..3d6d687894505 100644 --- a/source/common/upstream/health_discovery_service.cc +++ b/source/common/upstream/health_discovery_service.cc @@ -524,8 +524,9 @@ void HdsCluster::updateHosts( // Update the priority set. hosts_per_locality_ = std::make_shared(std::move(hosts_by_locality), false); - priority_set_.updateHosts(0, HostSetImpl::partitionHosts(hosts_, hosts_per_locality_), {}, - hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + priority_set_.updateHosts( + 0, HostSetImpl::partitionHosts(hosts_, hosts_per_locality_), {}, hosts_added, hosts_removed, + server_context_.api().randomGenerator().random(), absl::nullopt, absl::nullopt); } ClusterSharedPtr HdsCluster::create() { return nullptr; } @@ -575,7 +576,8 @@ void HdsCluster::initialize(std::function callback) { } // Use the ungrouped and grouped hosts lists to retain locality structure in the priority set. priority_set_.updateHosts(0, HostSetImpl::partitionHosts(hosts_, hosts_per_locality_), {}, - *hosts_, {}, absl::nullopt, absl::nullopt); + *hosts_, {}, server_context_.api().randomGenerator().random(), + absl::nullopt, absl::nullopt); initialized_ = true; } diff --git a/source/common/upstream/host_utility.cc b/source/common/upstream/host_utility.cc index 341b0674d8157..e0791aa04252d 100644 --- a/source/common/upstream/host_utility.cc +++ b/source/common/upstream/host_utility.cc @@ -73,6 +73,13 @@ void setHealthFlag(Upstream::Host::HealthFlag flag, const Host& host, std::strin } break; } + + case Host::HealthFlag::EDS_STATUS_DRAINING: { + if (host.healthFlagGet(Host::HealthFlag::EDS_STATUS_DRAINING)) { + health_status += "/eds_status_draining"; + } + break; + } } } diff --git a/source/common/upstream/load_balancer_impl.cc b/source/common/upstream/load_balancer_impl.cc index c85565bfc6fca..83f22f7adc805 100644 --- a/source/common/upstream/load_balancer_impl.cc +++ b/source/common/upstream/load_balancer_impl.cc @@ -1,4 +1,3 @@ -#include "load_balancer_impl.h" #include "source/common/upstream/load_balancer_impl.h" #include @@ -1299,12 +1298,72 @@ HostConstSharedPtr LeastRequestLoadBalancer::unweightedHostPick(const HostVector const HostsSource&) { HostSharedPtr candidate_host = nullptr; + switch (selection_method_) { + case envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest::FULL_SCAN: + candidate_host = unweightedHostPickFullScan(hosts_to_use); + break; + case envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest::N_CHOICES: + candidate_host = unweightedHostPickNChoices(hosts_to_use); + break; + default: + IS_ENVOY_BUG("unknown selection method specified for least request load balancer"); + } + + return candidate_host; +} + +HostSharedPtr LeastRequestLoadBalancer::unweightedHostPickFullScan(const HostVector& hosts_to_use) { + HostSharedPtr candidate_host = nullptr; + + size_t num_hosts_known_tied_for_least = 0; + + const size_t num_hosts = hosts_to_use.size(); + + for (size_t i = 0; i < num_hosts; ++i) { + const HostSharedPtr& sampled_host = hosts_to_use[i]; + + if (candidate_host == nullptr) { + // Make a first choice to start the comparisons. + num_hosts_known_tied_for_least = 1; + candidate_host = sampled_host; + continue; + } + + const auto candidate_active_rq = candidate_host->stats().rq_active_.value(); + const auto sampled_active_rq = sampled_host->stats().rq_active_.value(); + + if (sampled_active_rq < candidate_active_rq) { + // Reset the count of known tied hosts. + num_hosts_known_tied_for_least = 1; + candidate_host = sampled_host; + } else if (sampled_active_rq == candidate_active_rq) { + ++num_hosts_known_tied_for_least; + + // Use reservoir sampling to select 1 unique sample from the total number of hosts N + // that will tie for least requests after processing the full hosts array. + // + // Upon each new tie encountered, replace candidate_host with sampled_host + // with probability (1 / num_hosts_known_tied_for_least percent). + // The end result is that each tied host has an equal 1 / N chance of being the + // candidate_host returned by this function. + const size_t random_tied_host_index = random_.random() % num_hosts_known_tied_for_least; + if (random_tied_host_index == 0) { + candidate_host = sampled_host; + } + } + } + + return candidate_host; +} + +HostSharedPtr LeastRequestLoadBalancer::unweightedHostPickNChoices(const HostVector& hosts_to_use) { + HostSharedPtr candidate_host = nullptr; + for (uint32_t choice_idx = 0; choice_idx < choice_count_; ++choice_idx) { const int rand_idx = random_.random() % hosts_to_use.size(); const HostSharedPtr& sampled_host = hosts_to_use[rand_idx]; if (candidate_host == nullptr) { - // Make a first choice to start the comparisons. candidate_host = sampled_host; continue; @@ -1312,6 +1371,7 @@ HostConstSharedPtr LeastRequestLoadBalancer::unweightedHostPick(const HostVector const auto candidate_active_rq = candidate_host->stats().rq_active_.value(); const auto sampled_active_rq = sampled_host->stats().rq_active_.value(); + if (sampled_active_rq < candidate_active_rq) { candidate_host = sampled_host; } diff --git a/source/common/upstream/load_balancer_impl.h b/source/common/upstream/load_balancer_impl.h index 614541057798c..55927ed4a1f04 100644 --- a/source/common/upstream/load_balancer_impl.h +++ b/source/common/upstream/load_balancer_impl.h @@ -710,7 +710,8 @@ class LeastRequestLoadBalancer : public EdfLoadBalancerBase { least_request_config.has_active_request_bias() ? absl::optional( {least_request_config.active_request_bias(), runtime}) - : absl::nullopt) { + : absl::nullopt), + selection_method_(least_request_config.selection_method()) { initialize(); } @@ -737,6 +738,8 @@ class LeastRequestLoadBalancer : public EdfLoadBalancerBase { const HostsSource& source) override; HostConstSharedPtr unweightedHostPick(const HostVector& hosts_to_use, const HostsSource& source) override; + HostSharedPtr unweightedHostPickFullScan(const HostVector& hosts_to_use); + HostSharedPtr unweightedHostPickNChoices(const HostVector& hosts_to_use); const uint32_t choice_count_; @@ -746,6 +749,8 @@ class LeastRequestLoadBalancer : public EdfLoadBalancerBase { double active_request_bias_{}; const absl::optional active_request_bias_runtime_; + const envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest::SelectionMethod + selection_method_{}; }; /** diff --git a/source/common/upstream/upstream_impl.cc b/source/common/upstream/upstream_impl.cc index 5c781c9bd70a7..66a0d339f83ee 100644 --- a/source/common/upstream/upstream_impl.cc +++ b/source/common/upstream/upstream_impl.cc @@ -80,7 +80,7 @@ parseTcpKeepaliveConfig(const envoy::config::cluster::v3::Cluster& config) { PROTOBUF_GET_WRAPPED_OR_DEFAULT(options, keepalive_interval, absl::optional())}; } -ProtocolOptionsConfigConstSharedPtr +absl::StatusOr createProtocolOptionsConfig(const std::string& name, const ProtobufWkt::Any& typed_config, Server::Configuration::ProtocolOptionsFactoryContext& factory_context) { Server::Configuration::ProtocolOptionsFactory* factory = @@ -121,9 +121,10 @@ absl::flat_hash_map parseExten for (const auto& it : config.typed_extension_protocol_options()) { auto& name = it.first; - auto object = createProtocolOptionsConfig(name, it.second, factory_context); - if (object != nullptr) { - options[name] = std::move(object); + auto object_or_error = createProtocolOptionsConfig(name, it.second, factory_context); + THROW_IF_STATUS_NOT_OK(object_or_error, throw); + if (object_or_error.value() != nullptr) { + options[name] = std::move(object_or_error.value()); } } @@ -450,16 +451,24 @@ void HostImpl::setEdsHealthFlag(envoy::config::core::v3::HealthStatus health_sta // Clear all old EDS health flags first. HostImpl::healthFlagClear(Host::HealthFlag::FAILED_EDS_HEALTH); HostImpl::healthFlagClear(Host::HealthFlag::DEGRADED_EDS_HEALTH); + if (Runtime::runtimeFeatureEnabled( + "envoy.reloadable_features.exclude_host_in_eds_status_draining")) { + HostImpl::healthFlagClear(Host::HealthFlag::EDS_STATUS_DRAINING); + } // Set the appropriate EDS health flag. switch (health_status) { case envoy::config::core::v3::UNHEALTHY: FALLTHRU; - case envoy::config::core::v3::DRAINING: - FALLTHRU; case envoy::config::core::v3::TIMEOUT: HostImpl::healthFlagSet(Host::HealthFlag::FAILED_EDS_HEALTH); break; + case envoy::config::core::v3::DRAINING: + if (Runtime::runtimeFeatureEnabled( + "envoy.reloadable_features.exclude_host_in_eds_status_draining")) { + HostImpl::healthFlagSet(Host::HealthFlag::EDS_STATUS_DRAINING); + } + break; case envoy::config::core::v3::DEGRADED: HostImpl::healthFlagSet(Host::HealthFlag::DEGRADED_EDS_HEALTH); break; @@ -505,9 +514,23 @@ Host::CreateConnectionData HostImpl::createConnection( socket_factory.createTransportSocket(transport_socket_options, host), upstream_local_address.socket_options_, transport_socket_options); } else if (address_list.size() > 1) { + absl::optional + happy_eyeballs_config; + if (Runtime::runtimeFeatureEnabled("envoy.reloadable_features.use_config_in_happy_eyeballs")) { + ENVOY_LOG(debug, "Upstream using happy eyeballs config."); + if (cluster.happyEyeballsConfig().has_value()) { + happy_eyeballs_config = cluster.happyEyeballsConfig(); + } else { + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig default_config; + default_config.set_first_address_family_version( + envoy::config::cluster::v3::UpstreamConnectionOptions::DEFAULT); + default_config.mutable_first_address_family_count()->set_value(1); + happy_eyeballs_config = absl::make_optional(default_config); + } + } connection = std::make_unique( dispatcher, address_list, source_address_selector, socket_factory, transport_socket_options, - host, options); + host, options, happy_eyeballs_config); } else { auto upstream_local_address = source_address_selector->getUpstreamLocalAddress(address, options); @@ -566,7 +589,7 @@ std::vector HostsPerLocalityImpl::filter( void HostSetImpl::updateHosts(PrioritySet::UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, const HostVector& hosts_removed, - absl::optional weighted_priority_health, + uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor) { if (weighted_priority_health.has_value()) { weighted_priority_health_ = weighted_priority_health.value(); @@ -589,11 +612,11 @@ void HostSetImpl::updateHosts(PrioritySet::UpdateHostsParams&& update_hosts_para rebuildLocalityScheduler(healthy_locality_scheduler_, healthy_locality_entries_, *healthy_hosts_per_locality_, healthy_hosts_->get(), hosts_per_locality_, excluded_hosts_per_locality_, locality_weights_, - overprovisioning_factor_); + overprovisioning_factor_, seed); rebuildLocalityScheduler(degraded_locality_scheduler_, degraded_locality_entries_, *degraded_hosts_per_locality_, degraded_hosts_->get(), hosts_per_locality_, excluded_hosts_per_locality_, locality_weights_, - overprovisioning_factor_); + overprovisioning_factor_, seed); runUpdateCallbacks(hosts_added, hosts_removed); } @@ -604,7 +627,8 @@ void HostSetImpl::rebuildLocalityScheduler( const HostsPerLocality& eligible_hosts_per_locality, const HostVector& eligible_hosts, HostsPerLocalityConstSharedPtr all_hosts_per_locality, HostsPerLocalityConstSharedPtr excluded_hosts_per_locality, - LocalityWeightsConstSharedPtr locality_weights, uint32_t overprovisioning_factor) { + LocalityWeightsConstSharedPtr locality_weights, uint32_t overprovisioning_factor, + uint64_t seed) { // Rebuild the locality scheduler by computing the effective weight of each // locality in this priority. The scheduler is reset by default, and is rebuilt only if we have // locality weights (i.e. using EDS) and there is at least one eligible host in this priority. @@ -623,20 +647,40 @@ void HostSetImpl::rebuildLocalityScheduler( locality_scheduler = nullptr; if (all_hosts_per_locality != nullptr && locality_weights != nullptr && !locality_weights->empty() && !eligible_hosts.empty()) { - locality_scheduler = std::make_unique>(); - locality_entries.clear(); - for (uint32_t i = 0; i < all_hosts_per_locality->get().size(); ++i) { - const double effective_weight = effectiveLocalityWeight( - i, eligible_hosts_per_locality, *excluded_hosts_per_locality, *all_hosts_per_locality, - *locality_weights, overprovisioning_factor); - if (effective_weight > 0) { - locality_entries.emplace_back(std::make_shared(i, effective_weight)); - locality_scheduler->add(effective_weight, locality_entries.back()); + if (Runtime::runtimeFeatureEnabled( + "envoy.reloadable_features.edf_lb_locality_scheduler_init_fix")) { + locality_entries.clear(); + for (uint32_t i = 0; i < all_hosts_per_locality->get().size(); ++i) { + const double effective_weight = effectiveLocalityWeight( + i, eligible_hosts_per_locality, *excluded_hosts_per_locality, *all_hosts_per_locality, + *locality_weights, overprovisioning_factor); + if (effective_weight > 0) { + locality_entries.emplace_back(std::make_shared(i, effective_weight)); + } + } + // If not all effective weights were zero, create the scheduler. + if (!locality_entries.empty()) { + locality_scheduler = std::make_unique>( + EdfScheduler::createWithPicks( + locality_entries, + [](const LocalityEntry& entry) { return entry.effective_weight_; }, seed)); + } + } else { + locality_scheduler = std::make_unique>(); + locality_entries.clear(); + for (uint32_t i = 0; i < all_hosts_per_locality->get().size(); ++i) { + const double effective_weight = effectiveLocalityWeight( + i, eligible_hosts_per_locality, *excluded_hosts_per_locality, *all_hosts_per_locality, + *locality_weights, overprovisioning_factor); + if (effective_weight > 0) { + locality_entries.emplace_back(std::make_shared(i, effective_weight)); + locality_scheduler->add(effective_weight, locality_entries.back()); + } + } + // If all effective weights were zero, reset the scheduler. + if (locality_scheduler->empty()) { + locality_scheduler = nullptr; } - } - // If all effective weights were zero, reset the scheduler. - if (locality_scheduler->empty()) { - locality_scheduler = nullptr; } } } @@ -748,7 +792,7 @@ PrioritySetImpl::getOrCreateHostSet(uint32_t priority, void PrioritySetImpl::updateHosts(uint32_t priority, UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, const HostVector& hosts_removed, - absl::optional weighted_priority_health, + uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor, HostMapConstSharedPtr cross_priority_host_map) { // Update cross priority host map first. In this way, when the update callbacks of the priority @@ -761,7 +805,7 @@ void PrioritySetImpl::updateHosts(uint32_t priority, UpdateHostsParams&& update_ getOrCreateHostSet(priority, weighted_priority_health, overprovisioning_factor); static_cast(host_sets_[priority].get()) ->updateHosts(std::move(update_hosts_params), std::move(locality_weights), hosts_added, - hosts_removed, weighted_priority_health, overprovisioning_factor); + hosts_removed, seed, weighted_priority_health, overprovisioning_factor); if (!batch_update_) { runUpdateCallbacks(hosts_added, hosts_removed); @@ -784,7 +828,7 @@ void PrioritySetImpl::batchHostUpdate(BatchUpdateCb& callback) { void PrioritySetImpl::BatchUpdateScope::updateHosts( uint32_t priority, PrioritySet::UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, absl::optional weighted_priority_health, + const HostVector& hosts_removed, uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor) { // We assume that each call updates a different priority. ASSERT(priorities_.find(priority) == priorities_.end()); @@ -799,13 +843,13 @@ void PrioritySetImpl::BatchUpdateScope::updateHosts( } parent_.updateHosts(priority, std::move(update_hosts_params), locality_weights, hosts_added, - hosts_removed, weighted_priority_health, overprovisioning_factor); + hosts_removed, seed, weighted_priority_health, overprovisioning_factor); } void MainPrioritySetImpl::updateHosts(uint32_t priority, UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, + const HostVector& hosts_removed, uint64_t seed, absl::optional weighted_priority_health, absl::optional overprovisioning_factor, HostMapConstSharedPtr cross_priority_host_map) { @@ -814,7 +858,7 @@ void MainPrioritySetImpl::updateHosts(uint32_t priority, UpdateHostsParams&& upd updateCrossPriorityHostMap(hosts_added, hosts_removed); PrioritySetImpl::updateHosts(priority, std::move(update_hosts_params), locality_weights, - hosts_added, hosts_removed, weighted_priority_health, + hosts_added, hosts_removed, seed, weighted_priority_health, overprovisioning_factor); } @@ -823,6 +867,8 @@ HostMapConstSharedPtr MainPrioritySetImpl::crossPriorityHostMap() const { if (mutable_cross_priority_host_map_ != nullptr) { const_cross_priority_host_map_ = std::move(mutable_cross_priority_host_map_); ASSERT(mutable_cross_priority_host_map_ == nullptr); + ENVOY_LOG(debug, "cross_priority host map, moving mutable to const, len: {}", + const_cross_priority_host_map_->size()); } return const_cross_priority_host_map_; } @@ -839,14 +885,18 @@ void MainPrioritySetImpl::updateCrossPriorityHostMap(const HostVector& hosts_add if (mutable_cross_priority_host_map_ == nullptr) { // Copy old read only host map to mutable host map. mutable_cross_priority_host_map_ = std::make_shared(*const_cross_priority_host_map_); + ENVOY_LOG(debug, "cross_priority host map, copying from const, len: {}", + const_cross_priority_host_map_->size()); } for (const auto& host : hosts_removed) { mutable_cross_priority_host_map_->erase(addressToString(host->address())); + ENVOY_LOG(debug, "cross_priority host map, removing: {}", addressToString(host->address())); } for (const auto& host : hosts_added) { mutable_cross_priority_host_map_->insert({addressToString(host->address()), host}); + ENVOY_LOG(debug, "cross_priority host map, adding: {}", addressToString(host->address())); } } @@ -891,15 +941,19 @@ createOptions(const envoy::config::cluster::v3::Cluster& config, } } - return std::make_shared( - config.http_protocol_options(), config.http2_protocol_options(), - config.common_http_protocol_options(), - (config.has_upstream_http_protocol_options() - ? absl::make_optional( - config.upstream_http_protocol_options()) - : absl::nullopt), - config.protocol_selection() == envoy::config::cluster::v3::Cluster::USE_DOWNSTREAM_PROTOCOL, - config.has_http2_protocol_options(), validation_visitor); + auto options_or_error = + ClusterInfoImpl::HttpProtocolOptionsConfigImpl::createProtocolOptionsConfig( + config.http_protocol_options(), config.http2_protocol_options(), + config.common_http_protocol_options(), + (config.has_upstream_http_protocol_options() + ? absl::make_optional( + config.upstream_http_protocol_options()) + : absl::nullopt), + config.protocol_selection() == + envoy::config::cluster::v3::Cluster::USE_DOWNSTREAM_PROTOCOL, + config.has_http2_protocol_options(), validation_visitor); + THROW_IF_STATUS_NOT_OK(options_or_error, throw); + return options_or_error.value(); } absl::StatusOr @@ -1096,7 +1150,13 @@ ClusterInfoImpl::ClusterInfoImpl( config.upstream_connection_options().set_local_interface_name_on_upstream_connections()), added_via_api_(added_via_api), has_configured_http_filters_(false), per_endpoint_stats_(config.has_track_cluster_stats() && - config.track_cluster_stats().per_endpoint_stats()) { + config.track_cluster_stats().per_endpoint_stats()), + happy_eyeballs_config_( + config.upstream_connection_options().has_happy_eyeballs_config() + ? absl::make_optional< + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig>( + config.upstream_connection_options().happy_eyeballs_config()) + : absl::nullopt) { #ifdef WIN32 if (set_local_interface_name_on_upstream_connections_) { throwEnvoyExceptionOrPanic( @@ -1448,6 +1508,7 @@ ClusterImplBase::ClusterImplBase(const envoy::config::cluster::v3::Cluster& clus init_watcher_("ClusterImplBase", [this]() { onInitDone(); }), runtime_(cluster_context.serverFactoryContext().runtime()), wait_for_warm_on_init_(PROTOBUF_GET_WRAPPED_OR_DEFAULT(cluster, wait_for_warm_on_init, true)), + random_(cluster_context.serverFactoryContext().api().randomGenerator()), time_source_(cluster_context.serverFactoryContext().timeSource()), local_cluster_(cluster_context.clusterManager().localClusterName().value_or("") == cluster.name()), @@ -1544,7 +1605,8 @@ namespace { bool excludeBasedOnHealthFlag(const Host& host) { return host.healthFlagGet(Host::HealthFlag::PENDING_ACTIVE_HC) || - host.healthFlagGet(Host::HealthFlag::EXCLUDED_VIA_IMMEDIATE_HC_FAIL); + host.healthFlagGet(Host::HealthFlag::EXCLUDED_VIA_IMMEDIATE_HC_FAIL) || + host.healthFlagGet(Host::HealthFlag::EDS_STATUS_DRAINING); } } // namespace @@ -1665,7 +1727,7 @@ absl::Status ClusterImplBase::parseDropOverloadConfig( if (!cluster_load_assignment.has_policy()) { return absl::OkStatus(); } - auto policy = cluster_load_assignment.policy(); + const auto& policy = cluster_load_assignment.policy(); if (policy.drop_overloads().size() == 0) { return absl::OkStatus(); } @@ -1675,7 +1737,7 @@ absl::Status ClusterImplBase::parseDropOverloadConfig( policy.drop_overloads().size())); } - const auto drop_percentage = policy.drop_overloads(0).drop_percentage(); + const auto& drop_percentage = policy.drop_overloads(0).drop_percentage(); float denominator = 100; switch (drop_percentage.denominator()) { case envoy::type::v3::FractionalPercent::HUNDRED: @@ -1741,9 +1803,9 @@ void ClusterImplBase::reloadHealthyHostsHelper(const HostSharedPtr&) { HostVectorConstSharedPtr hosts_copy = std::make_shared(host_set->hosts()); HostsPerLocalityConstSharedPtr hosts_per_locality_copy = host_set->hostsPerLocality().clone(); - prioritySet().updateHosts(priority, - HostSetImpl::partitionHosts(hosts_copy, hosts_per_locality_copy), - host_set->localityWeights(), {}, {}, absl::nullopt, absl::nullopt); + prioritySet().updateHosts( + priority, HostSetImpl::partitionHosts(hosts_copy, hosts_per_locality_copy), + host_set->localityWeights(), {}, {}, random_.random(), absl::nullopt, absl::nullopt); } } @@ -1974,8 +2036,10 @@ ClusterInfoImpl::ResourceManagers::load(const envoy::config::cluster::v3::Cluste PriorityStateManager::PriorityStateManager(ClusterImplBase& cluster, const LocalInfo::LocalInfo& local_info, - PrioritySet::HostUpdateCb* update_cb) - : parent_(cluster), local_info_node_(local_info.node()), update_cb_(update_cb) {} + PrioritySet::HostUpdateCb* update_cb, + Random::RandomGenerator& random) + : parent_(cluster), local_info_node_(local_info.node()), update_cb_(update_cb), + random_(random) {} void PriorityStateManager::initializePriorityFor( const envoy::config::endpoint::v3::LocalityLbEndpoints& locality_lb_endpoint) { @@ -2099,13 +2163,14 @@ void PriorityStateManager::updateClusterPrioritySet( if (update_cb_ != nullptr) { update_cb_->updateHosts(priority, HostSetImpl::partitionHosts(hosts, per_locality_shared), std::move(locality_weights), hosts_added.value_or(*hosts), - hosts_removed.value_or({}), weighted_priority_health, - overprovisioning_factor); + hosts_removed.value_or({}), random_.random(), + weighted_priority_health, overprovisioning_factor); } else { - parent_.prioritySet().updateHosts( - priority, HostSetImpl::partitionHosts(hosts, per_locality_shared), - std::move(locality_weights), hosts_added.value_or(*hosts), - hosts_removed.value_or({}), weighted_priority_health, overprovisioning_factor); + parent_.prioritySet().updateHosts(priority, + HostSetImpl::partitionHosts(hosts, per_locality_shared), + std::move(locality_weights), hosts_added.value_or(*hosts), + hosts_removed.value_or({}), random_.random(), + weighted_priority_health, overprovisioning_factor); } } @@ -2241,37 +2306,26 @@ bool BaseDynamicClusterImpl::updateDynamicHostList( // If there's an existing host with the same health checker, the // active health-status is kept. if (health_checker_ != nullptr && !host->disableActiveHealthCheck()) { - if (Runtime::runtimeFeatureEnabled( - "envoy.reloadable_features.keep_endpoint_active_hc_status_on_locality_update")) { - if (existing_host_found && !health_check_address_changed && - !active_health_check_flag_changed) { - // If there's an existing host, use the same active health-status. - // The existing host can be marked PENDING_ACTIVE_HC or - // ACTIVE_HC_TIMEOUT if it is also marked with FAILED_ACTIVE_HC. - ASSERT(!existing_host->second->healthFlagGet(Host::HealthFlag::PENDING_ACTIVE_HC) || - existing_host->second->healthFlagGet(Host::HealthFlag::FAILED_ACTIVE_HC)); - ASSERT(!existing_host->second->healthFlagGet(Host::HealthFlag::ACTIVE_HC_TIMEOUT) || - existing_host->second->healthFlagGet(Host::HealthFlag::FAILED_ACTIVE_HC)); - - constexpr uint32_t active_hc_statuses_mask = - enumToInt(Host::HealthFlag::FAILED_ACTIVE_HC) | - enumToInt(Host::HealthFlag::DEGRADED_ACTIVE_HC) | - enumToInt(Host::HealthFlag::PENDING_ACTIVE_HC) | - enumToInt(Host::HealthFlag::ACTIVE_HC_TIMEOUT); - - const uint32_t existing_host_statuses = existing_host->second->healthFlagsGetAll(); - host->healthFlagsSetAll(existing_host_statuses & active_hc_statuses_mask); - } else { - // No previous known host, mark it as failed active HC. - host->healthFlagSet(Host::HealthFlag::FAILED_ACTIVE_HC); - - // If we want to exclude hosts until they have been health checked, mark them with - // a flag to indicate that they have not been health checked yet. - if (info_->warmHosts()) { - host->healthFlagSet(Host::HealthFlag::PENDING_ACTIVE_HC); - } - } + if (existing_host_found && !health_check_address_changed && + !active_health_check_flag_changed) { + // If there's an existing host, use the same active health-status. + // The existing host can be marked PENDING_ACTIVE_HC or + // ACTIVE_HC_TIMEOUT if it is also marked with FAILED_ACTIVE_HC. + ASSERT(!existing_host->second->healthFlagGet(Host::HealthFlag::PENDING_ACTIVE_HC) || + existing_host->second->healthFlagGet(Host::HealthFlag::FAILED_ACTIVE_HC)); + ASSERT(!existing_host->second->healthFlagGet(Host::HealthFlag::ACTIVE_HC_TIMEOUT) || + existing_host->second->healthFlagGet(Host::HealthFlag::FAILED_ACTIVE_HC)); + + constexpr uint32_t active_hc_statuses_mask = + enumToInt(Host::HealthFlag::FAILED_ACTIVE_HC) | + enumToInt(Host::HealthFlag::DEGRADED_ACTIVE_HC) | + enumToInt(Host::HealthFlag::PENDING_ACTIVE_HC) | + enumToInt(Host::HealthFlag::ACTIVE_HC_TIMEOUT); + + const uint32_t existing_host_statuses = existing_host->second->healthFlagsGetAll(); + host->healthFlagsSetAll(existing_host_statuses & active_hc_statuses_mask); } else { + // No previous known host, mark it as failed active HC. host->healthFlagSet(Host::HealthFlag::FAILED_ACTIVE_HC); // If we want to exclude hosts until they have been health checked, mark them with diff --git a/source/common/upstream/upstream_impl.h b/source/common/upstream/upstream_impl.h index 7a2a7cc30616d..1ea732bf1686c 100644 --- a/source/common/upstream/upstream_impl.h +++ b/source/common/upstream/upstream_impl.h @@ -409,7 +409,8 @@ class HostImpl : public HostDescriptionImpl, // If any of the unhealthy flags are set, host is unhealthy. if (healthFlagsGet(enumToInt(HealthFlag::FAILED_ACTIVE_HC) | enumToInt(HealthFlag::FAILED_OUTLIER_CHECK) | - enumToInt(HealthFlag::FAILED_EDS_HEALTH))) { + enumToInt(HealthFlag::FAILED_EDS_HEALTH) | + enumToInt(HealthFlag::EDS_STATUS_DRAINING))) { return Host::Health::Unhealthy; } @@ -600,7 +601,7 @@ class HostSetImpl : public HostSet { void updateHosts(PrioritySet::UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, + const HostVector& hosts_removed, uint64_t seed, absl::optional weighted_priority_health = absl::nullopt, absl::optional overprovisioning_factor = absl::nullopt); @@ -656,13 +657,18 @@ class HostSetImpl : public HostSet { // @param locality_weights the weighting of each locality. // @param overprovisioning_factor the overprovisioning factor to use when computing the effective // weight of a locality. - static void rebuildLocalityScheduler( - std::unique_ptr>& locality_scheduler, - std::vector>& locality_entries, - const HostsPerLocality& eligible_hosts_per_locality, const HostVector& eligible_hosts, - HostsPerLocalityConstSharedPtr all_hosts_per_locality, - HostsPerLocalityConstSharedPtr excluded_hosts_per_locality, - LocalityWeightsConstSharedPtr locality_weights, uint32_t overprovisioning_factor); + // @param seed a random number of initial picks to "invoke" on the locality scheduler. This + // allows to distribute the load between different localities across worker threads and a fleet + // of Envoys. + static void + rebuildLocalityScheduler(std::unique_ptr>& locality_scheduler, + std::vector>& locality_entries, + const HostsPerLocality& eligible_hosts_per_locality, + const HostVector& eligible_hosts, + HostsPerLocalityConstSharedPtr all_hosts_per_locality, + HostsPerLocalityConstSharedPtr excluded_hosts_per_locality, + LocalityWeightsConstSharedPtr locality_weights, + uint32_t overprovisioning_factor, uint64_t seed); static absl::optional chooseLocality(EdfScheduler* locality_scheduler); @@ -700,7 +706,7 @@ class PrioritySetImpl : public PrioritySet { void updateHosts(uint32_t priority, UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, + const HostVector& hosts_removed, uint64_t seed, absl::optional weighted_priority_health = absl::nullopt, absl::optional overprovisioning_factor = absl::nullopt, HostMapConstSharedPtr cross_priority_host_map = nullptr) override; @@ -759,7 +765,8 @@ class PrioritySetImpl : public PrioritySet { void updateHosts(uint32_t priority, PrioritySet::UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, absl::optional weighted_priority_health, + const HostVector& hosts_removed, uint64_t seed, + absl::optional weighted_priority_health, absl::optional overprovisioning_factor) override; absl::node_hash_set all_hosts_added_; @@ -780,7 +787,7 @@ class MainPrioritySetImpl : public PrioritySetImpl, public Logger::Loggable weighted_priority_health = absl::nullopt, absl::optional overprovisioning_factor = absl::nullopt, HostMapConstSharedPtr cross_priority_host_map = nullptr) override; @@ -1053,6 +1060,11 @@ class ClusterInfoImpl : public ClusterInfo, Http::Http3::CodecStats& http3CodecStats() const override; Http::ClientHeaderValidatorPtr makeHeaderValidator(Http::Protocol protocol) const override; + const absl::optional + happyEyeballsConfig() const override { + return happy_eyeballs_config_; + } + protected: // Gets the retry budget percent/concurrency from the circuit breaker thresholds. If the retry // budget message is specified, defaults will be filled in if either params are unspecified. @@ -1127,10 +1139,11 @@ class ClusterInfoImpl : public ClusterInfo, common_lb_config_; std::unique_ptr cluster_type_; // TODO(ohadvano): http_filter_config_provider_manager_ and - // network_filter_config_provider_manager_ should be maintained in the ClusterManager object as a - // singleton. This is currently not possible due to circular dependency (filter config provider - // manager depends on the ClusterManager object). The circular dependency can be resolved when the - // following issue is resolved: https://github.com/envoyproxy/envoy/issues/26653. + // network_filter_config_provider_manager_ should be maintained in the ClusterManager object as + // a singleton. This is currently not possible due to circular dependency (filter config + // provider manager depends on the ClusterManager object). The circular dependency can be + // resolved when the following issue is resolved: + // https://github.com/envoyproxy/envoy/issues/26653. std::shared_ptr http_filter_config_provider_manager_; std::shared_ptr network_filter_config_provider_manager_; @@ -1155,6 +1168,8 @@ class ClusterInfoImpl : public ClusterInfo, // true iff the cluster proto specified upstream http filters. bool has_configured_http_filters_ : 1; const bool per_endpoint_stats_ : 1; + const absl::optional + happy_eyeballs_config_; }; /** @@ -1204,8 +1219,8 @@ class ClusterImplBase : public Cluster, protected Logger::Loggable partitionHostList(const HostVector& hosts); - // Partitions the provided list of hosts per locality into three new lists containing the healthy, - // degraded and excluded hosts respectively. + // Partitions the provided list of hosts per locality into three new lists containing the + // healthy, degraded and excluded hosts respectively. static std::tuple partitionHostsPerLocality(const HostsPerLocality& hosts); @@ -1227,8 +1242,8 @@ class ClusterImplBase : public Cluster, protected Logger::Loggable; class PriorityStateManager : protected Logger::Loggable { public: PriorityStateManager(ClusterImplBase& cluster, const LocalInfo::LocalInfo& local_info, - PrioritySet::HostUpdateCb* update_cb); + PrioritySet::HostUpdateCb* update_cb, Random::RandomGenerator& random); // Initializes the PriorityState vector based on the priority specified in locality_lb_endpoint. void initializePriorityFor( const envoy::config::endpoint::v3::LocalityLbEndpoints& locality_lb_endpoint); - // Registers a host based on its address to the PriorityState based on the specified priority (the - // priority is specified by locality_lb_endpoint.priority()). + // Registers a host based on its address to the PriorityState based on the specified priority + // (the priority is specified by locality_lb_endpoint.priority()). // // The specified health_checker_flag is used to set the registered-host's health-flag when the // lb_endpoint health status is unhealthy, draining or timeout. @@ -1339,6 +1355,7 @@ class PriorityStateManager : protected Logger::Loggable { PriorityState priority_state_; const envoy::config::core::v3::Node& local_info_node_; PrioritySet::HostUpdateCb* update_cb_; + Random::RandomGenerator& random_; }; using PriorityStateManagerPtr = std::unique_ptr; @@ -1355,8 +1372,8 @@ class BaseDynamicClusterImpl : public ClusterImplBase { * with existing hosts. * * @param new_hosts the full lists of hosts in the new configuration. - * @param current_priority_hosts the full lists of hosts for the priority to be updated. The list - * will be modified to contain the updated list of hosts. + * @param current_priority_hosts the full lists of hosts for the priority to be updated. The + * list will be modified to contain the updated list of hosts. * @param hosts_added_to_current_priority will be populated with hosts added to the priority. * @param hosts_removed_from_current_priority will be populated with hosts removed from the * priority. diff --git a/source/extensions/access_loggers/grpc/grpc_access_log_utils.cc b/source/extensions/access_loggers/grpc/grpc_access_log_utils.cc index 018599c2ecc50..e353949f0fea7 100644 --- a/source/extensions/access_loggers/grpc/grpc_access_log_utils.cc +++ b/source/extensions/access_loggers/grpc/grpc_access_log_utils.cc @@ -41,115 +41,115 @@ void Utility::responseFlagsToAccessLogResponseFlags( envoy::data::accesslog::v3::AccessLogCommon& common_access_log, const StreamInfo::StreamInfo& stream_info) { - static_assert(StreamInfo::ResponseFlag::LastFlag == 0x8000000, + static_assert(StreamInfo::CoreResponseFlag::LastFlag == 27, "A flag has been added. Fix this code."); - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::FailedLocalHealthCheck)) { common_access_log.mutable_response_flags()->set_failed_local_healthcheck(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream)) { common_access_log.mutable_response_flags()->set_no_healthy_upstream(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)) { common_access_log.mutable_response_flags()->set_upstream_request_timeout(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::LocalReset)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::LocalReset)) { common_access_log.mutable_response_flags()->set_local_reset(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamRemoteReset)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRemoteReset)) { common_access_log.mutable_response_flags()->set_upstream_remote_reset(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure)) { common_access_log.mutable_response_flags()->set_upstream_connection_failure(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionTermination)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionTermination)) { common_access_log.mutable_response_flags()->set_upstream_connection_termination(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow)) { common_access_log.mutable_response_flags()->set_upstream_overflow(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::NoRouteFound)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound)) { common_access_log.mutable_response_flags()->set_no_route_found(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) { common_access_log.mutable_response_flags()->set_delay_injected(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) { common_access_log.mutable_response_flags()->set_fault_injected(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::RateLimited)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) { common_access_log.mutable_response_flags()->set_rate_limited(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UnauthorizedExternalService)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) { common_access_log.mutable_response_flags()->mutable_unauthorized_details()->set_reason( envoy::data::accesslog::v3::ResponseFlags::Unauthorized::EXTERNAL_SERVICE); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::RateLimitServiceError)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::RateLimitServiceError)) { common_access_log.mutable_response_flags()->set_rate_limit_service_error(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DownstreamConnectionTermination)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DownstreamConnectionTermination)) { common_access_log.mutable_response_flags()->set_downstream_connection_termination(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded)) { common_access_log.mutable_response_flags()->set_upstream_retry_limit_exceeded(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::StreamIdleTimeout)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::StreamIdleTimeout)) { common_access_log.mutable_response_flags()->set_stream_idle_timeout(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::InvalidEnvoyRequestHeaders)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::InvalidEnvoyRequestHeaders)) { common_access_log.mutable_response_flags()->set_invalid_envoy_request_headers(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DownstreamProtocolError)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DownstreamProtocolError)) { common_access_log.mutable_response_flags()->set_downstream_protocol_error(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamMaxStreamDurationReached)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamMaxStreamDurationReached)) { common_access_log.mutable_response_flags()->set_upstream_max_stream_duration_reached(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::ResponseFromCacheFilter)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::ResponseFromCacheFilter)) { common_access_log.mutable_response_flags()->set_response_from_cache_filter(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::NoFilterConfigFound)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::NoFilterConfigFound)) { common_access_log.mutable_response_flags()->set_no_filter_config_found(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DurationTimeout)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DurationTimeout)) { common_access_log.mutable_response_flags()->set_duration_timeout(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::UpstreamProtocolError)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::UpstreamProtocolError)) { common_access_log.mutable_response_flags()->set_upstream_protocol_error(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::NoClusterFound)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::NoClusterFound)) { common_access_log.mutable_response_flags()->set_no_cluster_found(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::OverloadManager)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::OverloadManager)) { common_access_log.mutable_response_flags()->set_overload_manager(true); } - if (stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DnsResolutionFailed)) { + if (stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DnsResolutionFailed)) { common_access_log.mutable_response_flags()->set_dns_resolution_failure(true); } } diff --git a/source/extensions/clusters/aggregate/cluster.cc b/source/extensions/clusters/aggregate/cluster.cc index c8e0bc8b5dee3..a9ff4d5ec4261 100644 --- a/source/extensions/clusters/aggregate/cluster.cc +++ b/source/extensions/clusters/aggregate/cluster.cc @@ -86,8 +86,8 @@ AggregateClusterLoadBalancer::linearizePrioritySet(OptRef exc if (!host_set->hosts().empty()) { priority_context->priority_set_.updateHosts( next_priority_after_linearizing, Upstream::HostSetImpl::updateHostsParams(*host_set), - host_set->localityWeights(), host_set->hosts(), {}, host_set->weightedPriorityHealth(), - host_set->overprovisioningFactor()); + host_set->localityWeights(), host_set->hosts(), {}, random_.random(), + host_set->weightedPriorityHealth(), host_set->overprovisioningFactor()); priority_context->priority_to_cluster_.emplace_back( std::make_pair(priority_in_current_cluster, tlc)); diff --git a/source/extensions/clusters/dynamic_forward_proxy/cluster.cc b/source/extensions/clusters/dynamic_forward_proxy/cluster.cc index 1200a49052dab..b6c69d79e5b6f 100644 --- a/source/extensions/clusters/dynamic_forward_proxy/cluster.cc +++ b/source/extensions/clusters/dynamic_forward_proxy/cluster.cc @@ -98,14 +98,10 @@ Cluster::~Cluster() { void Cluster::startPreInit() { // If we are attaching to a pre-populated cache we need to initialize our hosts. - std::unique_ptr hosts_added; dns_cache_->iterateHostMap( [&](absl::string_view host, const Common::DynamicForwardProxy::DnsHostInfoSharedPtr& info) { - addOrUpdateHost(host, info, hosts_added); + addOrUpdateHost(host, info); }); - if (hosts_added) { - updatePriorityState(*hosts_added, {}); - } onPreInitComplete(); } @@ -237,9 +233,11 @@ bool Cluster::ClusterInfo::checkIdle() { void Cluster::addOrUpdateHost( absl::string_view host, - const Extensions::Common::DynamicForwardProxy::DnsHostInfoSharedPtr& host_info, - std::unique_ptr& hosts_added) { - Upstream::LogicalHostSharedPtr emplaced_host; + const Extensions::Common::DynamicForwardProxy::DnsHostInfoSharedPtr& host_info) { + Upstream::HostVector hosts_added, hosts_removed; + Upstream::LogicalHostSharedPtr new_host = std::make_shared( + info(), std::string{host}, host_info->address(), host_info->addressList(), + dummy_locality_lb_endpoint_, dummy_lb_endpoint_, nullptr, time_source_); { absl::WriterMutexLock lock{&host_map_lock_}; @@ -251,7 +249,6 @@ void Cluster::addOrUpdateHost( // future. const auto host_map_it = host_map_.find(host); if (host_map_it != host_map_.end()) { - // If we only have an address change, we can do that swap inline without any other updates. // The appropriate R/W locking is in place to allow this. The details of this locking are: // - Hosts are not thread local, they are global. // - We take a read lock when reading the address and a write lock when changing it. @@ -267,49 +264,36 @@ void Cluster::addOrUpdateHost( // semantics, meaning the cache would expose multiple addresses and the // cluster would create multiple logical hosts based on those addresses. // We will leave this is a follow up depending on need. - ASSERT(host_info == host_map_it->second.shared_host_info_); ASSERT(host_map_it->second.shared_host_info_->address() != host_map_it->second.logical_host_->address()); - ENVOY_LOG(debug, "updating dfproxy cluster host address '{}'", host); - host_map_it->second.logical_host_->setNewAddresses( - host_info->address(), host_info->addressList(), dummy_lb_endpoint_); - return; - } - ENVOY_LOG(debug, "adding new dfproxy cluster host '{}'", host); + // remove the old host + hosts_removed.emplace_back(host_map_it->second.logical_host_); + ENVOY_LOG(debug, "updating dfproxy cluster host address '{}'", host); + host_map_.erase(host_map_it); + host_map_.try_emplace(host, host_info, new_host); - emplaced_host = host_map_ - .try_emplace(host, host_info, - std::make_shared( - info(), std::string{host}, host_info->address(), - host_info->addressList(), dummy_locality_lb_endpoint_, - dummy_lb_endpoint_, nullptr, time_source_)) - .first->second.logical_host_; + } else { + ENVOY_LOG(debug, "adding new dfproxy cluster host '{}'", host); + host_map_.try_emplace(host, host_info, new_host); + } + hosts_added.emplace_back(new_host); } - ASSERT(emplaced_host); - if (hosts_added == nullptr) { - hosts_added = std::make_unique(); - } - hosts_added->emplace_back(emplaced_host); + ASSERT(hosts_added.size() > 0); + updatePriorityState(hosts_added, hosts_removed); } void Cluster::onDnsHostAddOrUpdate( const std::string& host, const Extensions::Common::DynamicForwardProxy::DnsHostInfoSharedPtr& host_info) { - ENVOY_LOG(debug, "Adding host info for {}", host); - - std::unique_ptr hosts_added; - addOrUpdateHost(host, host_info, hosts_added); - if (hosts_added != nullptr) { - ASSERT(!hosts_added->empty()); - updatePriorityState(*hosts_added, {}); - } + ENVOY_LOG(debug, "Adding/Updating host info for {}", host); + addOrUpdateHost(host, host_info); } void Cluster::updatePriorityState(const Upstream::HostVector& hosts_added, const Upstream::HostVector& hosts_removed) { - Upstream::PriorityStateManager priority_state_manager(*this, local_info_, nullptr); + Upstream::PriorityStateManager priority_state_manager(*this, local_info_, nullptr, random_); priority_state_manager.initializePriorityFor(dummy_locality_lb_endpoint_); { absl::ReaderMutexLock lock{&host_map_lock_}; diff --git a/source/extensions/clusters/dynamic_forward_proxy/cluster.h b/source/extensions/clusters/dynamic_forward_proxy/cluster.h index f974474b3e900..82e62c01711d7 100644 --- a/source/extensions/clusters/dynamic_forward_proxy/cluster.h +++ b/source/extensions/clusters/dynamic_forward_proxy/cluster.h @@ -161,8 +161,7 @@ class Cluster : public Upstream::BaseDynamicClusterImpl, void addOrUpdateHost(absl::string_view host, - const Extensions::Common::DynamicForwardProxy::DnsHostInfoSharedPtr& host_info, - std::unique_ptr& hosts_added) + const Extensions::Common::DynamicForwardProxy::DnsHostInfoSharedPtr& host_info) ABSL_LOCKS_EXCLUDED(host_map_lock_); void updatePriorityState(const Upstream::HostVector& hosts_added, diff --git a/source/extensions/clusters/eds/eds.cc b/source/extensions/clusters/eds/eds.cc index 962b0f249e497..76d0b258514fd 100644 --- a/source/extensions/clusters/eds/eds.cc +++ b/source/extensions/clusters/eds/eds.cc @@ -50,7 +50,8 @@ void EdsClusterImpl::startPreInit() { subscription_->start({edsServiceName()}); void EdsClusterImpl::BatchUpdateHelper::batchUpdate(PrioritySet::HostUpdateCb& host_update_cb) { absl::flat_hash_set all_new_hosts; - PriorityStateManager priority_state_manager(parent_, parent_.local_info_, &host_update_cb); + PriorityStateManager priority_state_manager(parent_, parent_.local_info_, &host_update_cb, + parent_.random_); for (const auto& locality_lb_endpoint : cluster_load_assignment_.endpoints()) { parent_.validateEndpointsForZoneAwareRouting(locality_lb_endpoint); @@ -370,9 +371,10 @@ void EdsClusterImpl::reloadHealthyHostsHelper(const HostSharedPtr& host) { HostsPerLocalityConstSharedPtr hosts_per_locality_copy = host_set->hostsPerLocality().filter( {[&host_to_exclude](const Host& host) { return &host != host_to_exclude.get(); }})[0]; - prioritySet().updateHosts( - priority, HostSetImpl::partitionHosts(hosts_copy, hosts_per_locality_copy), - host_set->localityWeights(), {}, hosts_to_remove, absl::nullopt, absl::nullopt); + prioritySet().updateHosts(priority, + HostSetImpl::partitionHosts(hosts_copy, hosts_per_locality_copy), + host_set->localityWeights(), {}, hosts_to_remove, random_.random(), + absl::nullopt, absl::nullopt); } } diff --git a/source/extensions/clusters/logical_dns/logical_dns_cluster.cc b/source/extensions/clusters/logical_dns/logical_dns_cluster.cc index f1e84526b68f4..26e7c38d2b789 100644 --- a/source/extensions/clusters/logical_dns/logical_dns_cluster.cc +++ b/source/extensions/clusters/logical_dns/logical_dns_cluster.cc @@ -121,7 +121,7 @@ void LogicalDnsCluster::startResolve() { lbEndpoint(), nullptr, time_source_); const auto& locality_lb_endpoint = localityLbEndpoint(); - PriorityStateManager priority_state_manager(*this, local_info_, nullptr); + PriorityStateManager priority_state_manager(*this, local_info_, nullptr, random_); priority_state_manager.initializePriorityFor(locality_lb_endpoint); priority_state_manager.registerHostForPriority(logical_host_, locality_lb_endpoint); diff --git a/source/extensions/clusters/original_dst/original_dst_cluster.cc b/source/extensions/clusters/original_dst/original_dst_cluster.cc index 2b3313862933c..d6e39adbbe992 100644 --- a/source/extensions/clusters/original_dst/original_dst_cluster.cc +++ b/source/extensions/clusters/original_dst/original_dst_cluster.cc @@ -236,9 +236,9 @@ void OriginalDstCluster::addHost(HostSharedPtr& host) { const auto& first_host_set = priority_set_.getOrCreateHostSet(0); HostVectorSharedPtr all_hosts(new HostVector(first_host_set.hosts())); all_hosts->emplace_back(host); - priority_set_.updateHosts(0, - HostSetImpl::partitionHosts(all_hosts, HostsPerLocalityImpl::empty()), - {}, {std::move(host)}, {}, absl::nullopt, absl::nullopt); + priority_set_.updateHosts( + 0, HostSetImpl::partitionHosts(all_hosts, HostsPerLocalityImpl::empty()), {}, + {std::move(host)}, {}, random_.random(), absl::nullopt, absl::nullopt); } void OriginalDstCluster::cleanup() { diff --git a/source/extensions/clusters/redis/crc16.cc b/source/extensions/clusters/redis/crc16.cc index d3102b71f533b..d714a1e67f677 100644 --- a/source/extensions/clusters/redis/crc16.cc +++ b/source/extensions/clusters/redis/crc16.cc @@ -1,4 +1,4 @@ -#include "crc16.h" +#include "source/extensions/clusters/redis/crc16.h" #include "absl/strings/string_view.h" diff --git a/source/extensions/clusters/redis/redis_cluster.cc b/source/extensions/clusters/redis/redis_cluster.cc index 55f80bb1a1440..9bcf635292b93 100644 --- a/source/extensions/clusters/redis/redis_cluster.cc +++ b/source/extensions/clusters/redis/redis_cluster.cc @@ -1,4 +1,4 @@ -#include "redis_cluster.h" +#include "source/extensions/clusters/redis/redis_cluster.h" #include #include @@ -75,7 +75,7 @@ void RedisCluster::startPreInit() { void RedisCluster::updateAllHosts(const Upstream::HostVector& hosts_added, const Upstream::HostVector& hosts_removed, uint32_t current_priority) { - Upstream::PriorityStateManager priority_state_manager(*this, local_info_, nullptr); + Upstream::PriorityStateManager priority_state_manager(*this, local_info_, nullptr, random_); auto locality_lb_endpoint = localityLbEndpoint(); priority_state_manager.initializePriorityFor(locality_lb_endpoint); diff --git a/source/extensions/clusters/redis/redis_cluster_lb.cc b/source/extensions/clusters/redis/redis_cluster_lb.cc index 441b5a2b276c4..476fda7cd59c4 100644 --- a/source/extensions/clusters/redis/redis_cluster_lb.cc +++ b/source/extensions/clusters/redis/redis_cluster_lb.cc @@ -1,4 +1,4 @@ -#include "redis_cluster_lb.h" +#include "source/extensions/clusters/redis/redis_cluster_lb.h" namespace Envoy { namespace Extensions { @@ -56,8 +56,8 @@ bool RedisClusterLoadBalancerFactory::onClusterSlotUpdate(ClusterSlotsSharedPtr& primary_and_replicas->push_back(replica_host->second); } - shard_vector->emplace_back( - std::make_shared(primary_host->second, replicas, primary_and_replicas)); + shard_vector->emplace_back(std::make_shared(primary_host->second, replicas, + primary_and_replicas, random_)); } for (auto i = slot.start(); i <= slot.end(); ++i) { @@ -90,7 +90,7 @@ void RedisClusterLoadBalancerFactory::onHostHealthUpdate() { for (auto const& shard : *current_shard_vector) { shard_vector->emplace_back(std::make_shared( - shard->primary(), shard->replicas().hostsPtr(), shard->allHosts().hostsPtr())); + shard->primary(), shard->replicas().hostsPtr(), shard->allHosts().hostsPtr(), random_)); } { diff --git a/source/extensions/clusters/redis/redis_cluster_lb.h b/source/extensions/clusters/redis/redis_cluster_lb.h index 66b00e0897a46..222a8bae8dce1 100644 --- a/source/extensions/clusters/redis/redis_cluster_lb.h +++ b/source/extensions/clusters/redis/redis_cluster_lb.h @@ -155,14 +155,14 @@ class RedisClusterLoadBalancerFactory : public ClusterSlotUpdateCallBack, class RedisShard { public: RedisShard(Upstream::HostConstSharedPtr primary, Upstream::HostVectorConstSharedPtr replicas, - Upstream::HostVectorConstSharedPtr all_hosts) + Upstream::HostVectorConstSharedPtr all_hosts, Random::RandomGenerator& random) : primary_(std::move(primary)) { replicas_.updateHosts(Upstream::HostSetImpl::partitionHosts( std::move(replicas), Upstream::HostsPerLocalityImpl::empty()), - nullptr, {}, {}); + nullptr, {}, {}, random.random()); all_hosts_.updateHosts(Upstream::HostSetImpl::partitionHosts( std::move(all_hosts), Upstream::HostsPerLocalityImpl::empty()), - nullptr, {}, {}); + nullptr, {}, {}, random.random()); } const Upstream::HostConstSharedPtr primary() const { return primary_; } const Upstream::HostSetImpl& replicas() const { return replicas_; } diff --git a/source/extensions/clusters/static/static_cluster.cc b/source/extensions/clusters/static/static_cluster.cc index 8d6a3e85766a4..37ee4c968e209 100644 --- a/source/extensions/clusters/static/static_cluster.cc +++ b/source/extensions/clusters/static/static_cluster.cc @@ -10,8 +10,8 @@ namespace Upstream { StaticClusterImpl::StaticClusterImpl(const envoy::config::cluster::v3::Cluster& cluster, ClusterFactoryContext& context) : ClusterImplBase(cluster, context), - priority_state_manager_( - new PriorityStateManager(*this, context.serverFactoryContext().localInfo(), nullptr)) { + priority_state_manager_(new PriorityStateManager( + *this, context.serverFactoryContext().localInfo(), nullptr, random_)) { const envoy::config::endpoint::v3::ClusterLoadAssignment& cluster_load_assignment = cluster.load_assignment(); overprovisioning_factor_ = PROTOBUF_GET_WRAPPED_OR_DEFAULT( diff --git a/source/extensions/clusters/strict_dns/strict_dns_cluster.cc b/source/extensions/clusters/strict_dns/strict_dns_cluster.cc index 306f773d13ada..dcb0c10f783d7 100644 --- a/source/extensions/clusters/strict_dns/strict_dns_cluster.cc +++ b/source/extensions/clusters/strict_dns/strict_dns_cluster.cc @@ -59,7 +59,7 @@ void StrictDnsClusterImpl::startPreInit() { void StrictDnsClusterImpl::updateAllHosts(const HostVector& hosts_added, const HostVector& hosts_removed, uint32_t current_priority) { - PriorityStateManager priority_state_manager(*this, local_info_, nullptr); + PriorityStateManager priority_state_manager(*this, local_info_, nullptr, random_); // At this point we know that we are different so make a new host list and notify. // // TODO(dio): The uniqueness of a host address resolved in STRICT_DNS cluster per priority is not diff --git a/source/extensions/common/dubbo/codec.cc b/source/extensions/common/dubbo/codec.cc index 9daed14fb79ef..5fdb34843cdf6 100644 --- a/source/extensions/common/dubbo/codec.cc +++ b/source/extensions/common/dubbo/codec.cc @@ -1,4 +1,3 @@ -#include "codec.h" #include "source/extensions/common/dubbo/codec.h" #include @@ -8,10 +7,9 @@ #include "source/common/common/assert.h" #include "source/extensions/common/dubbo/hessian2_serializer_impl.h" +#include "source/extensions/common/dubbo/message.h" #include "source/extensions/common/dubbo/message_impl.h" - -#include "message.h" -#include "metadata.h" +#include "source/extensions/common/dubbo/metadata.h" namespace Envoy { namespace Extensions { diff --git a/source/extensions/common/dubbo/codec.h b/source/extensions/common/dubbo/codec.h index d20f127ff57f9..e177c642b18e4 100644 --- a/source/extensions/common/dubbo/codec.h +++ b/source/extensions/common/dubbo/codec.h @@ -1,10 +1,9 @@ #pragma once +#include "source/extensions/common/dubbo/message.h" +#include "source/extensions/common/dubbo/metadata.h" #include "source/extensions/common/dubbo/serializer.h" -#include "message.h" -#include "metadata.h" - namespace Envoy { namespace Extensions { namespace Common { diff --git a/source/extensions/common/dubbo/hessian2_serializer_impl.cc b/source/extensions/common/dubbo/hessian2_serializer_impl.cc index 0c846562ec8b7..506e315c8d94d 100644 --- a/source/extensions/common/dubbo/hessian2_serializer_impl.cc +++ b/source/extensions/common/dubbo/hessian2_serializer_impl.cc @@ -7,11 +7,11 @@ #include "source/common/common/assert.h" #include "source/common/common/macros.h" #include "source/extensions/common/dubbo/hessian2_utils.h" +#include "source/extensions/common/dubbo/message.h" #include "source/extensions/common/dubbo/message_impl.h" +#include "source/extensions/common/dubbo/metadata.h" #include "hessian2/object.hpp" -#include "message.h" -#include "metadata.h" namespace Envoy { namespace Extensions { diff --git a/source/extensions/common/dynamic_forward_proxy/dns_cache.h b/source/extensions/common/dynamic_forward_proxy/dns_cache.h index 25af3e34e6492..0860ed2db0b88 100644 --- a/source/extensions/common/dynamic_forward_proxy/dns_cache.h +++ b/source/extensions/common/dynamic_forward_proxy/dns_cache.h @@ -31,7 +31,7 @@ class DnsHostInfo { if (!Runtime::runtimeFeatureEnabled("envoy.reloadable_features.dfp_mixed_scheme")) { return std::string(host); } - if (Http::HeaderUtility::hostHasPort(host)) { + if (Envoy::Http::HeaderUtility::hostHasPort(host)) { return std::string(host); } return absl::StrCat(host, ":", default_port); diff --git a/source/extensions/config_subscription/grpc/grpc_collection_subscription_factory.cc b/source/extensions/config_subscription/grpc/grpc_collection_subscription_factory.cc index bfd2c706070c6..ca0266efa6427 100644 --- a/source/extensions/config_subscription/grpc/grpc_collection_subscription_factory.cc +++ b/source/extensions/config_subscription/grpc/grpc_collection_subscription_factory.cc @@ -17,15 +17,17 @@ SubscriptionPtr DeltaGrpcCollectionConfigSubscriptionFactory::create( CustomConfigValidatorsPtr custom_config_validators = std::make_unique( data.validation_visitor_, data.server_, api_config_source.config_validators()); - JitteredExponentialBackOffStrategyPtr backoff_strategy = - Utility::prepareJitteredExponentialBackOffStrategy( - api_config_source, data.api_.randomGenerator(), SubscriptionFactory::RetryInitialDelayMs, - SubscriptionFactory::RetryMaxDelayMs); + auto strategy_or_error = Utility::prepareJitteredExponentialBackOffStrategy( + api_config_source, data.api_.randomGenerator(), SubscriptionFactory::RetryInitialDelayMs, + SubscriptionFactory::RetryMaxDelayMs); + THROW_IF_STATUS_NOT_OK(strategy_or_error, throw); + JitteredExponentialBackOffStrategyPtr backoff_strategy = std::move(strategy_or_error.value()); + auto factory_or_error = Config::Utility::factoryForGrpcApiConfigSource( + data.cm_.grpcAsyncClientManager(), api_config_source, data.scope_, true); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); GrpcMuxContext grpc_mux_context{ - /*async_client_=*/Config::Utility::factoryForGrpcApiConfigSource( - data.cm_.grpcAsyncClientManager(), api_config_source, data.scope_, true) - ->createUncachedRawAsyncClient(), + factory_or_error.value()->createUncachedRawAsyncClient(), /*dispatcher_=*/data.dispatcher_, /*service_method_=*/deltaGrpcMethod(data.type_url_), /*local_info_=*/data.local_info_, diff --git a/source/extensions/config_subscription/grpc/grpc_mux_impl.cc b/source/extensions/config_subscription/grpc/grpc_mux_impl.cc index 4f21f98a400e0..3c9473dd51051 100644 --- a/source/extensions/config_subscription/grpc/grpc_mux_impl.cc +++ b/source/extensions/config_subscription/grpc/grpc_mux_impl.cc @@ -76,7 +76,7 @@ GrpcMuxImpl::GrpcMuxImpl(GrpcMuxContext& grpc_mux_context, bool skip_subsequent_ [this](absl::string_view resource_type_url) { onDynamicContextUpdate(resource_type_url); })) { - Config::Utility::checkLocalInfo("ads", local_info_); + THROW_IF_NOT_OK(Config::Utility::checkLocalInfo("ads", local_info_)); AllMuxes::get().insert(this); } diff --git a/source/extensions/config_subscription/grpc/grpc_subscription_factory.cc b/source/extensions/config_subscription/grpc/grpc_subscription_factory.cc index 722bdf5b689e4..aea80ca7b8f1d 100644 --- a/source/extensions/config_subscription/grpc/grpc_subscription_factory.cc +++ b/source/extensions/config_subscription/grpc/grpc_subscription_factory.cc @@ -20,15 +20,17 @@ GrpcConfigSubscriptionFactory::create(ConfigSubscriptionFactory::SubscriptionDat data.validation_visitor_, data.server_, api_config_source.config_validators()); const std::string control_plane_id = Utility::getGrpcControlPlane(api_config_source).value_or(""); - JitteredExponentialBackOffStrategyPtr backoff_strategy = - Utility::prepareJitteredExponentialBackOffStrategy( - api_config_source, data.api_.randomGenerator(), SubscriptionFactory::RetryInitialDelayMs, - SubscriptionFactory::RetryMaxDelayMs); + auto strategy_or_error = Utility::prepareJitteredExponentialBackOffStrategy( + api_config_source, data.api_.randomGenerator(), SubscriptionFactory::RetryInitialDelayMs, + SubscriptionFactory::RetryMaxDelayMs); + THROW_IF_STATUS_NOT_OK(strategy_or_error, throw); + JitteredExponentialBackOffStrategyPtr backoff_strategy = std::move(strategy_or_error.value()); + auto factory_or_error = Utility::factoryForGrpcApiConfigSource( + data.cm_.grpcAsyncClientManager(), api_config_source, data.scope_, true); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); GrpcMuxContext grpc_mux_context{ - /*async_client_=*/Utility::factoryForGrpcApiConfigSource(data.cm_.grpcAsyncClientManager(), - api_config_source, data.scope_, true) - ->createUncachedRawAsyncClient(), + /*async_client_=*/factory_or_error.value()->createUncachedRawAsyncClient(), /*dispatcher_=*/data.dispatcher_, /*service_method_=*/sotwGrpcMethod(data.type_url_), /*local_info_=*/data.local_info_, @@ -63,15 +65,17 @@ DeltaGrpcConfigSubscriptionFactory::create(ConfigSubscriptionFactory::Subscripti CustomConfigValidatorsPtr custom_config_validators = std::make_unique( data.validation_visitor_, data.server_, api_config_source.config_validators()); - JitteredExponentialBackOffStrategyPtr backoff_strategy = - Utility::prepareJitteredExponentialBackOffStrategy( - api_config_source, data.api_.randomGenerator(), SubscriptionFactory::RetryInitialDelayMs, - SubscriptionFactory::RetryMaxDelayMs); + auto strategy_or_error = Utility::prepareJitteredExponentialBackOffStrategy( + api_config_source, data.api_.randomGenerator(), SubscriptionFactory::RetryInitialDelayMs, + SubscriptionFactory::RetryMaxDelayMs); + THROW_IF_STATUS_NOT_OK(strategy_or_error, throw); + JitteredExponentialBackOffStrategyPtr backoff_strategy = std::move(strategy_or_error.value()); + auto factory_or_error = Utility::factoryForGrpcApiConfigSource( + data.cm_.grpcAsyncClientManager(), api_config_source, data.scope_, true); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); GrpcMuxContext grpc_mux_context{ - /*async_client_=*/Utility::factoryForGrpcApiConfigSource(data.cm_.grpcAsyncClientManager(), - api_config_source, data.scope_, true) - ->createUncachedRawAsyncClient(), + /*async_client_=*/factory_or_error.value()->createUncachedRawAsyncClient(), /*dispatcher_=*/data.dispatcher_, /*service_method_=*/deltaGrpcMethod(data.type_url_), /*local_info_=*/data.local_info_, diff --git a/source/extensions/config_subscription/grpc/xds_mux/grpc_mux_impl.cc b/source/extensions/config_subscription/grpc/xds_mux/grpc_mux_impl.cc index ebcb675b62a08..7f15728b26ef0 100644 --- a/source/extensions/config_subscription/grpc/xds_mux/grpc_mux_impl.cc +++ b/source/extensions/config_subscription/grpc/xds_mux/grpc_mux_impl.cc @@ -56,7 +56,7 @@ GrpcMuxImpl::GrpcMuxImpl(std::unique_ptr subscription_state_fac xds_resources_delegate_(grpc_mux_content.xds_resources_delegate_), eds_resources_cache_(std::move(grpc_mux_content.eds_resources_cache_)), target_xds_authority_(grpc_mux_content.target_xds_authority_) { - Config::Utility::checkLocalInfo("ads", grpc_mux_content.local_info_); + THROW_IF_NOT_OK(Config::Utility::checkLocalInfo("ads", grpc_mux_content.local_info_)); AllMuxes::get().insert(this); } diff --git a/source/extensions/config_subscription/rest/http_subscription_impl.cc b/source/extensions/config_subscription/rest/http_subscription_impl.cc index 2f641d3b9e7b7..b629c964a64fa 100644 --- a/source/extensions/config_subscription/rest/http_subscription_impl.cc +++ b/source/extensions/config_subscription/rest/http_subscription_impl.cc @@ -149,6 +149,22 @@ void HttpSubscriptionImpl::disableInitFetchTimeoutTimer() { } } +std::chrono::milliseconds HttpSubscriptionFactory::apiConfigSourceRefreshDelay( + const envoy::config::core::v3::ApiConfigSource& api_config_source) { + if (!api_config_source.has_refresh_delay()) { + throwEnvoyExceptionOrPanic("refresh_delay is required for REST API configuration sources"); + } + + return std::chrono::milliseconds( + DurationUtil::durationToMilliseconds(api_config_source.refresh_delay())); +} + +std::chrono::milliseconds HttpSubscriptionFactory::apiConfigSourceRequestTimeout( + const envoy::config::core::v3::ApiConfigSource& api_config_source) { + return std::chrono::milliseconds( + PROTOBUF_GET_MS_OR_DEFAULT(api_config_source, request_timeout, 1000)); +} + REGISTER_FACTORY(HttpSubscriptionFactory, ConfigSubscriptionFactory); } // namespace Config diff --git a/source/extensions/config_subscription/rest/http_subscription_impl.h b/source/extensions/config_subscription/rest/http_subscription_impl.h index 9275ca6169878..9f8009471c65d 100644 --- a/source/extensions/config_subscription/rest/http_subscription_impl.h +++ b/source/extensions/config_subscription/rest/http_subscription_impl.h @@ -67,13 +67,29 @@ class HttpSubscriptionImpl : public Http::RestApiFetcher, class HttpSubscriptionFactory : public ConfigSubscriptionFactory { public: std::string name() const override { return "envoy.config_subscription.rest"; } + + /** + * Extract refresh_delay as a std::chrono::milliseconds from + * envoy::config::core::v3::ApiConfigSource. + */ + static std::chrono::milliseconds + apiConfigSourceRefreshDelay(const envoy::config::core::v3::ApiConfigSource& api_config_source); + + /** + * Extract request_timeout as a std::chrono::milliseconds from + * envoy::config::core::v3::ApiConfigSource. If request_timeout isn't set in the config source, a + * default value of 1s will be returned. + */ + static std::chrono::milliseconds + apiConfigSourceRequestTimeout(const envoy::config::core::v3::ApiConfigSource& api_config_source); + SubscriptionPtr create(SubscriptionData& data) override { const envoy::config::core::v3::ApiConfigSource& api_config_source = data.config_.api_config_source(); return std::make_unique( data.local_info_, data.cm_, api_config_source.cluster_names()[0], data.dispatcher_, - data.api_.randomGenerator(), Utility::apiConfigSourceRefreshDelay(api_config_source), - Utility::apiConfigSourceRequestTimeout(api_config_source), restMethod(data.type_url_), + data.api_.randomGenerator(), apiConfigSourceRefreshDelay(api_config_source), + apiConfigSourceRequestTimeout(api_config_source), restMethod(data.type_url_), data.type_url_, data.callbacks_, data.resource_decoder_, data.stats_, Utility::configSourceInitialFetchTimeout(data.config_), data.validation_visitor_); } diff --git a/source/extensions/extensions_metadata.yaml b/source/extensions/extensions_metadata.yaml index 587fb00c03631..119da4c25529f 100644 --- a/source/extensions/extensions_metadata.yaml +++ b/source/extensions/extensions_metadata.yaml @@ -205,8 +205,10 @@ envoy.filters.http.aws_lambda: envoy.filters.http.aws_request_signing: categories: - envoy.filters.http + - envoy.filters.http.upstream security_posture: requires_trusted_downstream_and_upstream status: alpha + status_upstream: alpha type_urls: - envoy.extensions.filters.http.aws_request_signing.v3.AwsRequestSigning - envoy.extensions.filters.http.aws_request_signing.v3.AwsRequestSigningPerRoute @@ -1021,7 +1023,7 @@ envoy.resource_monitors.downstream_connections: categories: - envoy.resource_monitors security_posture: data_plane_agnostic - status: alpha + status: stable type_urls: - envoy.extensions.resource_monitors.downstream_connections.v3.DownstreamConnectionsConfig envoy.resource_monitors.fixed_heap: diff --git a/source/extensions/filters/common/expr/context.cc b/source/extensions/filters/common/expr/context.cc index a84fe1e4cf472..cc30fb794a958 100644 --- a/source/extensions/filters/common/expr/context.cc +++ b/source/extensions/filters/common/expr/context.cc @@ -164,7 +164,7 @@ absl::optional ResponseWrapper::operator[](CelValue key) const { } else if (value == Trailers) { return CelValue::CreateMap(&trailers_); } else if (value == Flags) { - return CelValue::CreateInt64(info_.responseFlags()); + return CelValue::CreateInt64(info_.legacyResponseFlags()); } else if (value == GrpcStatus) { auto const& optional_status = Grpc::Common::getGrpcStatus( trailers_.value_ ? *trailers_.value_ : *Http::StaticEmptyHeaders::get().response_trailers, @@ -357,49 +357,54 @@ absl::optional XDSWrapper::operator[](CelValue key) const { return {}; } auto value = key.StringOrDie().value(); + if (value == Node) { + if (local_info_) { + return CelProtoWrapper::CreateMessage(&local_info_->node(), &arena_); + } + return {}; + } + if (info_ == nullptr) { + return {}; + } if (value == ClusterName) { - const auto cluster_info = info_.upstreamClusterInfo(); + const auto cluster_info = info_->upstreamClusterInfo(); if (cluster_info && cluster_info.value()) { return CelValue::CreateString(&cluster_info.value()->name()); } } else if (value == ClusterMetadata) { - const auto cluster_info = info_.upstreamClusterInfo(); + const auto cluster_info = info_->upstreamClusterInfo(); if (cluster_info && cluster_info.value()) { return CelProtoWrapper::CreateMessage(&cluster_info.value()->metadata(), &arena_); } } else if (value == RouteName) { - if (info_.route()) { - return CelValue::CreateString(&info_.route()->routeName()); + if (info_->route()) { + return CelValue::CreateString(&info_->route()->routeName()); } } else if (value == RouteMetadata) { - if (info_.route()) { - return CelProtoWrapper::CreateMessage(&info_.route()->metadata(), &arena_); + if (info_->route()) { + return CelProtoWrapper::CreateMessage(&info_->route()->metadata(), &arena_); } } else if (value == UpstreamHostMetadata) { - const auto upstream_info = info_.upstreamInfo(); + const auto upstream_info = info_->upstreamInfo(); if (upstream_info && upstream_info->upstreamHost()) { return CelProtoWrapper::CreateMessage(upstream_info->upstreamHost()->metadata().get(), &arena_); } } else if (value == FilterChainName) { - const auto filter_chain_info = info_.downstreamAddressProvider().filterChainInfo(); + const auto filter_chain_info = info_->downstreamAddressProvider().filterChainInfo(); const absl::string_view filter_chain_name = filter_chain_info.has_value() ? filter_chain_info->name() : absl::string_view{}; return CelValue::CreateStringView(filter_chain_name); } else if (value == ListenerMetadata) { - const auto listener_info = info_.downstreamAddressProvider().listenerInfo(); + const auto listener_info = info_->downstreamAddressProvider().listenerInfo(); if (listener_info) { return CelProtoWrapper::CreateMessage(&listener_info->metadata(), &arena_); } } else if (value == ListenerDirection) { - const auto listener_info = info_.downstreamAddressProvider().listenerInfo(); + const auto listener_info = info_->downstreamAddressProvider().listenerInfo(); if (listener_info) { return CelValue::CreateInt64(listener_info->direction()); } - } else if (value == Node) { - if (local_info_) { - return CelProtoWrapper::CreateMessage(&local_info_->node(), &arena_); - } } return {}; } diff --git a/source/extensions/filters/common/expr/context.h b/source/extensions/filters/common/expr/context.h index b397a6e358688..b0487084a19dc 100644 --- a/source/extensions/filters/common/expr/context.h +++ b/source/extensions/filters/common/expr/context.h @@ -237,13 +237,13 @@ class FilterStateWrapper : public BaseWrapper { class XDSWrapper : public BaseWrapper { public: - XDSWrapper(Protobuf::Arena& arena, const StreamInfo::StreamInfo& info, + XDSWrapper(Protobuf::Arena& arena, const StreamInfo::StreamInfo* info, const LocalInfo::LocalInfo* local_info) : BaseWrapper(arena), info_(info), local_info_(local_info) {} absl::optional operator[](CelValue key) const override; private: - const StreamInfo::StreamInfo& info_; + const StreamInfo::StreamInfo* info_; const LocalInfo::LocalInfo* local_info_; }; diff --git a/source/extensions/filters/common/expr/evaluator.cc b/source/extensions/filters/common/expr/evaluator.cc index a6eec90a949a5..5ca4d71041f76 100644 --- a/source/extensions/filters/common/expr/evaluator.cc +++ b/source/extensions/filters/common/expr/evaluator.cc @@ -34,15 +34,19 @@ const ActivationLookupTable& getActivationTokens() { absl::optional StreamActivation::FindValue(absl::string_view name, Protobuf::Arena* arena) const { - if (activation_info_ == nullptr) { - return {}; - } - const StreamInfo::StreamInfo& info = *activation_info_; const auto& tokens = getActivationTokens(); const auto token = tokens.find(name); if (token == tokens.end()) { return {}; } + if (token->second == ActivationToken::XDS) { + return CelValue::CreateMap( + Protobuf::Arena::Create(arena, *arena, activation_info_, local_info_)); + } + if (activation_info_ == nullptr) { + return {}; + } + const StreamInfo::StreamInfo& info = *activation_info_; switch (token->second) { case ActivationToken::Request: return CelValue::CreateMap( @@ -64,8 +68,7 @@ absl::optional StreamActivation::FindValue(absl::string_view name, return CelValue::CreateMap( Protobuf::Arena::Create(arena, *arena, info.filterState())); case ActivationToken::XDS: - return CelValue::CreateMap( - Protobuf::Arena::Create(arena, *arena, info, local_info_)); + return {}; } return {}; } diff --git a/source/extensions/filters/common/ext_authz/ext_authz_http_impl.cc b/source/extensions/filters/common/ext_authz/ext_authz_http_impl.cc index 49a1a95e52186..bd6bfa0e26bd6 100644 --- a/source/extensions/filters/common/ext_authz/ext_authz_http_impl.cc +++ b/source/extensions/filters/common/ext_authz/ext_authz_http_impl.cc @@ -11,10 +11,10 @@ #include "source/common/http/async_client_impl.h" #include "source/common/http/codes.h" #include "source/common/runtime/runtime_features.h" +#include "source/extensions/filters/common/ext_authz/check_request_utils.h" #include "absl/strings/str_cat.h" #include "absl/types/optional.h" -#include "check_request_utils.h" namespace Envoy { namespace Extensions { diff --git a/source/extensions/filters/common/rbac/BUILD b/source/extensions/filters/common/rbac/BUILD index 69df5c59201e3..5cb7ee9d20951 100644 --- a/source/extensions/filters/common/rbac/BUILD +++ b/source/extensions/filters/common/rbac/BUILD @@ -38,6 +38,7 @@ envoy_cc_library( "//source/common/http:header_utility_lib", "//source/common/network:cidr_range_lib", "//source/extensions/filters/common/expr:evaluator_lib", + "//source/extensions/path/match/uri_template:uri_template_match_lib", "@envoy_api//envoy/config/core/v3:pkg_cc_proto", "@envoy_api//envoy/config/rbac/v3:pkg_cc_proto", "@envoy_api//envoy/config/route/v3:pkg_cc_proto", diff --git a/source/extensions/filters/common/rbac/matchers.cc b/source/extensions/filters/common/rbac/matchers.cc index 10ca0b60ed40f..5df6db1bfe376 100644 --- a/source/extensions/filters/common/rbac/matchers.cc +++ b/source/extensions/filters/common/rbac/matchers.cc @@ -38,6 +38,13 @@ MatcherConstSharedPtr Matcher::create(const envoy::config::rbac::v3::Permission& return std::make_shared(permission.requested_server_name()); case envoy::config::rbac::v3::Permission::RuleCase::kUrlPath: return std::make_shared(permission.url_path()); + case envoy::config::rbac::v3::Permission::RuleCase::kUriTemplate: { + auto& factory = + Config::Utility::getAndCheckFactory(permission.uri_template()); + ProtobufTypes::MessagePtr config = Envoy::Config::Utility::translateAnyToFactoryConfig( + permission.uri_template().typed_config(), validation_visitor, factory); + return std::make_shared(factory.createPathMatcher(*config)); + } case envoy::config::rbac::v3::Permission::RuleCase::kMatcher: { auto& factory = Config::Utility::getAndCheckFactory(permission.matcher()); @@ -262,6 +269,12 @@ bool PathMatcher::matches(const Network::Connection&, const Envoy::Http::Request return path_matcher_.match(headers.getPathValue()); } +bool UriTemplateMatcher::matches(const Network::Connection&, + const Envoy::Http::RequestHeaderMap& headers, + const StreamInfo::StreamInfo&) const { + return uri_template_matcher_->match(headers.getPathValue()); +} + } // namespace RBAC } // namespace Common } // namespace Filters diff --git a/source/extensions/filters/common/rbac/matchers.h b/source/extensions/filters/common/rbac/matchers.h index 2a2b41ea7f8f2..b5914f397f3fd 100644 --- a/source/extensions/filters/common/rbac/matchers.h +++ b/source/extensions/filters/common/rbac/matchers.h @@ -14,6 +14,7 @@ #include "source/common/http/header_utility.h" #include "source/common/network/cidr_range.h" #include "source/extensions/filters/common/expr/evaluator.h" +#include "source/extensions/path/match/uri_template/uri_template_match.h" namespace Envoy { namespace Extensions { @@ -283,6 +284,18 @@ class PathMatcher : public Matcher { const Matchers::PathMatcher path_matcher_; }; +class UriTemplateMatcher : public Matcher { +public: + UriTemplateMatcher(const absl::StatusOr uri_template_matcher) + : uri_template_matcher_(uri_template_matcher.value()) {} + + bool matches(const Network::Connection&, const Envoy::Http::RequestHeaderMap& headers, + const StreamInfo::StreamInfo&) const override; + +private: + const Router::PathMatcherSharedPtr uri_template_matcher_; +}; + } // namespace RBAC } // namespace Common } // namespace Filters diff --git a/source/extensions/filters/http/adaptive_concurrency/controller/gradient_controller.cc b/source/extensions/filters/http/adaptive_concurrency/controller/gradient_controller.cc index c00112da2ede4..cb5287bc08709 100644 --- a/source/extensions/filters/http/adaptive_concurrency/controller/gradient_controller.cc +++ b/source/extensions/filters/http/adaptive_concurrency/controller/gradient_controller.cc @@ -168,7 +168,10 @@ uint32_t GradientController::calculateNewLimit() { const auto buffered_min_rtt = min_rtt_.count() + min_rtt_.count() * config_.minRTTBufferPercent(); const double raw_gradient = static_cast(buffered_min_rtt) / sample_rtt_.count(); const double gradient = std::max(0.5, std::min(2.0, raw_gradient)); - stats_.gradient_.set(gradient); + + // Scale the value by 1000 when reporting it to maintain the granularity of its details + // See: https://github.com/envoyproxy/envoy/issues/31695 + stats_.gradient_.set(gradient * 1000); const double limit = concurrencyLimit() * gradient; const double burst_headroom = sqrt(limit); diff --git a/source/extensions/filters/http/aws_request_signing/config.cc b/source/extensions/filters/http/aws_request_signing/config.cc index 67ea8df9f7cad..578ae81d2b6c1 100644 --- a/source/extensions/filters/http/aws_request_signing/config.cc +++ b/source/extensions/filters/http/aws_request_signing/config.cc @@ -46,11 +46,10 @@ SigningAlgorithm getSigningAlgorithm( PANIC_DUE_TO_CORRUPT_ENUM; } -Http::FilterFactoryCb AwsRequestSigningFilterFactory::createFilterFactoryFromProtoTyped( - const AwsRequestSigningProtoConfig& config, const std::string& stats_prefix, - Server::Configuration::FactoryContext& context) { - - auto& server_context = context.serverFactoryContext(); +absl::StatusOr +AwsRequestSigningFilterFactory::createFilterFactoryFromProtoTyped( + const AwsRequestSigningProtoConfig& config, const std::string& stats_prefix, DualInfo dual_info, + Server::Configuration::ServerFactoryContext& server_context) { auto credentials_provider = std::make_shared( @@ -77,7 +76,7 @@ Http::FilterFactoryCb AwsRequestSigningFilterFactory::createFilterFactoryFromPro } auto filter_config = - std::make_shared(std::move(signer), stats_prefix, context.scope(), + std::make_shared(std::move(signer), stats_prefix, dual_info.scope, config.host_rewrite(), config.use_unsigned_payload()); return [filter_config](Http::FilterChainFactoryCallbacks& callbacks) -> void { auto filter = std::make_shared(filter_config); @@ -126,6 +125,8 @@ AwsRequestSigningFilterFactory::createRouteSpecificFilterConfigTyped( */ REGISTER_FACTORY(AwsRequestSigningFilterFactory, Server::Configuration::NamedHttpFilterConfigFactory); +REGISTER_FACTORY(UpstreamAwsRequestSigningFilterFactory, + Server::Configuration::UpstreamHttpFilterConfigFactory); } // namespace AwsRequestSigningFilter } // namespace HttpFilters diff --git a/source/extensions/filters/http/aws_request_signing/config.h b/source/extensions/filters/http/aws_request_signing/config.h index e066323ee9e5f..93cd82648205c 100644 --- a/source/extensions/filters/http/aws_request_signing/config.h +++ b/source/extensions/filters/http/aws_request_signing/config.h @@ -20,16 +20,16 @@ using AwsRequestSigningProtoPerRouteConfig = * Config registration for the AWS request signing filter. */ class AwsRequestSigningFilterFactory - : public Common::FactoryBase { + : public Common::DualFactoryBase { public: - AwsRequestSigningFilterFactory() : FactoryBase("envoy.filters.http.aws_request_signing") {} + AwsRequestSigningFilterFactory() : DualFactoryBase("envoy.filters.http.aws_request_signing") {} private: - Http::FilterFactoryCb + absl::StatusOr createFilterFactoryFromProtoTyped(const AwsRequestSigningProtoConfig& proto_config, - const std::string& stats_prefix, - Server::Configuration::FactoryContext& context) override; + const std::string& stats_prefix, DualInfo dual_info, + Server::Configuration::ServerFactoryContext& context) override; Router::RouteSpecificFilterConfigConstSharedPtr createRouteSpecificFilterConfigTyped(const AwsRequestSigningProtoPerRouteConfig& per_route_config, @@ -37,6 +37,8 @@ class AwsRequestSigningFilterFactory ProtobufMessage::ValidationVisitor&) override; }; +using UpstreamAwsRequestSigningFilterFactory = AwsRequestSigningFilterFactory; + } // namespace AwsRequestSigningFilter } // namespace HttpFilters } // namespace Extensions diff --git a/source/extensions/filters/http/bandwidth_limit/bandwidth_limit.h b/source/extensions/filters/http/bandwidth_limit/bandwidth_limit.h index 7f9b001c6e1fc..3f800fd6fe2b5 100644 --- a/source/extensions/filters/http/bandwidth_limit/bandwidth_limit.h +++ b/source/extensions/filters/http/bandwidth_limit/bandwidth_limit.h @@ -162,7 +162,7 @@ class BandwidthLimiter : public Http::StreamFilter, Logger::Loggable response_limiter_; Stats::TimespanPtr request_latency_; Stats::TimespanPtr response_latency_; - std::chrono::milliseconds request_duration_; + std::chrono::milliseconds request_duration_ = zero_milliseconds_; std::chrono::milliseconds request_delay_ = zero_milliseconds_; std::chrono::milliseconds response_delay_ = zero_milliseconds_; Http::ResponseTrailerMap* trailers_; diff --git a/source/extensions/filters/http/cache/cache_filter.cc b/source/extensions/filters/http/cache/cache_filter.cc index 8fe7fa56dbf7c..c17486d360c28 100644 --- a/source/extensions/filters/http/cache/cache_filter.cc +++ b/source/extensions/filters/http/cache/cache_filter.cc @@ -641,7 +641,7 @@ void CacheFilter::encodeCachedResponse() { ? static_cast(decoder_callbacks_) : static_cast(encoder_callbacks_); - callbacks->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::ResponseFromCacheFilter); + callbacks->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::ResponseFromCacheFilter); callbacks->streamInfo().setResponseCodeDetails( CacheResponseCodeDetails::get().ResponseFromCacheFilter); diff --git a/source/extensions/filters/http/connect_grpc_bridge/filter.h b/source/extensions/filters/http/connect_grpc_bridge/filter.h index d585f914ff478..8fe0d8d7ac8cc 100644 --- a/source/extensions/filters/http/connect_grpc_bridge/filter.h +++ b/source/extensions/filters/http/connect_grpc_bridge/filter.h @@ -5,8 +5,7 @@ #include "source/common/common/logger.h" #include "source/extensions/filters/http/common/factory_base.h" #include "source/extensions/filters/http/common/pass_through_filter.h" - -#include "end_stream_response.h" +#include "source/extensions/filters/http/connect_grpc_bridge/end_stream_response.h" namespace Envoy { namespace Extensions { diff --git a/source/extensions/filters/http/dynamic_forward_proxy/proxy_filter.cc b/source/extensions/filters/http/dynamic_forward_proxy/proxy_filter.cc index f9cf7c253f470..da91a3c205f82 100644 --- a/source/extensions/filters/http/dynamic_forward_proxy/proxy_filter.cc +++ b/source/extensions/filters/http/dynamic_forward_proxy/proxy_filter.cc @@ -379,7 +379,8 @@ void ProxyFilter::onDnsResolutionFail() { return; } - decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::DnsResolutionFailed); + decoder_callbacks_->streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::DnsResolutionFailed); decoder_callbacks_->sendLocalReply(Http::Code::ServiceUnavailable, ResponseStrings::get().DnsResolutionFailure, nullptr, absl::nullopt, RcDetails::get().DnsResolutionFailure); diff --git a/source/extensions/filters/http/ext_authz/ext_authz.cc b/source/extensions/filters/http/ext_authz/ext_authz.cc index fe713f7e98e41..5a38c228b24bd 100644 --- a/source/extensions/filters/http/ext_authz/ext_authz.cc +++ b/source/extensions/filters/http/ext_authz/ext_authz.cc @@ -136,7 +136,7 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, ENVOY_STREAM_LOG(trace, "ext_authz filter is disabled. Deny the request.", *decoder_callbacks_); decoder_callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UnauthorizedExternalService); + StreamInfo::CoreResponseFlag::UnauthorizedExternalService); decoder_callbacks_->sendLocalReply( config_->statusOnError(), EMPTY_STRING, nullptr, absl::nullopt, Filters::Common::ExtAuthz::ResponseCodeDetails::get().AuthzError); @@ -152,16 +152,16 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, !(end_stream || Http::Utility::isWebSocketUpgradeRequest(headers) || Http::Utility::isH2UpgradeRequest(headers)); + max_request_bytes_ = config_->maxRequestBytes(); if (buffer_data_) { ENVOY_STREAM_LOG(debug, "ext_authz filter is buffering the request", *decoder_callbacks_); allow_partial_message_ = check_settings.has_with_request_body() ? check_settings.with_request_body().allow_partial_message() : config_->allowPartialMessage(); - max_request_bytes_ = check_settings.has_with_request_body() - ? check_settings.with_request_body().max_request_bytes() - : config_->maxRequestBytes(); - + if (check_settings.has_with_request_body()) { + max_request_bytes_ = check_settings.with_request_body().max_request_bytes(); + } if (!allow_partial_message_) { decoder_callbacks_->setDecoderBufferLimit(max_request_bytes_); } @@ -422,7 +422,7 @@ void Filter::onComplete(Filters::Common::ExtAuthz::ResponsePtr&& response) { // setResponseFlag must be called before sendLocalReply decoder_callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UnauthorizedExternalService); + StreamInfo::CoreResponseFlag::UnauthorizedExternalService); decoder_callbacks_->sendLocalReply( response->status_code, response->body, [&headers = response->headers_to_set, @@ -467,7 +467,7 @@ void Filter::onComplete(Filters::Common::ExtAuthz::ResponsePtr&& response) { trace, "ext_authz filter rejected the request with an error. Response status code: {}", *decoder_callbacks_, enumToInt(config_->statusOnError())); decoder_callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UnauthorizedExternalService); + StreamInfo::CoreResponseFlag::UnauthorizedExternalService); decoder_callbacks_->sendLocalReply( config_->statusOnError(), EMPTY_STRING, nullptr, absl::nullopt, Filters::Common::ExtAuthz::ResponseCodeDetails::get().AuthzError); diff --git a/source/extensions/filters/http/ext_authz/ext_authz.h b/source/extensions/filters/http/ext_authz/ext_authz.h index d18aa27cccccd..7a24e2d84debb 100644 --- a/source/extensions/filters/http/ext_authz/ext_authz.h +++ b/source/extensions/filters/http/ext_authz/ext_authz.h @@ -388,7 +388,7 @@ class Filter : public Logger::Loggable, // This is used to hold the final configs after we merge them with per-route configs. bool allow_partial_message_{}; - uint32_t max_request_bytes_; + uint32_t max_request_bytes_{}; // Used to identify if the callback to onComplete() is synchronous (on the stack) or asynchronous. bool initiating_call_{}; diff --git a/source/extensions/filters/http/ext_proc/BUILD b/source/extensions/filters/http/ext_proc/BUILD index 484395f170d30..976de7b294b86 100644 --- a/source/extensions/filters/http/ext_proc/BUILD +++ b/source/extensions/filters/http/ext_proc/BUILD @@ -19,8 +19,10 @@ envoy_cc_library( "ext_proc.h", "processor_state.h", ], + tags = ["skip_on_windows"], deps = [ ":client_interface", + ":matching_utils_lib", ":mutation_utils_lib", "//envoy/event:timer_interface", "//envoy/http:filter_interface", @@ -44,6 +46,7 @@ envoy_cc_extension( name = "config", srcs = ["config.cc"], hdrs = ["config.h"], + tags = ["skip_on_windows"], deps = [ ":client_lib", ":ext_proc", @@ -55,6 +58,7 @@ envoy_cc_extension( envoy_cc_library( name = "client_interface", hdrs = ["client.h"], + tags = ["skip_on_windows"], deps = [ "//envoy/grpc:async_client_manager_interface", "//envoy/grpc:status", @@ -80,10 +84,37 @@ envoy_cc_library( ], ) +envoy_cc_library( + name = "matching_utils_lib", + srcs = ["matching_utils.cc"], + hdrs = ["matching_utils.h"], + copts = select({ + "//bazel:windows_x86_64": [], + "//conditions:default": [ + "-DUSE_CEL_PARSER", + ], + }), + tags = ["skip_on_windows"], + deps = [ + "//envoy/http:header_map_interface", + "//source/common/protobuf", + "//source/extensions/filters/common/expr:evaluator_lib", + "@com_google_cel_cpp//eval/public:cel_expr_builder_factory", + ] + select( + { + "//bazel:windows_x86_64": [], + "//conditions:default": [ + "@com_google_cel_cpp//parser", + ], + }, + ), +) + envoy_cc_library( name = "client_lib", srcs = ["client_impl.cc"], hdrs = ["client_impl.h"], + tags = ["skip_on_windows"], deps = [ ":client_interface", "//envoy/grpc:async_client_interface", diff --git a/source/extensions/filters/http/ext_proc/config.cc b/source/extensions/filters/http/ext_proc/config.cc index d119530368438..ee45fc6a73c46 100644 --- a/source/extensions/filters/http/ext_proc/config.cc +++ b/source/extensions/filters/http/ext_proc/config.cc @@ -1,5 +1,6 @@ #include "source/extensions/filters/http/ext_proc/config.h" +#include "source/extensions/filters/common/expr/evaluator.h" #include "source/extensions/filters/http/ext_proc/client_impl.h" #include "source/extensions/filters/http/ext_proc/ext_proc.h" @@ -15,9 +16,11 @@ Http::FilterFactoryCb ExternalProcessingFilterConfig::createFilterFactoryFromPro PROTOBUF_GET_MS_OR_DEFAULT(proto_config, message_timeout, DefaultMessageTimeoutMs); const uint32_t max_message_timeout_ms = PROTOBUF_GET_MS_OR_DEFAULT(proto_config, max_message_timeout, DefaultMaxMessageTimeoutMs); - const auto filter_config = - std::make_shared(proto_config, std::chrono::milliseconds(message_timeout_ms), - max_message_timeout_ms, context.scope(), stats_prefix); + const auto filter_config = std::make_shared( + proto_config, std::chrono::milliseconds(message_timeout_ms), max_message_timeout_ms, + context.scope(), stats_prefix, + Envoy::Extensions::Filters::Common::Expr::getBuilder(context.serverFactoryContext()), + context.serverFactoryContext().localInfo()); return [filter_config, grpc_service = proto_config.grpc_service(), &context](Http::FilterChainFactoryCallbacks& callbacks) { @@ -44,9 +47,11 @@ ExternalProcessingFilterConfig::createFilterFactoryFromProtoWithServerContextTyp PROTOBUF_GET_MS_OR_DEFAULT(proto_config, message_timeout, DefaultMessageTimeoutMs); const uint32_t max_message_timeout_ms = PROTOBUF_GET_MS_OR_DEFAULT(proto_config, max_message_timeout, DefaultMaxMessageTimeoutMs); - const auto filter_config = - std::make_shared(proto_config, std::chrono::milliseconds(message_timeout_ms), - max_message_timeout_ms, server_context.scope(), stats_prefix); + const auto filter_config = std::make_shared( + proto_config, std::chrono::milliseconds(message_timeout_ms), max_message_timeout_ms, + server_context.scope(), stats_prefix, + Envoy::Extensions::Filters::Common::Expr::getBuilder(server_context), + server_context.localInfo()); return [filter_config, grpc_service = proto_config.grpc_service(), &server_context](Http::FilterChainFactoryCallbacks& callbacks) { diff --git a/source/extensions/filters/http/ext_proc/ext_proc.cc b/source/extensions/filters/http/ext_proc/ext_proc.cc index 82b6848f9d3fd..4b41dbdc57a24 100644 --- a/source/extensions/filters/http/ext_proc/ext_proc.cc +++ b/source/extensions/filters/http/ext_proc/ext_proc.cc @@ -115,6 +115,49 @@ ExtProcLoggingInfo::grpcCalls(envoy::config::core::v3::TrafficDirection traffic_ : encoding_processor_grpc_calls_; } +std::vector +FilterConfigPerRoute::initNamespaces(const Protobuf::RepeatedPtrField& ns) { + if (ns.empty()) { + return {}; + } + + std::vector namespaces; + for (const auto& single_ns : ns) { + namespaces.emplace_back(single_ns); + } + return namespaces; +} + +absl::optional> +FilterConfigPerRoute::initUntypedForwardingNamespaces(const ExtProcPerRoute& config) { + if (!config.has_overrides() || !config.overrides().has_metadata_options() || + !config.overrides().metadata_options().has_forwarding_namespaces()) { + return absl::nullopt; + } + + return {initNamespaces(config.overrides().metadata_options().forwarding_namespaces().untyped())}; +} + +absl::optional> +FilterConfigPerRoute::initTypedForwardingNamespaces(const ExtProcPerRoute& config) { + if (!config.has_overrides() || !config.overrides().has_metadata_options() || + !config.overrides().metadata_options().has_forwarding_namespaces()) { + return absl::nullopt; + } + + return {initNamespaces(config.overrides().metadata_options().forwarding_namespaces().typed())}; +} + +absl::optional> +FilterConfigPerRoute::initUntypedReceivingNamespaces(const ExtProcPerRoute& config) { + if (!config.has_overrides() || !config.overrides().has_metadata_options() || + !config.overrides().metadata_options().has_receiving_namespaces()) { + return absl::nullopt; + } + + return {initNamespaces(config.overrides().metadata_options().receiving_namespaces().untyped())}; +} + absl::optional FilterConfigPerRoute::initProcessingMode(const ExtProcPerRoute& config) { if (!config.disabled() && config.has_overrides() && config.overrides().has_processing_mode()) { @@ -142,14 +185,26 @@ FilterConfigPerRoute::mergeProcessingMode(const FilterConfigPerRoute& less_speci FilterConfigPerRoute::FilterConfigPerRoute(const ExtProcPerRoute& config) : disabled_(config.disabled()), processing_mode_(initProcessingMode(config)), - grpc_service_(initGrpcService(config)) {} + grpc_service_(initGrpcService(config)), + untyped_forwarding_namespaces_(initUntypedForwardingNamespaces(config)), + typed_forwarding_namespaces_(initTypedForwardingNamespaces(config)), + untyped_receiving_namespaces_(initUntypedReceivingNamespaces(config)) {} FilterConfigPerRoute::FilterConfigPerRoute(const FilterConfigPerRoute& less_specific, const FilterConfigPerRoute& more_specific) : disabled_(more_specific.disabled()), processing_mode_(mergeProcessingMode(less_specific, more_specific)), grpc_service_(more_specific.grpcService().has_value() ? more_specific.grpcService() - : less_specific.grpcService()) {} + : less_specific.grpcService()), + untyped_forwarding_namespaces_(more_specific.untypedForwardingMetadataNamespaces().has_value() + ? more_specific.untypedForwardingMetadataNamespaces() + : less_specific.untypedForwardingMetadataNamespaces()), + typed_forwarding_namespaces_(more_specific.typedForwardingMetadataNamespaces().has_value() + ? more_specific.typedForwardingMetadataNamespaces() + : less_specific.typedForwardingMetadataNamespaces()), + untyped_receiving_namespaces_(more_specific.untypedReceivingMetadataNamespaces().has_value() + ? more_specific.untypedReceivingMetadataNamespaces() + : less_specific.untypedReceivingMetadataNamespaces()) {} void Filter::setDecoderFilterCallbacks(Http::StreamDecoderFilterCallbacks& callbacks) { Http::PassThroughFilter::setDecoderFilterCallbacks(callbacks); @@ -221,7 +276,8 @@ void Filter::onDestroy() { } FilterHeadersStatus Filter::onHeaders(ProcessorState& state, - Http::RequestOrResponseHeaderMap& headers, bool end_stream) { + Http::RequestOrResponseHeaderMap& headers, bool end_stream, + ProtobufWkt::Struct* proto) { switch (openStream()) { case StreamOpenState::Error: return FilterHeadersStatus::StopIteration; @@ -235,10 +291,14 @@ FilterHeadersStatus Filter::onHeaders(ProcessorState& state, state.setHeaders(&headers); state.setHasNoBody(end_stream); ProcessingRequest req; + addDynamicMetadata(state, req); auto* headers_req = state.mutableHeaders(req); MutationUtils::headersToProto(headers, config_->allowedHeaders(), config_->disallowedHeaders(), *headers_req->mutable_headers()); headers_req->set_end_of_stream(end_stream); + if (proto != nullptr) { + (*headers_req->mutable_attributes())[FilterName] = *proto; + } state.onStartProcessorCall(std::bind(&Filter::onMessageTimeout, this), config_->messageTimeout(), ProcessorState::CallbackState::HeadersCallback); ENVOY_LOG(debug, "Sending headers message"); @@ -257,7 +317,17 @@ FilterHeadersStatus Filter::decodeHeaders(RequestHeaderMap& headers, bool end_st FilterHeadersStatus status = FilterHeadersStatus::Continue; if (decoding_state_.sendHeaders()) { - status = onHeaders(decoding_state_, headers, end_stream); + ProtobufWkt::Struct proto; + + if (config_->expressionManager().hasRequestExpr()) { + auto activation_ptr = Filters::Common::Expr::createActivation( + &config_->expressionManager().localInfo(), decoding_state_.callbacks()->streamInfo(), + &headers, nullptr, nullptr); + proto = config_->expressionManager().evaluateRequestAttributes(*activation_ptr); + } + + status = onHeaders(decoding_state_, headers, end_stream, + config_->expressionManager().hasRequestExpr() ? &proto : nullptr); ENVOY_LOG(trace, "onHeaders returning {}", static_cast(status)); } else { ENVOY_LOG(trace, "decodeHeaders: Skipped header processing"); @@ -535,7 +605,17 @@ FilterHeadersStatus Filter::encodeHeaders(ResponseHeaderMap& headers, bool end_s FilterHeadersStatus status = FilterHeadersStatus::Continue; if (!processing_complete_ && encoding_state_.sendHeaders()) { - status = onHeaders(encoding_state_, headers, end_stream); + ProtobufWkt::Struct proto; + + if (config_->expressionManager().hasResponseExpr()) { + auto activation_ptr = Filters::Common::Expr::createActivation( + &config_->expressionManager().localInfo(), encoding_state_.callbacks()->streamInfo(), + nullptr, &headers, nullptr); + proto = config_->expressionManager().evaluateResponseAttributes(*activation_ptr); + } + + status = onHeaders(encoding_state_, headers, end_stream, + config_->expressionManager().hasResponseExpr() ? &proto : nullptr); ENVOY_LOG(trace, "onHeaders returns {}", static_cast(status)); } else { ENVOY_LOG(trace, "encodeHeaders: Skipped header processing"); @@ -570,6 +650,7 @@ ProcessingRequest Filter::setupBodyChunk(ProcessorState& state, const Buffer::In bool end_stream) { ENVOY_LOG(debug, "Sending a body chunk of {} bytes, end_stream {}", data.length(), end_stream); ProcessingRequest req; + addDynamicMetadata(state, req); auto* body_req = state.mutableBody(req); body_req->set_end_of_stream(end_stream); body_req->set_body(data.toString()); @@ -586,6 +667,7 @@ void Filter::sendBodyChunk(ProcessorState& state, ProcessorState::CallbackState void Filter::sendTrailers(ProcessorState& state, const Http::HeaderMap& trailers) { ProcessingRequest req; + addDynamicMetadata(state, req); auto* trailers_req = state.mutableTrailers(req); MutationUtils::headersToProto(trailers, config_->allowedHeaders(), config_->disallowedHeaders(), *trailers_req->mutable_trailers()); @@ -639,6 +721,93 @@ void Filter::onNewTimeout(const ProtobufWkt::Duration& override_message_timeout) stats_.override_message_timeout_received_.inc(); } +void Filter::addDynamicMetadata(const ProcessorState& state, ProcessingRequest& req) { + // get the callbacks from the ProcessorState. This will be the appropriate + // callbacks for the current state of the filter + auto* cb = state.callbacks(); + envoy::config::core::v3::Metadata forwarding_metadata; + + // If metadata_context_namespaces is specified, pass matching filter metadata to the ext_proc + // service. If metadata key is set in both the connection and request metadata then the value + // will be the request metadata value. The metadata will only be searched for the callbacks + // corresponding to the traffic direction at the time of the external processing request. + const auto& request_metadata = cb->streamInfo().dynamicMetadata().filter_metadata(); + for (const auto& context_key : state.untypedForwardingMetadataNamespaces()) { + if (const auto metadata_it = request_metadata.find(context_key); + metadata_it != request_metadata.end()) { + (*forwarding_metadata.mutable_filter_metadata())[metadata_it->first] = metadata_it->second; + } else if (cb->connection().has_value()) { + const auto& connection_metadata = + cb->connection().value().get().streamInfo().dynamicMetadata().filter_metadata(); + if (const auto metadata_it = connection_metadata.find(context_key); + metadata_it != connection_metadata.end()) { + (*forwarding_metadata.mutable_filter_metadata())[metadata_it->first] = metadata_it->second; + } + } + } + + // If typed_metadata_context_namespaces is specified, pass matching typed filter metadata to the + // ext_proc service. If metadata key is set in both the connection and request metadata then + // the value will be the request metadata value. The metadata will only be searched for the + // callbacks corresponding to the traffic direction at the time of the external processing + // request. + const auto& request_typed_metadata = cb->streamInfo().dynamicMetadata().typed_filter_metadata(); + for (const auto& context_key : state.typedForwardingMetadataNamespaces()) { + if (const auto metadata_it = request_typed_metadata.find(context_key); + metadata_it != request_typed_metadata.end()) { + (*forwarding_metadata.mutable_typed_filter_metadata())[metadata_it->first] = + metadata_it->second; + } else if (cb->connection().has_value()) { + const auto& connection_typed_metadata = + cb->connection().value().get().streamInfo().dynamicMetadata().typed_filter_metadata(); + if (const auto metadata_it = connection_typed_metadata.find(context_key); + metadata_it != connection_typed_metadata.end()) { + (*forwarding_metadata.mutable_typed_filter_metadata())[metadata_it->first] = + metadata_it->second; + } + } + } + + *req.mutable_metadata_context() = forwarding_metadata; +} + +void Filter::setDynamicMetadata(Http::StreamFilterCallbacks* cb, const ProcessorState& state, + const ProcessingResponse& response) { + if (state.untypedReceivingMetadataNamespaces().empty() || !response.has_dynamic_metadata()) { + if (response.has_dynamic_metadata()) { + ENVOY_LOG(debug, "processing response included dynamic metadata, but no receiving " + "namespaces are configured."); + } + return; + } + + auto response_metadata = response.dynamic_metadata().fields(); + auto receiving_namespaces = state.untypedReceivingMetadataNamespaces(); + for (const auto& context_key : response_metadata) { + bool found_allowed_namespace = false; + if (auto metadata_it = + std::find(receiving_namespaces.begin(), receiving_namespaces.end(), context_key.first); + metadata_it != receiving_namespaces.end()) { + cb->streamInfo().setDynamicMetadata(context_key.first, + response_metadata.at(context_key.first).struct_value()); + found_allowed_namespace = true; + } + if (!found_allowed_namespace) { + ENVOY_LOG(debug, + "processing response included dynamic metadata for namespace not " + "configured for receiving: {}", + context_key.first); + } + } +} + +void Filter::setEncoderDynamicMetadata(const ProcessingResponse& response) { + setDynamicMetadata(encoder_callbacks_, encoding_state_, response); +} +void Filter::setDecoderDynamicMetadata(const ProcessingResponse& response) { + setDynamicMetadata(decoder_callbacks_, decoding_state_, response); +} + void Filter::onReceiveMessage(std::unique_ptr&& r) { if (processing_complete_) { ENVOY_LOG(debug, "Ignoring stream message received after processing complete"); @@ -669,21 +838,27 @@ void Filter::onReceiveMessage(std::unique_ptr&& r) { absl::Status processing_status; switch (response->response_case()) { case ProcessingResponse::ResponseCase::kRequestHeaders: + setDecoderDynamicMetadata(*response); processing_status = decoding_state_.handleHeadersResponse(response->request_headers()); break; case ProcessingResponse::ResponseCase::kResponseHeaders: + setEncoderDynamicMetadata(*response); processing_status = encoding_state_.handleHeadersResponse(response->response_headers()); break; case ProcessingResponse::ResponseCase::kRequestBody: + setDecoderDynamicMetadata(*response); processing_status = decoding_state_.handleBodyResponse(response->request_body()); break; case ProcessingResponse::ResponseCase::kResponseBody: + setEncoderDynamicMetadata(*response); processing_status = encoding_state_.handleBodyResponse(response->response_body()); break; case ProcessingResponse::ResponseCase::kRequestTrailers: + setDecoderDynamicMetadata(*response); processing_status = decoding_state_.handleTrailersResponse(response->request_trailers()); break; case ProcessingResponse::ResponseCase::kResponseTrailers: + setEncoderDynamicMetadata(*response); processing_status = encoding_state_.handleTrailersResponse(response->response_trailers()); break; case ProcessingResponse::ResponseCase::kImmediateResponse: @@ -693,6 +868,7 @@ void Filter::onReceiveMessage(std::unique_ptr&& r) { processing_status = absl::FailedPreconditionError("unhandled immediate response due to config disabled it"); } else { + setDecoderDynamicMetadata(*response); // We won't be sending anything more to the stream after we // receive this message. ENVOY_LOG(debug, "Sending immediate response"); @@ -882,7 +1058,7 @@ void Filter::mergePerRouteConfig() { ENVOY_LOG_MISC(debug, "Failed to retrieve the correct type of route specific filter config"); return; } - if (!merged_config) { + if (!merged_config.has_value()) { merged_config.emplace(*typed_cfg); } else { merged_config.emplace(FilterConfigPerRoute(merged_config.value(), *typed_cfg)); @@ -912,6 +1088,34 @@ void Filter::mergePerRouteConfig() { grpc_service_ = *merged_config->grpcService(); config_with_hash_key_.setConfig(*merged_config->grpcService()); } + + // For metadata namespaces, we only override the existing value if we have a + // value from our merged config. We indicate a lack of value from the merged + // config with absl::nullopt + + if (merged_config->untypedForwardingMetadataNamespaces().has_value()) { + untyped_forwarding_namespaces_ = merged_config->untypedForwardingMetadataNamespaces().value(); + ENVOY_LOG(trace, + "Setting new untyped forwarding metadata namespaces from per-route configuration"); + decoding_state_.setUntypedForwardingMetadataNamespaces(untyped_forwarding_namespaces_); + encoding_state_.setUntypedForwardingMetadataNamespaces(untyped_forwarding_namespaces_); + } + + if (merged_config->typedForwardingMetadataNamespaces().has_value()) { + typed_forwarding_namespaces_ = merged_config->typedForwardingMetadataNamespaces().value(); + ENVOY_LOG(trace, + "Setting new typed forwarding metadata namespaces from per-route configuration"); + decoding_state_.setTypedForwardingMetadataNamespaces(typed_forwarding_namespaces_); + encoding_state_.setTypedForwardingMetadataNamespaces(typed_forwarding_namespaces_); + } + + if (merged_config->untypedReceivingMetadataNamespaces().has_value()) { + untyped_receiving_namespaces_ = merged_config->untypedReceivingMetadataNamespaces().value(); + ENVOY_LOG(trace, + "Setting new untyped receiving metadata namespaces from per-route configuration"); + decoding_state_.setUntypedReceivingMetadataNamespaces(untyped_receiving_namespaces_); + encoding_state_.setUntypedReceivingMetadataNamespaces(untyped_receiving_namespaces_); + } } std::string responseCaseToString(const ProcessingResponse::ResponseCase response_case) { diff --git a/source/extensions/filters/http/ext_proc/ext_proc.h b/source/extensions/filters/http/ext_proc/ext_proc.h index 20a2e676719f4..78d97cbe9bab0 100644 --- a/source/extensions/filters/http/ext_proc/ext_proc.h +++ b/source/extensions/filters/http/ext_proc/ext_proc.h @@ -24,6 +24,7 @@ #include "source/extensions/filters/common/mutation_rules/mutation_rules.h" #include "source/extensions/filters/http/common/pass_through_filter.h" #include "source/extensions/filters/http/ext_proc/client.h" +#include "source/extensions/filters/http/ext_proc/matching_utils.h" #include "source/extensions/filters/http/ext_proc/processor_state.h" namespace Envoy { @@ -126,7 +127,9 @@ class FilterConfig { FilterConfig(const envoy::extensions::filters::http::ext_proc::v3::ExternalProcessor& config, const std::chrono::milliseconds message_timeout, const uint32_t max_message_timeout_ms, Stats::Scope& scope, - const std::string& stats_prefix) + const std::string& stats_prefix, + Extensions::Filters::Common::Expr::BuilderInstanceSharedPtr builder, + const LocalInfo::LocalInfo& local_info) : failure_mode_allow_(config.failure_mode_allow()), disable_clear_route_cache_(config.disable_clear_route_cache()), message_timeout_(message_timeout), max_message_timeout_ms_(max_message_timeout_ms), @@ -136,7 +139,18 @@ class FilterConfig { allow_mode_override_(config.allow_mode_override()), disable_immediate_response_(config.disable_immediate_response()), allowed_headers_(initHeaderMatchers(config.forward_rules().allowed_headers())), - disallowed_headers_(initHeaderMatchers(config.forward_rules().disallowed_headers())) {} + disallowed_headers_(initHeaderMatchers(config.forward_rules().disallowed_headers())), + untyped_forwarding_namespaces_( + config.metadata_options().forwarding_namespaces().untyped().begin(), + config.metadata_options().forwarding_namespaces().untyped().end()), + typed_forwarding_namespaces_( + config.metadata_options().forwarding_namespaces().typed().begin(), + config.metadata_options().forwarding_namespaces().typed().end()), + untyped_receiving_namespaces_( + config.metadata_options().receiving_namespaces().untyped().begin(), + config.metadata_options().receiving_namespaces().untyped().end()), + expression_manager_(builder, local_info, config.request_attributes(), + config.response_attributes()) {} bool failureModeAllow() const { return failure_mode_allow_; } @@ -164,7 +178,21 @@ class FilterConfig { return disallowed_headers_; } - const Envoy::ProtobufWkt::Struct& filterMetadata() const { return filter_metadata_; } + const ProtobufWkt::Struct& filterMetadata() const { return filter_metadata_; } + + const ExpressionManager& expressionManager() const { return expression_manager_; } + + const std::vector& untypedForwardingMetadataNamespaces() const { + return untyped_forwarding_namespaces_; + } + + const std::vector& typedForwardingMetadataNamespaces() const { + return typed_forwarding_namespaces_; + } + + const std::vector& untypedReceivingMetadataNamespaces() const { + return untyped_receiving_namespaces_; + } private: ExtProcFilterStats generateStats(const std::string& prefix, @@ -172,17 +200,6 @@ class FilterConfig { const std::string final_prefix = absl::StrCat(prefix, "ext_proc.", filter_stats_prefix); return {ALL_EXT_PROC_FILTER_STATS(POOL_COUNTER_PREFIX(scope, final_prefix))}; } - const std::vector - initHeaderMatchers(const envoy::type::matcher::v3::ListStringMatcher& header_list) { - std::vector header_matchers; - for (const auto& matcher : header_list.patterns()) { - header_matchers.push_back( - std::make_unique>( - matcher)); - } - return header_matchers; - } - const bool failure_mode_allow_; const bool disable_clear_route_cache_; const std::chrono::milliseconds message_timeout_; @@ -191,7 +208,7 @@ class FilterConfig { ExtProcFilterStats stats_; const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode processing_mode_; const Filters::Common::MutationRules::Checker mutation_checker_; - const Envoy::ProtobufWkt::Struct filter_metadata_; + const ProtobufWkt::Struct filter_metadata_; // If set to true, allow the processing mode to be modified by the ext_proc response. const bool allow_mode_override_; // If set to true, disable the immediate response from the ext_proc server, which means @@ -201,6 +218,12 @@ class FilterConfig { const std::vector allowed_headers_; // Empty disallowed_header_ means disallow nothing, i.e, allow all. const std::vector disallowed_headers_; + + const std::vector untyped_forwarding_namespaces_; + const std::vector typed_forwarding_namespaces_; + const std::vector untyped_receiving_namespaces_; + + const ExpressionManager expression_manager_; }; using FilterConfigSharedPtr = std::shared_ptr; @@ -225,6 +248,17 @@ class FilterConfigPerRoute : public Router::RouteSpecificFilterConfig { return grpc_service_; } + const absl::optional>& + untypedForwardingMetadataNamespaces() const { + return untyped_forwarding_namespaces_; + } + const absl::optional>& typedForwardingMetadataNamespaces() const { + return typed_forwarding_namespaces_; + } + const absl::optional>& untypedReceivingMetadataNamespaces() const { + return untyped_receiving_namespaces_; + } + private: absl::optional initProcessingMode(const envoy::extensions::filters::http::ext_proc::v3::ExtProcPerRoute& config); @@ -232,6 +266,17 @@ class FilterConfigPerRoute : public Router::RouteSpecificFilterConfig { absl::optional initGrpcService(const envoy::extensions::filters::http::ext_proc::v3::ExtProcPerRoute& config); + std::vector initNamespaces(const Protobuf::RepeatedPtrField& ns); + + absl::optional> initUntypedForwardingNamespaces( + const envoy::extensions::filters::http::ext_proc::v3::ExtProcPerRoute& config); + + absl::optional> initTypedForwardingNamespaces( + const envoy::extensions::filters::http::ext_proc::v3::ExtProcPerRoute& config); + + absl::optional> initUntypedReceivingNamespaces( + const envoy::extensions::filters::http::ext_proc::v3::ExtProcPerRoute& config); + absl::optional mergeProcessingMode(const FilterConfigPerRoute& less_specific, const FilterConfigPerRoute& more_specific); @@ -240,6 +285,10 @@ class FilterConfigPerRoute : public Router::RouteSpecificFilterConfig { const absl::optional processing_mode_; const absl::optional grpc_service_; + + const absl::optional> untyped_forwarding_namespaces_; + const absl::optional> typed_forwarding_namespaces_; + const absl::optional> untyped_receiving_namespaces_; }; class Filter : public Logger::Loggable, @@ -262,8 +311,14 @@ class Filter : public Logger::Loggable, const envoy::config::core::v3::GrpcService& grpc_service) : config_(config), client_(std::move(client)), stats_(config->stats()), grpc_service_(grpc_service), config_with_hash_key_(grpc_service), - decoding_state_(*this, config->processingMode()), - encoding_state_(*this, config->processingMode()) {} + decoding_state_(*this, config->processingMode(), + config->untypedForwardingMetadataNamespaces(), + config->typedForwardingMetadataNamespaces(), + config->untypedReceivingMetadataNamespaces()), + encoding_state_(*this, config->processingMode(), + config->untypedForwardingMetadataNamespaces(), + config->typedForwardingMetadataNamespaces(), + config->untypedReceivingMetadataNamespaces()) {} const FilterConfig& config() const { return *config_; } @@ -305,6 +360,9 @@ class Filter : public Logger::Loggable, encoding_state_.callbackState() == ProcessorState::CallbackState::HeadersCallback); } + const ProcessorState& encodingState() { return encoding_state_; } + const ProcessorState& decodingState() { return decoding_state_; } + private: void mergePerRouteConfig(); StreamOpenState openStream(); @@ -315,11 +373,19 @@ class Filter : public Logger::Loggable, void sendImmediateResponse(const envoy::service::ext_proc::v3::ImmediateResponse& response); Http::FilterHeadersStatus onHeaders(ProcessorState& state, - Http::RequestOrResponseHeaderMap& headers, bool end_stream); + Http::RequestOrResponseHeaderMap& headers, bool end_stream, + ProtobufWkt::Struct* proto); + // Return a pair of whether to terminate returning the current result. std::pair sendStreamChunk(ProcessorState& state); Http::FilterDataStatus onData(ProcessorState& state, Buffer::Instance& data, bool end_stream); Http::FilterTrailersStatus onTrailers(ProcessorState& state, Http::HeaderMap& trailers); + void setDynamicMetadata(Http::StreamFilterCallbacks* cb, const ProcessorState& state, + const envoy::service::ext_proc::v3::ProcessingResponse& response); + void setEncoderDynamicMetadata(const envoy::service::ext_proc::v3::ProcessingResponse& response); + void setDecoderDynamicMetadata(const envoy::service::ext_proc::v3::ProcessingResponse& response); + void addDynamicMetadata(const ProcessorState& state, + envoy::service::ext_proc::v3::ProcessingRequest& req); const FilterConfigSharedPtr config_; const ExternalProcessorClientPtr client_; @@ -347,6 +413,10 @@ class Filter : public Logger::Loggable, // Set to true when the mergePerRouteConfig() method has been called. bool route_config_merged_ = false; + + std::vector untyped_forwarding_namespaces_{}; + std::vector typed_forwarding_namespaces_{}; + std::vector untyped_receiving_namespaces_{}; }; extern std::string responseCaseToString( diff --git a/source/extensions/filters/http/ext_proc/matching_utils.cc b/source/extensions/filters/http/ext_proc/matching_utils.cc new file mode 100644 index 0000000000000..e778be5ab9452 --- /dev/null +++ b/source/extensions/filters/http/ext_proc/matching_utils.cc @@ -0,0 +1,102 @@ +#include "source/extensions/filters/http/ext_proc/matching_utils.h" + +#include + +#if defined(USE_CEL_PARSER) +#include "parser/parser.h" +#endif + +namespace Envoy { +namespace Extensions { +namespace HttpFilters { +namespace ExternalProcessing { + +absl::flat_hash_map +ExpressionManager::initExpressions(const Protobuf::RepeatedPtrField& matchers) { + absl::flat_hash_map expressions; +#if defined(USE_CEL_PARSER) + for (const auto& matcher : matchers) { + if (expressions.contains(matcher)) { + continue; + } + auto parse_status = google::api::expr::parser::Parse(matcher); + if (!parse_status.ok()) { + throw EnvoyException("Unable to parse descriptor expression: " + + parse_status.status().ToString()); + } + + Filters::Common::Expr::ExpressionPtr expression = + Extensions::Filters::Common::Expr::createExpression(builder_->builder(), + parse_status.value().expr()); + + expressions.emplace( + matcher, ExpressionManager::CelExpression{parse_status.value(), std::move(expression)}); + } +#else + ENVOY_LOG(warn, "CEL expression parsing is not available for use in this environment." + " Attempted to parse " + + std::to_string(matchers.size()) + " expressions"); +#endif + return expressions; +} + +ProtobufWkt::Struct +ExpressionManager::evaluateAttributes(const Filters::Common::Expr::Activation& activation, + const absl::flat_hash_map& expr) { + + ProtobufWkt::Struct proto; + + if (expr.empty()) { + return proto; + } + + for (const auto& hash_entry : expr) { + ProtobufWkt::Arena arena; + const auto result = hash_entry.second.compiled_expr_->Evaluate(activation, &arena); + if (!result.ok()) { + // TODO: Stats? + continue; + } + + if (result.value().IsError()) { + ENVOY_LOG(trace, "error parsing cel expression {}", hash_entry.first); + continue; + } + + ProtobufWkt::Value value; + switch (result.value().type()) { + case google::api::expr::runtime::CelValue::Type::kBool: + value.set_bool_value(result.value().BoolOrDie()); + break; + case google::api::expr::runtime::CelValue::Type::kNullType: + value.set_null_value(ProtobufWkt::NullValue{}); + break; + case google::api::expr::runtime::CelValue::Type::kDouble: + value.set_number_value(result.value().DoubleOrDie()); + break; + default: + value.set_string_value(Filters::Common::Expr::print(result.value())); + } + + auto proto_mut_fields = proto.mutable_fields(); + (*proto_mut_fields)[hash_entry.first] = value; + } + + return proto; +} + +std::vector +initHeaderMatchers(const envoy::type::matcher::v3::ListStringMatcher& header_list) { + std::vector header_matchers; + for (const auto& matcher : header_list.patterns()) { + header_matchers.push_back( + std::make_unique>( + matcher)); + } + return header_matchers; +} + +} // namespace ExternalProcessing +} // namespace HttpFilters +} // namespace Extensions +} // namespace Envoy diff --git a/source/extensions/filters/http/ext_proc/matching_utils.h b/source/extensions/filters/http/ext_proc/matching_utils.h new file mode 100644 index 0000000000000..f02c51ac27283 --- /dev/null +++ b/source/extensions/filters/http/ext_proc/matching_utils.h @@ -0,0 +1,65 @@ +#pragma once + +#include "source/common/common/logger.h" +#include "source/common/common/matchers.h" +#include "source/common/protobuf/protobuf.h" +#include "source/extensions/filters/common/expr/evaluator.h" + +namespace Envoy { +namespace Extensions { +namespace HttpFilters { +namespace ExternalProcessing { + +class ExpressionManager : public Logger::Loggable { +public: + struct CelExpression { + google::api::expr::v1alpha1::ParsedExpr parsed_expr_; + Filters::Common::Expr::ExpressionPtr compiled_expr_; + }; + + ExpressionManager(Extensions::Filters::Common::Expr::BuilderInstanceSharedPtr builder, + const LocalInfo::LocalInfo& local_info, + const Protobuf::RepeatedPtrField& request_matchers, + const Protobuf::RepeatedPtrField& response_matchers) + : builder_(builder), local_info_(local_info), + request_expr_(initExpressions(request_matchers)), + response_expr_(initExpressions(response_matchers)){}; + + bool hasRequestExpr() const { return !request_expr_.empty(); }; + + bool hasResponseExpr() const { return !response_expr_.empty(); }; + + ProtobufWkt::Struct + evaluateRequestAttributes(const Filters::Common::Expr::Activation& activation) const { + return evaluateAttributes(activation, request_expr_); + } + + ProtobufWkt::Struct + evaluateResponseAttributes(const Filters::Common::Expr::Activation& activation) const { + return evaluateAttributes(activation, response_expr_); + } + + static ProtobufWkt::Struct + evaluateAttributes(const Filters::Common::Expr::Activation& activation, + const absl::flat_hash_map& expr); + + const LocalInfo::LocalInfo& localInfo() const { return local_info_; }; + +private: + absl::flat_hash_map + initExpressions(const Protobuf::RepeatedPtrField& matchers); + + Extensions::Filters::Common::Expr::BuilderInstanceSharedPtr builder_; + const LocalInfo::LocalInfo& local_info_; + + const absl::flat_hash_map request_expr_; + const absl::flat_hash_map response_expr_; +}; + +std::vector +initHeaderMatchers(const envoy::type::matcher::v3::ListStringMatcher& header_list); + +} // namespace ExternalProcessing +} // namespace HttpFilters +} // namespace Extensions +} // namespace Envoy diff --git a/source/extensions/filters/http/ext_proc/processor_state.cc b/source/extensions/filters/http/ext_proc/processor_state.cc index 124d59a6f107c..a6c843c9e9e25 100644 --- a/source/extensions/filters/http/ext_proc/processor_state.cc +++ b/source/extensions/filters/http/ext_proc/processor_state.cc @@ -1,4 +1,3 @@ -#include "processor_state.h" #include "source/extensions/filters/http/ext_proc/processor_state.h" #include "source/common/buffer/buffer_impl.h" @@ -266,7 +265,7 @@ absl::Status ProcessorState::handleBodyResponse(const BodyResponse& response) { } else if (callback_state_ == CallbackState::StreamedBodyCallback) { Buffer::OwnedImpl chunk_data; auto chunk = dequeueStreamingChunk(chunk_data); - ENVOY_BUG(chunk, "Bad streamed body callback state"); + ENVOY_BUG(chunk != nullptr, "Bad streamed body callback state"); if (common_response.has_body_mutation()) { ENVOY_LOG(debug, "Applying body response to chunk of data. Size = {}", chunk->length); MutationUtils::applyBodyMutations(common_response.body_mutation(), chunk_data); @@ -289,7 +288,7 @@ absl::Status ProcessorState::handleBodyResponse(const BodyResponse& response) { // Apply changes to the buffer that we sent to the server Buffer::OwnedImpl chunk_data; auto chunk = dequeueStreamingChunk(chunk_data); - ENVOY_BUG(chunk, "Bad partial body callback state"); + ENVOY_BUG(chunk != nullptr, "Bad partial body callback state"); if (common_response.has_header_mutation()) { if (headers_ != nullptr) { ENVOY_LOG(debug, "Applying header mutations to buffered body message"); diff --git a/source/extensions/filters/http/ext_proc/processor_state.h b/source/extensions/filters/http/ext_proc/processor_state.h index de4628864941d..a3ebe27617f0b 100644 --- a/source/extensions/filters/http/ext_proc/processor_state.h +++ b/source/extensions/filters/http/ext_proc/processor_state.h @@ -73,10 +73,16 @@ class ProcessorState : public Logger::Loggable { }; explicit ProcessorState(Filter& filter, - envoy::config::core::v3::TrafficDirection traffic_direction) + envoy::config::core::v3::TrafficDirection traffic_direction, + const std::vector& untyped_forwarding_namespaces, + const std::vector& typed_forwarding_namespaces, + const std::vector& untyped_receiving_namespaces) : filter_(filter), watermark_requested_(false), paused_(false), no_body_(false), complete_body_available_(false), trailers_available_(false), body_replaced_(false), - partial_body_processed_(false), traffic_direction_(traffic_direction) {} + partial_body_processed_(false), traffic_direction_(traffic_direction), + untyped_forwarding_namespaces_(&untyped_forwarding_namespaces), + typed_forwarding_namespaces_(&typed_forwarding_namespaces), + untyped_receiving_namespaces_(&untyped_receiving_namespaces) {} ProcessorState(const ProcessorState&) = delete; virtual ~ProcessorState() = default; ProcessorState& operator=(const ProcessorState&) = delete; @@ -100,6 +106,28 @@ class ProcessorState : public Logger::Loggable { virtual void setProcessingMode( const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode) PURE; + + const std::vector& untypedForwardingMetadataNamespaces() const { + return *untyped_forwarding_namespaces_; + }; + void setUntypedForwardingMetadataNamespaces(const std::vector& ns) { + untyped_forwarding_namespaces_ = &ns; + }; + + const std::vector& typedForwardingMetadataNamespaces() const { + return *typed_forwarding_namespaces_; + }; + void setTypedForwardingMetadataNamespaces(const std::vector& ns) { + typed_forwarding_namespaces_ = &ns; + }; + + const std::vector& untypedReceivingMetadataNamespaces() const { + return *untyped_receiving_namespaces_; + }; + void setUntypedReceivingMetadataNamespaces(const std::vector& ns) { + untyped_receiving_namespaces_ = &ns; + }; + bool sendHeaders() const { return send_headers_; } bool sendTrailers() const { return send_trailers_; } envoy::extensions::filters::http::ext_proc::v3::ProcessingMode_BodySendMode bodyMode() const { @@ -172,6 +200,8 @@ class ProcessorState : public Logger::Loggable { virtual envoy::service::ext_proc::v3::HttpTrailers* mutableTrailers(envoy::service::ext_proc::v3::ProcessingRequest& request) const PURE; + virtual Http::StreamFilterCallbacks* callbacks() const PURE; + protected: void setBodyMode( envoy::extensions::filters::http::ext_proc::v3::ProcessingMode_BodySendMode body_mode); @@ -216,6 +246,10 @@ class ProcessorState : public Logger::Loggable { absl::optional call_start_time_ = absl::nullopt; const envoy::config::core::v3::TrafficDirection traffic_direction_; + const std::vector* untyped_forwarding_namespaces_{}; + const std::vector* typed_forwarding_namespaces_{}; + const std::vector* untyped_receiving_namespaces_{}; + private: virtual void clearRouteCache(const envoy::service::ext_proc::v3::CommonResponse&) {} }; @@ -223,8 +257,13 @@ class ProcessorState : public Logger::Loggable { class DecodingProcessorState : public ProcessorState { public: explicit DecodingProcessorState( - Filter& filter, const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode) - : ProcessorState(filter, envoy::config::core::v3::TrafficDirection::INBOUND) { + Filter& filter, const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode, + const std::vector& untyped_forwarding_namespaces, + const std::vector& typed_forwarding_namespaces, + const std::vector& untyped_receiving_namespaces) + : ProcessorState(filter, envoy::config::core::v3::TrafficDirection::INBOUND, + untyped_forwarding_namespaces, typed_forwarding_namespaces, + untyped_receiving_namespaces) { setProcessingModeInternal(mode); } DecodingProcessorState(const DecodingProcessorState&) = delete; @@ -283,6 +322,8 @@ class DecodingProcessorState : public ProcessorState { void requestWatermark() override; void clearWatermark() override; + Http::StreamFilterCallbacks* callbacks() const override { return decoder_callbacks_; } + private: void setProcessingModeInternal( const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode); @@ -296,8 +337,13 @@ class DecodingProcessorState : public ProcessorState { class EncodingProcessorState : public ProcessorState { public: explicit EncodingProcessorState( - Filter& filter, const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode) - : ProcessorState(filter, envoy::config::core::v3::TrafficDirection::OUTBOUND) { + Filter& filter, const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode, + const std::vector& untyped_forwarding_namespaces, + const std::vector& typed_forwarding_namespaces, + const std::vector& untyped_receiving_namespaces) + : ProcessorState(filter, envoy::config::core::v3::TrafficDirection::OUTBOUND, + untyped_forwarding_namespaces, typed_forwarding_namespaces, + untyped_receiving_namespaces) { setProcessingModeInternal(mode); } EncodingProcessorState(const EncodingProcessorState&) = delete; @@ -356,6 +402,8 @@ class EncodingProcessorState : public ProcessorState { void requestWatermark() override; void clearWatermark() override; + Http::StreamFilterCallbacks* callbacks() const override { return encoder_callbacks_; } + private: void setProcessingModeInternal( const envoy::extensions::filters::http::ext_proc::v3::ProcessingMode& mode); diff --git a/source/extensions/filters/http/fault/fault_filter.cc b/source/extensions/filters/http/fault/fault_filter.cc index 1ddbf8affced1..1edb0d62a04b0 100644 --- a/source/extensions/filters/http/fault/fault_filter.cc +++ b/source/extensions/filters/http/fault/fault_filter.cc @@ -169,7 +169,7 @@ bool FaultFilter::maybeSetupDelay(const Http::RequestHeaderMap& request_headers) ENVOY_LOG(debug, "fault: delaying request {}ms", duration.value().count()); delay_timer_->enableTimer(duration.value(), &decoder_callbacks_->scope()); recordDelaysInjectedStats(); - decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::DelayInjected); + decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected); auto& dynamic_metadata = decoder_callbacks_->streamInfo().dynamicMetadata(); (*dynamic_metadata.mutable_filter_metadata())[decoder_callbacks_->filterConfigName()] = fault_settings_->filterMetadata(); @@ -470,7 +470,7 @@ void FaultFilter::postDelayInjection(const Http::RequestHeaderMap& request_heade void FaultFilter::abortWithStatus(Http::Code http_status_code, absl::optional grpc_status) { recordAbortsInjectedStats(); - decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::FaultInjected); + decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected); auto& dynamic_metadata = decoder_callbacks_->streamInfo().dynamicMetadata(); (*dynamic_metadata.mutable_filter_metadata())[decoder_callbacks_->filterConfigName()] = fault_settings_->filterMetadata(); diff --git a/source/extensions/filters/http/grpc_http1_reverse_bridge/filter.cc b/source/extensions/filters/http/grpc_http1_reverse_bridge/filter.cc index f59cdd4575083..d8a4f6758839d 100644 --- a/source/extensions/filters/http/grpc_http1_reverse_bridge/filter.cc +++ b/source/extensions/filters/http/grpc_http1_reverse_bridge/filter.cc @@ -181,6 +181,12 @@ Http::FilterHeadersStatus Filter::encodeHeaders(Http::ResponseHeaderMap& headers // until then. grpc_status_ = grpcStatusFromHeaders(headers); + // gRPC clients expect that the HTTP status will always be 200. + if (Runtime::runtimeFeatureEnabled( + "envoy.reloadable_features.grpc_http1_reverse_bridge_change_http_status")) { + headers.setStatus(enumToInt(Http::Code::OK)); + } + if (Runtime::runtimeFeatureEnabled( "envoy.reloadable_features.grpc_http1_reverse_bridge_handle_empty_response")) { // This is a header-only response, and we should prepend the gRPC frame diff --git a/source/extensions/filters/http/health_check/health_check.cc b/source/extensions/filters/http/health_check/health_check.cc index 8a6bb39fdd43a..ded52a64eca13 100644 --- a/source/extensions/filters/http/health_check/health_check.cc +++ b/source/extensions/filters/http/health_check/health_check.cc @@ -120,7 +120,7 @@ void HealthCheckFilter::onComplete() { const std::string* details = &RcDetails::get().HealthCheckOk; bool degraded = false; if (context_.healthCheckFailed()) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::FailedLocalHealthCheck); final_status = Http::Code::ServiceUnavailable; details = &RcDetails::get().HealthCheckFailed; } else { @@ -171,7 +171,8 @@ void HealthCheckFilter::onComplete() { } if (!Http::CodeUtility::is2xx(enumToInt(final_status))) { - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck); + callbacks_->streamInfo().setResponseFlag( + StreamInfo::CoreResponseFlag::FailedLocalHealthCheck); } } diff --git a/source/extensions/filters/http/local_ratelimit/local_ratelimit.cc b/source/extensions/filters/http/local_ratelimit/local_ratelimit.cc index ac0ba0bed89d0..6938c8b1d6eae 100644 --- a/source/extensions/filters/http/local_ratelimit/local_ratelimit.cc +++ b/source/extensions/filters/http/local_ratelimit/local_ratelimit.cc @@ -152,7 +152,7 @@ Http::FilterHeadersStatus Filter::decodeHeaders(Http::RequestHeaderMap& headers, config->responseHeadersParser().evaluateHeaders(headers, decoder_callbacks_->streamInfo()); }, config->rateLimitedGrpcStatus(), "local_rate_limited"); - decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::RateLimited); + decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited); return Http::FilterHeadersStatus::StopIteration; } diff --git a/source/extensions/filters/http/rate_limit_quota/filter.cc b/source/extensions/filters/http/rate_limit_quota/filter.cc index 1de563104e026..58baf4bc8f1f4 100644 --- a/source/extensions/filters/http/rate_limit_quota/filter.cc +++ b/source/extensions/filters/http/rate_limit_quota/filter.cc @@ -194,7 +194,7 @@ Http::FilterHeadersStatus RateLimitQuotaFilter::processCachedBucket(size_t bucke // configured. callbacks_->sendLocalReply(Envoy::Http::Code::TooManyRequests, "", nullptr, absl::nullopt, ""); - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::RateLimited); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited); return Envoy::Http::FilterHeadersStatus::StopIteration; } } diff --git a/source/extensions/filters/http/ratelimit/ratelimit.cc b/source/extensions/filters/http/ratelimit/ratelimit.cc index a8576331a16f3..5a462979bea7a 100644 --- a/source/extensions/filters/http/ratelimit/ratelimit.cc +++ b/source/extensions/filters/http/ratelimit/ratelimit.cc @@ -199,7 +199,7 @@ void Filter::complete(Filters::Common::RateLimit::LimitStatus status, if (status == Filters::Common::RateLimit::LimitStatus::OverLimit && config_->runtime().snapshot().featureEnabled("ratelimit.http_filter_enforcing", 100)) { state_ = State::Responded; - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::RateLimited); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited); callbacks_->sendLocalReply( config_->rateLimitedStatus(), response_body, [this](Http::HeaderMap& headers) { @@ -218,7 +218,7 @@ void Filter::complete(Filters::Common::RateLimit::LimitStatus status, } } else { state_ = State::Responded; - callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::RateLimitServiceError); + callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::RateLimitServiceError); callbacks_->sendLocalReply(config_->statusOnError(), response_body, nullptr, absl::nullopt, RcDetails::get().RateLimitError); } diff --git a/source/extensions/filters/listener/proxy_protocol/proxy_protocol.h b/source/extensions/filters/listener/proxy_protocol/proxy_protocol.h index e7f6974626f1e..228dc6f366fba 100644 --- a/source/extensions/filters/listener/proxy_protocol/proxy_protocol.h +++ b/source/extensions/filters/listener/proxy_protocol/proxy_protocol.h @@ -8,9 +8,9 @@ #include "source/common/common/logger.h" #include "source/extensions/common/proxy_protocol/proxy_protocol_header.h" +#include "source/extensions/filters/listener//proxy_protocol/proxy_protocol_header.h" #include "absl/container/flat_hash_map.h" -#include "proxy_protocol_header.h" using Envoy::Extensions::Common::ProxyProtocol::PROXY_PROTO_V2_ADDR_LEN_UNIX; using Envoy::Extensions::Common::ProxyProtocol::PROXY_PROTO_V2_HEADER_LEN; diff --git a/source/extensions/filters/network/common/factory_base.h b/source/extensions/filters/network/common/factory_base.h index fd77a6819dba9..2e5e5f6fecf59 100644 --- a/source/extensions/filters/network/common/factory_base.h +++ b/source/extensions/filters/network/common/factory_base.h @@ -34,7 +34,7 @@ class FactoryBase : public Server::Configuration::NamedNetworkFilterConfigFactor return std::make_unique(); } - Upstream::ProtocolOptionsConfigConstSharedPtr createProtocolOptionsConfig( + absl::StatusOr createProtocolOptionsConfig( const Protobuf::Message& proto_config, Server::Configuration::ProtocolOptionsFactoryContext& factory_context) override { return createProtocolOptionsTyped(MessageUtil::downcastAndValidate( diff --git a/source/extensions/filters/network/ext_authz/ext_authz.cc b/source/extensions/filters/network/ext_authz/ext_authz.cc index 7e1c6a33f0579..dc27b9d2e2662 100644 --- a/source/extensions/filters/network/ext_authz/ext_authz.cc +++ b/source/extensions/filters/network/ext_authz/ext_authz.cc @@ -108,7 +108,7 @@ void Filter::onComplete(Filters::Common::ExtAuthz::ResponsePtr&& response) { config_->stats().cx_closed_.inc(); filter_callbacks_->connection().close(Network::ConnectionCloseType::NoFlush, "ext_authz_close"); filter_callbacks_->connection().streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UnauthorizedExternalService); + StreamInfo::CoreResponseFlag::UnauthorizedExternalService); filter_callbacks_->connection().streamInfo().setResponseCodeDetails( response->status == Filters::Common::ExtAuthz::CheckStatus::Denied ? Filters::Common::ExtAuthz::ResponseCodeDetails::get().AuthzDenied diff --git a/source/extensions/filters/network/http_connection_manager/config.cc b/source/extensions/filters/network/http_connection_manager/config.cc index 2dca9a73952cb..9d94281cbc332 100644 --- a/source/extensions/filters/network/http_connection_manager/config.cc +++ b/source/extensions/filters/network/http_connection_manager/config.cc @@ -339,9 +339,6 @@ HttpConnectionManagerConfig::HttpConnectionManagerConfig( http3_options_(Http3::Utility::initializeAndValidateOptions( config.http3_protocol_options(), config.has_stream_error_on_invalid_http_message(), config.stream_error_on_invalid_http_message())), - http2_options_(Http2::Utility::initializeAndValidateOptions( - config.http2_protocol_options(), config.has_stream_error_on_invalid_http_message(), - config.stream_error_on_invalid_http_message())), http1_settings_(Http::Http1::parseHttp1Settings( config.http_protocol_options(), context.messageValidationVisitor(), config.stream_error_on_invalid_http_message(), @@ -404,6 +401,12 @@ HttpConnectionManagerConfig::HttpConnectionManagerConfig( append_x_forwarded_port_(config.append_x_forwarded_port()), add_proxy_protocol_connection_state_( PROTOBUF_GET_WRAPPED_OR_DEFAULT(config, add_proxy_protocol_connection_state, true)) { + + auto options_or_error = Http2::Utility::initializeAndValidateOptions( + config.http2_protocol_options(), config.has_stream_error_on_invalid_http_message(), + config.stream_error_on_invalid_http_message()); + THROW_IF_STATUS_NOT_OK(options_or_error, throw); + http2_options_ = options_or_error.value(); if (!idle_timeout_) { idle_timeout_ = std::chrono::hours(1); } else if (idle_timeout_.value().count() == 0) { diff --git a/source/extensions/filters/network/local_ratelimit/local_ratelimit.cc b/source/extensions/filters/network/local_ratelimit/local_ratelimit.cc index f48a8003985f1..8c6af4c820c14 100644 --- a/source/extensions/filters/network/local_ratelimit/local_ratelimit.cc +++ b/source/extensions/filters/network/local_ratelimit/local_ratelimit.cc @@ -107,7 +107,7 @@ Network::FilterStatus Filter::onNewConnection() { ENVOY_CONN_LOG(trace, "local_rate_limit: rate limiting connection", read_callbacks_->connection()); read_callbacks_->connection().streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded); + StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded); read_callbacks_->connection().close(Network::ConnectionCloseType::NoFlush, "local_ratelimit_close_over_limit"); return Network::FilterStatus::StopIteration; diff --git a/source/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit.cc b/source/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit.cc index 53e966a3f8d34..57781dd7efa36 100644 --- a/source/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit.cc +++ b/source/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit.cc @@ -90,7 +90,7 @@ void Filter::complete(Filters::Common::RateLimit::LimitStatus status, ThriftProxy::AppException(ThriftProxy::AppExceptionType::InternalError, "limiter error"), false); decoder_callbacks_->streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::RateLimitServiceError); + StreamInfo::CoreResponseFlag::RateLimitServiceError); return; } cluster_->statsScope().counterFromStatName(stat_names.failure_mode_allowed_).inc(); @@ -102,7 +102,7 @@ void Filter::complete(Filters::Common::RateLimit::LimitStatus status, decoder_callbacks_->sendLocalReply( ThriftProxy::AppException(ThriftProxy::AppExceptionType::InternalError, "over limit"), false); - decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::RateLimited); + decoder_callbacks_->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited); return; } break; diff --git a/source/extensions/filters/network/thrift_proxy/router/router.h b/source/extensions/filters/network/thrift_proxy/router/router.h index 760c1412b6bc7..0ffff508c81fa 100644 --- a/source/extensions/filters/network/thrift_proxy/router/router.h +++ b/source/extensions/filters/network/thrift_proxy/router/router.h @@ -140,6 +140,14 @@ class RouterStats { upstream_resp_reply_error_(stat_name_set_->add("thrift.upstream_resp_error")), upstream_resp_exception_(stat_name_set_->add("thrift.upstream_resp_exception")), upstream_resp_exception_local_(stat_name_set_->add("thrift.upstream_resp_exception_local")), + upstream_resp_exception_local_overflow_( + stat_name_set_->add("thrift.upstream_resp_exception_local.overflow")), + upstream_resp_exception_local_local_connection_failure_( + stat_name_set_->add("thrift.upstream_resp_exception_local.local_connection_failure")), + upstream_resp_exception_local_remote_connection_failure_( + stat_name_set_->add("thrift.upstream_resp_exception_local.remote_connection_failure")), + upstream_resp_exception_local_timeout_( + stat_name_set_->add("thrift.upstream_resp_exception_local.timeout")), upstream_resp_exception_remote_( stat_name_set_->add("thrift.upstream_resp_exception_remote")), upstream_resp_invalid_type_(stat_name_set_->add("thrift.upstream_resp_invalid_type")), @@ -249,9 +257,30 @@ class RouterStats { * upstream. * @param cluster Upstream::ClusterInfo& describing the upstream cluster */ - void incResponseLocalException(const Upstream::ClusterInfo& cluster) const { + void incResponseLocalException( + const Upstream::ClusterInfo& cluster, + absl::optional reason = absl::nullopt) const { incClusterScopeCounter(cluster, nullptr, upstream_resp_exception_); incClusterScopeCounter(cluster, nullptr, upstream_resp_exception_local_); + + if (reason.has_value()) { + switch (reason.value()) { + case ConnectionPool::PoolFailureReason::Overflow: + incClusterScopeCounter(cluster, nullptr, upstream_resp_exception_local_overflow_); + break; + case ConnectionPool::PoolFailureReason::LocalConnectionFailure: + incClusterScopeCounter(cluster, nullptr, + upstream_resp_exception_local_local_connection_failure_); + break; + case ConnectionPool::PoolFailureReason::RemoteConnectionFailure: + incClusterScopeCounter(cluster, nullptr, + upstream_resp_exception_local_remote_connection_failure_); + break; + case ConnectionPool::PoolFailureReason::Timeout: + incClusterScopeCounter(cluster, nullptr, upstream_resp_exception_local_timeout_); + break; + } + } } /** @@ -366,6 +395,10 @@ class RouterStats { const Stats::StatName upstream_resp_reply_error_; const Stats::StatName upstream_resp_exception_; const Stats::StatName upstream_resp_exception_local_; + const Stats::StatName upstream_resp_exception_local_overflow_; + const Stats::StatName upstream_resp_exception_local_local_connection_failure_; + const Stats::StatName upstream_resp_exception_local_remote_connection_failure_; + const Stats::StatName upstream_resp_exception_local_timeout_; const Stats::StatName upstream_resp_exception_remote_; const Stats::StatName upstream_resp_invalid_type_; const Stats::StatName upstream_resp_decoding_error_; diff --git a/source/extensions/filters/network/thrift_proxy/router/upstream_request.cc b/source/extensions/filters/network/thrift_proxy/router/upstream_request.cc index 99c1d8c4cbe29..436c9d2463952 100644 --- a/source/extensions/filters/network/thrift_proxy/router/upstream_request.cc +++ b/source/extensions/filters/network/thrift_proxy/router/upstream_request.cc @@ -302,10 +302,9 @@ bool UpstreamRequest::onResetStream(ConnectionPool::PoolFailureReason reason) { bool close_downstream = true; chargeResponseTiming(); - switch (reason) { case ConnectionPool::PoolFailureReason::Overflow: - stats_.incResponseLocalException(parent_.cluster()); + stats_.incResponseLocalException(parent_.cluster(), reason); parent_.sendLocalReply(AppException(AppExceptionType::InternalError, "thrift upstream request: too many connections"), false /* Don't close the downstream connection. */); @@ -328,7 +327,7 @@ bool UpstreamRequest::onResetStream(ConnectionPool::PoolFailureReason reason) { if (response_state_ == ResponseState::Started) { stats_.incClosePartialResponse(parent_.cluster()); } - stats_.incResponseLocalException(parent_.cluster()); + stats_.incResponseLocalException(parent_.cluster(), reason); parent_.sendLocalReply( AppException(AppExceptionType::InternalError, fmt::format("connection failure before response {}: {} '{}'", diff --git a/source/extensions/filters/udp/udp_proxy/config.h b/source/extensions/filters/udp/udp_proxy/config.h index 71dfa47287952..6778ea3b0992b 100644 --- a/source/extensions/filters/udp/udp_proxy/config.h +++ b/source/extensions/filters/udp/udp_proxy/config.h @@ -81,10 +81,9 @@ class TunnelingConfigImpl : public UdpTunnelingConfig { return; } - filter_state->setData(TunnelResponseHeaders::key(), - std::make_shared(std::move(headers)), - StreamInfo::FilterState::StateType::ReadOnly, - StreamInfo::FilterState::LifeSpan::Connection); + filter_state->setData( + TunnelResponseHeaders::key(), std::make_shared(std::move(headers)), + StreamInfo::FilterState::StateType::Mutable, StreamInfo::FilterState::LifeSpan::Connection); } void diff --git a/source/extensions/filters/udp/udp_proxy/udp_proxy_filter.cc b/source/extensions/filters/udp/udp_proxy/udp_proxy_filter.cc index b257f9c96e901..65402058363f5 100644 --- a/source/extensions/filters/udp/udp_proxy/udp_proxy_filter.cc +++ b/source/extensions/filters/udp/udp_proxy/udp_proxy_filter.cc @@ -912,13 +912,13 @@ bool UdpProxyFilter::TunnelingActiveSession::createConnectionPool() { ->resourceManager(Upstream::ResourcePriority::Default) .connections() .canCreate()) { - udp_session_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + udp_session_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); cluster_.cluster_.info()->trafficStats()->upstream_cx_overflow_.inc(); return false; } if (connect_attempts_ >= cluster_.filter_.config_->tunnelingConfig()->maxConnectAttempts()) { - udp_session_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded); + udp_session_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded); cluster_.cluster_.info()->trafficStats()->upstream_cx_connect_attempts_exceeded_.inc(); return false; } else if (connect_attempts_ >= 1) { @@ -938,7 +938,7 @@ bool UdpProxyFilter::TunnelingActiveSession::createConnectionPool() { return true; } - udp_session_info_.setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream); + udp_session_info_.setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream); return false; } @@ -956,12 +956,12 @@ void UdpProxyFilter::TunnelingActiveSession::onStreamFailure( onUpstreamEvent(Network::ConnectionEvent::LocalClose); break; case ConnectionPool::PoolFailureReason::Timeout: - udp_session_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + udp_session_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); onUpstreamEvent(Network::ConnectionEvent::RemoteClose); break; case ConnectionPool::PoolFailureReason::RemoteConnectionFailure: if (connecting_) { - udp_session_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + udp_session_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); } onUpstreamEvent(Network::ConnectionEvent::RemoteClose); break; @@ -1075,7 +1075,7 @@ void UdpProxyFilter::TunnelingActiveSession::onUpstreamData(Buffer::Instance& da void UdpProxyFilter::TunnelingActiveSession::onIdleTimer() { ENVOY_LOG(debug, "session idle timeout: downstream={} local={}", addresses_.peer_->asStringView(), addresses_.local_->asStringView()); - udp_session_info_.setResponseFlag(StreamInfo::ResponseFlag::StreamIdleTimeout); + udp_session_info_.setResponseFlag(StreamInfo::CoreResponseFlag::StreamIdleTimeout); cluster_.filter_.config_->stats().idle_timeout_.inc(); upstream_->onDownstreamEvent(Network::ConnectionEvent::LocalClose); cluster_.removeSession(this); diff --git a/source/extensions/geoip_providers/maxmind/BUILD b/source/extensions/geoip_providers/maxmind/BUILD index 5d9f368bf64fa..c73809203bb7f 100644 --- a/source/extensions/geoip_providers/maxmind/BUILD +++ b/source/extensions/geoip_providers/maxmind/BUILD @@ -16,6 +16,7 @@ envoy_cc_extension( name = "config", srcs = select({ "//bazel:linux": ["config.cc"], + "//bazel:darwin_any": ["config.cc"], "//conditions:default": [], }), hdrs = ["config.h"], @@ -34,6 +35,7 @@ envoy_cc_library( name = "provider_impl", srcs = select({ "//bazel:linux": ["geoip_provider.cc"], + "//bazel:darwin_any": ["geoip_provider.cc"], "//conditions:default": [], }), hdrs = ["geoip_provider.h"], diff --git a/source/extensions/geoip_providers/maxmind/config.cc b/source/extensions/geoip_providers/maxmind/config.cc index efe52b5ab1e9b..d75a56b3e6591 100644 --- a/source/extensions/geoip_providers/maxmind/config.cc +++ b/source/extensions/geoip_providers/maxmind/config.cc @@ -5,8 +5,7 @@ #include "source/common/common/utility.h" #include "source/common/protobuf/utility.h" - -#include "geoip_provider.h" +#include "source/extensions/geoip_providers/maxmind/geoip_provider.h" namespace Envoy { namespace Extensions { diff --git a/source/extensions/http/cache/file_system_http_cache/lookup_context.cc b/source/extensions/http/cache/file_system_http_cache/lookup_context.cc index 33eb22b8c9606..d0b006365c54d 100644 --- a/source/extensions/http/cache/file_system_http_cache/lookup_context.cc +++ b/source/extensions/http/cache/file_system_http_cache/lookup_context.cc @@ -1,11 +1,10 @@ #include "source/extensions/http/cache/file_system_http_cache/lookup_context.h" +#include "source/extensions/http/cache/file_system_http_cache/cache_file_fixed_block.h" #include "source/extensions/http/cache/file_system_http_cache/cache_file_header.pb.h" #include "source/extensions/http/cache/file_system_http_cache/cache_file_header_proto_util.h" #include "source/extensions/http/cache/file_system_http_cache/file_system_http_cache.h" -#include "cache_file_fixed_block.h" - namespace Envoy { namespace Extensions { namespace HttpFilters { diff --git a/source/extensions/load_balancing_policies/subset/subset_lb.cc b/source/extensions/load_balancing_policies/subset/subset_lb.cc index e8ae1707703a4..9ba717d83e96b 100644 --- a/source/extensions/load_balancing_policies/subset/subset_lb.cc +++ b/source/extensions/load_balancing_policies/subset/subset_lb.cc @@ -531,23 +531,25 @@ SubsetLoadBalancer::LbSubsetEntryPtr SubsetLoadBalancer::findSubset( } void SubsetLoadBalancer::updateFallbackSubset(uint32_t priority, const HostVector& all_hosts) { - auto update_func = [priority, &all_hosts](LbSubsetPtr& subset, const HostPredicate& predicate) { + auto update_func = [priority, &all_hosts](LbSubsetPtr& subset, const HostPredicate& predicate, + uint64_t seed) { for (const auto& host : all_hosts) { if (predicate(*host)) { subset->pushHost(priority, host); } } - subset->finalize(priority); + subset->finalize(priority, seed); }; if (subset_any_ != nullptr) { - update_func(subset_any_->lb_subset_, [](const Host&) { return true; }); + update_func( + subset_any_->lb_subset_, [](const Host&) { return true; }, random_.random()); } if (subset_default_ != nullptr) { HostPredicate predicate = std::bind(&SubsetLoadBalancer::hostMatches, this, default_subset_metadata_, std::placeholders::_1); - update_func(subset_default_->lb_subset_, predicate); + update_func(subset_default_->lb_subset_, predicate, random_.random()); } if (fallback_subset_ == nullptr) { @@ -622,9 +624,9 @@ void SubsetLoadBalancer::processSubsets(uint32_t priority, const HostVector& all single_duplicate_stat_->set(collision_count_of_single_host_entries); // Finalize updates after all the hosts are evaluated. - forEachSubset(subsets_, [priority](LbSubsetEntryPtr entry) { + forEachSubset(subsets_, [priority, this](LbSubsetEntryPtr entry) { if (entry->initialized()) { - entry->lb_subset_->finalize(priority); + entry->lb_subset_->finalize(priority, random_.random()); } }); } @@ -844,7 +846,7 @@ SubsetLoadBalancer::PrioritySubsetImpl::PrioritySubsetImpl(const SubsetLoadBalan // hosts that belong in this subset. void SubsetLoadBalancer::HostSubsetImpl::update(const HostHashSet& matching_hosts, const HostVector& hosts_added, - const HostVector& hosts_removed) { + const HostVector& hosts_removed, uint64_t seed) { auto cached_predicate = [&matching_hosts](const auto& host) { return matching_hosts.count(&host) == 1; }; @@ -905,7 +907,7 @@ void SubsetLoadBalancer::HostSubsetImpl::update(const HostHashSet& matching_host HostSetImpl::updateHostsParams( hosts, hosts_per_locality, healthy_hosts, healthy_hosts_per_locality, degraded_hosts, degraded_hosts_per_locality, excluded_hosts, excluded_hosts_per_locality), - determineLocalityWeights(*hosts_per_locality), hosts_added, hosts_removed, + determineLocalityWeights(*hosts_per_locality), hosts_added, hosts_removed, seed, original_host_set_.weightedPriorityHealth(), original_host_set_.overprovisioningFactor()); } @@ -962,9 +964,10 @@ HostSetImplPtr SubsetLoadBalancer::PrioritySubsetImpl::createHostSet( void SubsetLoadBalancer::PrioritySubsetImpl::update(uint32_t priority, const HostHashSet& matching_hosts, const HostVector& hosts_added, - const HostVector& hosts_removed) { + const HostVector& hosts_removed, + uint64_t seed) { const auto& host_subset = getOrCreateHostSet(priority); - updateSubset(priority, matching_hosts, hosts_added, hosts_removed); + updateSubset(priority, matching_hosts, hosts_added, hosts_removed, seed); if (host_subset.hosts().empty() != empty_) { empty_ = true; diff --git a/source/extensions/load_balancing_policies/subset/subset_lb.h b/source/extensions/load_balancing_policies/subset/subset_lb.h index ddf228a2c0e74..52c460c9d1eba 100644 --- a/source/extensions/load_balancing_policies/subset/subset_lb.h +++ b/source/extensions/load_balancing_policies/subset/subset_lb.h @@ -181,7 +181,7 @@ class SubsetLoadBalancer : public LoadBalancer, Logger::Loggable(host_sets_[priority].get()) - ->update(matching_hosts, hosts_added, hosts_removed); + ->update(matching_hosts, hosts_added, hosts_removed, seed); runUpdateCallbacks(hosts_added, hosts_removed); } @@ -318,7 +319,7 @@ class SubsetLoadBalancer : public LoadBalancer, Logger::Loggable; @@ -341,7 +342,7 @@ class SubsetLoadBalancer : public LoadBalancer, Logger::Loggable size_t { - // TODO(Diazalan): Remove if statement once runtime guard is deprecated - if (!Runtime::runtimeFeatureEnabled( - "envoy.reloadable_features.count_unused_mapped_pages_as_free")) { - const size_t physical = stats_->reservedHeapBytes(); - const size_t unmapped = stats_->unmappedHeapBytes(); - ASSERT(physical >= unmapped); - return physical - unmapped; - } else { - const size_t physical = stats_->reservedHeapBytes(); - const size_t unmapped = stats_->unmappedHeapBytes(); - const size_t free_mapped = stats_->freeMappedHeapBytes(); - ASSERT(physical >= (unmapped + free_mapped)); - return physical - unmapped - free_mapped; - } + const size_t physical = stats_->reservedHeapBytes(); + const size_t unmapped = stats_->unmappedHeapBytes(); + const size_t free_mapped = stats_->freeMappedHeapBytes(); + ASSERT(physical >= (unmapped + free_mapped)); + return physical - unmapped - free_mapped; }; const size_t used = computeUsedMemory(); diff --git a/source/extensions/stat_sinks/common/statsd/statsd.cc b/source/extensions/stat_sinks/common/statsd/statsd.cc index fa66a6205cdf8..6236fd67a8664 100644 --- a/source/extensions/stat_sinks/common/statsd/statsd.cc +++ b/source/extensions/stat_sinks/common/statsd/statsd.cc @@ -194,8 +194,11 @@ TcpStatsdSink::TcpStatsdSink(const LocalInfo::LocalInfo& local_info, cluster_manager_(cluster_manager), cx_overflow_stat_(scope.counterFromStatName( Stats::StatNameManagedStorage("statsd.cx_overflow", scope.symbolTable()).statName())) { - const auto cluster = Config::Utility::checkClusterAndLocalInfo("tcp statsd", cluster_name, - cluster_manager, local_info); + THROW_IF_NOT_OK(Config::Utility::checkLocalInfo("tcp statsd", local_info)); + const auto cluster_or_error = + Config::Utility::checkCluster("tcp statsd", cluster_name, cluster_manager); + THROW_IF_STATUS_NOT_OK(cluster_or_error, throw); + const auto cluster = std::move(cluster_or_error.value()); cluster_info_ = cluster->get().info(); tls_->set([this](Event::Dispatcher& dispatcher) -> ThreadLocal::ThreadLocalObjectSharedPtr { return std::make_shared(*this, dispatcher); diff --git a/source/extensions/tracers/datadog/tracer.cc b/source/extensions/tracers/datadog/tracer.cc index 4fee08432e0cd..e01c309118999 100644 --- a/source/extensions/tracers/datadog/tracer.cc +++ b/source/extensions/tracers/datadog/tracer.cc @@ -63,8 +63,9 @@ Tracer::Tracer(const std::string& collector_cluster, const std::string& collecto thread_local_slot_( ThreadLocal::TypedSlot::makeUnique(thread_local_slot_allocator)) { const bool allow_added_via_api = true; - Config::Utility::checkCluster("envoy.tracers.datadog", collector_cluster, cluster_manager, - allow_added_via_api); + THROW_IF_STATUS_NOT_OK(Config::Utility::checkCluster("envoy.tracers.datadog", collector_cluster, + cluster_manager, allow_added_via_api), + throw); thread_local_slot_->set([&logger = ENVOY_LOGGER(), collector_cluster, collector_reference_host, config, &tracer_stats = tracer_stats_, &cluster_manager, diff --git a/source/extensions/tracers/opentelemetry/grpc_trace_exporter.h b/source/extensions/tracers/opentelemetry/grpc_trace_exporter.h index ecfc4baaa27e8..b35823b851ba7 100644 --- a/source/extensions/tracers/opentelemetry/grpc_trace_exporter.h +++ b/source/extensions/tracers/opentelemetry/grpc_trace_exporter.h @@ -69,7 +69,7 @@ class OpenTelemetryGrpcTraceExporterClient : Logger::Loggablestream_->isAboveWriteBufferHighWatermark()) { return false; } - stream_->stream_->sendMessage(request, false); + stream_->stream_->sendMessage(request, true); } else { stream_.reset(); } diff --git a/source/extensions/tracers/opentelemetry/resource_detectors/environment/environment_resource_detector.cc b/source/extensions/tracers/opentelemetry/resource_detectors/environment/environment_resource_detector.cc index c56894c25c425..7cf34bb08cded 100644 --- a/source/extensions/tracers/opentelemetry/resource_detectors/environment/environment_resource_detector.cc +++ b/source/extensions/tracers/opentelemetry/resource_detectors/environment/environment_resource_detector.cc @@ -1,4 +1,4 @@ -#include "environment_resource_detector.h" +#include "source/extensions/tracers/opentelemetry/resource_detectors/environment/environment_resource_detector.h" #include #include diff --git a/source/extensions/tracers/opentelemetry/span_context_extractor.cc b/source/extensions/tracers/opentelemetry/span_context_extractor.cc index 6f0165267f3ce..0fc913cdb2b61 100644 --- a/source/extensions/tracers/opentelemetry/span_context_extractor.cc +++ b/source/extensions/tracers/opentelemetry/span_context_extractor.cc @@ -4,9 +4,9 @@ #include "source/common/http/header_map_impl.h" #include "source/common/tracing/trace_context_impl.h" +#include "source/extensions/tracers/opentelemetry/span_context.h" #include "absl/strings/escaping.h" -#include "span_context.h" namespace Envoy { namespace Extensions { diff --git a/source/extensions/tracers/zipkin/zipkin_tracer_impl.cc b/source/extensions/tracers/zipkin/zipkin_tracer_impl.cc index 7642681d8321d..fc64a2cac11a7 100644 --- a/source/extensions/tracers/zipkin/zipkin_tracer_impl.cc +++ b/source/extensions/tracers/zipkin/zipkin_tracer_impl.cc @@ -77,8 +77,10 @@ Driver::Driver(const envoy::config::trace::v3::ZipkinConfig& zipkin_config, POOL_COUNTER_PREFIX(scope, "tracing.zipkin."))}, tls_(tls.allocateSlot()), runtime_(runtime), local_info_(local_info), time_source_(time_source) { - Config::Utility::checkCluster("envoy.tracers.zipkin", zipkin_config.collector_cluster(), cm_, - /* allow_added_via_api */ true); + THROW_IF_STATUS_NOT_OK(Config::Utility::checkCluster("envoy.tracers.zipkin", + zipkin_config.collector_cluster(), cm_, + /* allow_added_via_api */ true), + throw); cluster_ = zipkin_config.collector_cluster(); hostname_ = !zipkin_config.collector_hostname().empty() ? zipkin_config.collector_hostname() : zipkin_config.collector_cluster(); diff --git a/source/extensions/upstreams/http/config.cc b/source/extensions/upstreams/http/config.cc index a60a135e0e227..b1e8deaaedbdb 100644 --- a/source/extensions/upstreams/http/config.cc +++ b/source/extensions/upstreams/http/config.cc @@ -184,13 +184,38 @@ uint64_t ProtocolOptionsConfigImpl::parseFeatures(const envoy::config::cluster:: return features; } +absl::StatusOr> +ProtocolOptionsConfigImpl::createProtocolOptionsConfig( + const envoy::extensions::upstreams::http::v3::HttpProtocolOptions& options, + Server::Configuration::ServerFactoryContext& server_context) { + auto options_or_error = Http2::Utility::initializeAndValidateOptions(getHttp2Options(options)); + RETURN_IF_STATUS_NOT_OK(options_or_error); + return std::shared_ptr( + new ProtocolOptionsConfigImpl(options, options_or_error.value(), server_context)); +} + +absl::StatusOr> +ProtocolOptionsConfigImpl::createProtocolOptionsConfig( + const envoy::config::core::v3::Http1ProtocolOptions& http1_settings, + const envoy::config::core::v3::Http2ProtocolOptions& http2_options, + const envoy::config::core::v3::HttpProtocolOptions& common_options, + const absl::optional upstream_options, + bool use_downstream_protocol, bool use_http2, + ProtobufMessage::ValidationVisitor& validation_visitor) { + auto options_or_error = Http2::Utility::initializeAndValidateOptions(http2_options); + RETURN_IF_STATUS_NOT_OK(options_or_error); + return std::shared_ptr(new ProtocolOptionsConfigImpl( + http1_settings, options_or_error.value(), common_options, upstream_options, + use_downstream_protocol, use_http2, validation_visitor)); +} + ProtocolOptionsConfigImpl::ProtocolOptionsConfigImpl( const envoy::extensions::upstreams::http::v3::HttpProtocolOptions& options, + envoy::config::core::v3::Http2ProtocolOptions http2_options, Server::Configuration::ServerFactoryContext& server_context) : http1_settings_(Envoy::Http::Http1::parseHttp1Settings( getHttpOptions(options), server_context.messageValidationVisitor())), - http2_options_(Http2::Utility::initializeAndValidateOptions(getHttp2Options(options))), - http3_options_(getHttp3Options(options)), + http2_options_(std::move(http2_options)), http3_options_(getHttp3Options(options)), common_http_protocol_options_(options.common_http_protocol_options()), upstream_http_protocol_options_( options.has_upstream_http_protocol_options() @@ -202,20 +227,23 @@ ProtocolOptionsConfigImpl::ProtocolOptionsConfigImpl( header_validator_factory_(createHeaderValidatorFactory(options, server_context)), use_downstream_protocol_(options.has_use_downstream_protocol_config()), use_http2_(useHttp2(options)), use_http3_(useHttp3(options)), - use_alpn_(options.has_auto_config()) {} + use_alpn_(options.has_auto_config()) { + ASSERT(Http2::Utility::initializeAndValidateOptions(http2_options).status().ok()); +} ProtocolOptionsConfigImpl::ProtocolOptionsConfigImpl( const envoy::config::core::v3::Http1ProtocolOptions& http1_settings, - const envoy::config::core::v3::Http2ProtocolOptions& http2_options, + const envoy::config::core::v3::Http2ProtocolOptions& validated_http2_options, const envoy::config::core::v3::HttpProtocolOptions& common_options, const absl::optional upstream_options, bool use_downstream_protocol, bool use_http2, ProtobufMessage::ValidationVisitor& validation_visitor) : http1_settings_(Envoy::Http::Http1::parseHttp1Settings(http1_settings, validation_visitor)), - http2_options_(Http2::Utility::initializeAndValidateOptions(http2_options)), - common_http_protocol_options_(common_options), + http2_options_(validated_http2_options), common_http_protocol_options_(common_options), upstream_http_protocol_options_(upstream_options), - use_downstream_protocol_(use_downstream_protocol), use_http2_(use_http2) {} + use_downstream_protocol_(use_downstream_protocol), use_http2_(use_http2) { + ASSERT(Http2::Utility::initializeAndValidateOptions(validated_http2_options).status().ok()); +} LEGACY_REGISTER_FACTORY(ProtocolOptionsConfigFactory, Server::Configuration::ProtocolOptionsFactory, "envoy.upstreams.http.http_protocol_options"); diff --git a/source/extensions/upstreams/http/config.h b/source/extensions/upstreams/http/config.h index 9e1d4c78283b9..bbd33753a38e8 100644 --- a/source/extensions/upstreams/http/config.h +++ b/source/extensions/upstreams/http/config.h @@ -26,11 +26,10 @@ namespace Http { class ProtocolOptionsConfigImpl : public Upstream::ProtocolOptionsConfig { public: - ProtocolOptionsConfigImpl( + static absl::StatusOr> createProtocolOptionsConfig( const envoy::extensions::upstreams::http::v3::HttpProtocolOptions& options, Server::Configuration::ServerFactoryContext& server_context); - // Constructor for legacy (deprecated) config. - ProtocolOptionsConfigImpl( + static absl::StatusOr> createProtocolOptionsConfig( const envoy::config::core::v3::Http1ProtocolOptions& http1_settings, const envoy::config::core::v3::Http2ProtocolOptions& http2_options, const envoy::config::core::v3::HttpProtocolOptions& common_options, @@ -60,19 +59,34 @@ class ProtocolOptionsConfigImpl : public Upstream::ProtocolOptionsConfig { const bool use_http2_{}; const bool use_http3_{}; const bool use_alpn_{}; + +private: + ProtocolOptionsConfigImpl( + const envoy::extensions::upstreams::http::v3::HttpProtocolOptions& options, + envoy::config::core::v3::Http2ProtocolOptions validated_h2_options, + Server::Configuration::ServerFactoryContext& server_context); + // Constructor for legacy (deprecated) config. + ProtocolOptionsConfigImpl( + const envoy::config::core::v3::Http1ProtocolOptions& http1_settings, + const envoy::config::core::v3::Http2ProtocolOptions& validated_http2_options, + const envoy::config::core::v3::HttpProtocolOptions& common_options, + const absl::optional upstream_options, + bool use_downstream_protocol, bool use_http2, + ProtobufMessage::ValidationVisitor& validation_visitor); }; class ProtocolOptionsConfigFactory : public Server::Configuration::ProtocolOptionsFactory { public: - Upstream::ProtocolOptionsConfigConstSharedPtr createProtocolOptionsConfig( + absl::StatusOr createProtocolOptionsConfig( const Protobuf::Message& config, Server::Configuration::ProtocolOptionsFactoryContext& context) override { const auto& typed_config = MessageUtil::downcastAndValidate< const envoy::extensions::upstreams::http::v3::HttpProtocolOptions&>( config, context.messageValidationVisitor()); - return std::make_shared(typed_config, - context.serverFactoryContext()); + return ProtocolOptionsConfigImpl::createProtocolOptionsConfig(typed_config, + context.serverFactoryContext()); } + std::string category() const override { return "envoy.upstream_options"; } std::string name() const override { return "envoy.extensions.upstreams.http.v3.HttpProtocolOptions"; diff --git a/source/extensions/upstreams/tcp/config.h b/source/extensions/upstreams/tcp/config.h index 222150ce64fea..26c410fda5bb9 100644 --- a/source/extensions/upstreams/tcp/config.h +++ b/source/extensions/upstreams/tcp/config.h @@ -35,7 +35,7 @@ class ProtocolOptionsConfigImpl : public Upstream::ProtocolOptionsConfig { class ProtocolOptionsConfigFactory : public Server::Configuration::ProtocolOptionsFactory { public: - Upstream::ProtocolOptionsConfigConstSharedPtr createProtocolOptionsConfig( + absl::StatusOr createProtocolOptionsConfig( const Protobuf::Message& config, Server::Configuration::ProtocolOptionsFactoryContext& context) override { const auto& typed_config = MessageUtil::downcastAndValidate< diff --git a/source/server/admin/admin.cc b/source/server/admin/admin.cc index 9a40639a60c74..07f3b271381a3 100644 --- a/source/server/admin/admin.cc +++ b/source/server/admin/admin.cc @@ -273,7 +273,8 @@ Http::ServerConnectionPtr AdminImpl::createCodec(Network::Connection& connection connection, data, callbacks, *server_.stats().rootScope(), server_.api().randomGenerator(), http1_codec_stats_, http2_codec_stats_, Http::Http1Settings(), ::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions()), + envoy::config::core::v3::Http2ProtocolOptions()) + .value(), maxRequestHeadersKb(), maxRequestHeadersCount(), headersWithUnderscoresAction(), overload_manager); } diff --git a/source/server/admin/clusters_handler.cc b/source/server/admin/clusters_handler.cc index d1ca2c2b285e7..5b05de26a27c9 100644 --- a/source/server/admin/clusters_handler.cc +++ b/source/server/admin/clusters_handler.cc @@ -99,6 +99,9 @@ void setHealthFlag(Upstream::Host::HealthFlag flag, const Upstream::Host& host, health_status.set_active_hc_timeout( host.healthFlagGet(Upstream::Host::HealthFlag::ACTIVE_HC_TIMEOUT)); break; + case Upstream::Host::HealthFlag::EDS_STATUS_DRAINING: + health_status.set_eds_health_status(envoy::config::core::v3::DRAINING); + break; } } diff --git a/source/server/config_validation/dispatcher.h b/source/server/config_validation/dispatcher.h index 13808db9c9dbf..33d3c39ed200b 100644 --- a/source/server/config_validation/dispatcher.h +++ b/source/server/config_validation/dispatcher.h @@ -3,8 +3,7 @@ #include "envoy/event/dispatcher.h" #include "source/common/event/dispatcher_impl.h" - -#include "dns.h" +#include "source/server/config_validation/dns.h" namespace Envoy { namespace Event { diff --git a/source/server/config_validation/server.cc b/source/server/config_validation/server.cc index f8d6e31813d6d..47cc069270bd2 100644 --- a/source/server/config_validation/server.cc +++ b/source/server/config_validation/server.cc @@ -112,7 +112,9 @@ void ValidationInstance::initialize(const Options& options, overload_manager_ = std::make_unique( dispatcher(), *stats().rootScope(), threadLocal(), bootstrap_.overload_manager(), messageValidationContext().staticValidationVisitor(), *api_, options_); - Configuration::InitialImpl initial_config(bootstrap_); + absl::Status creation_status = absl::OkStatus(); + Configuration::InitialImpl initial_config(bootstrap_, creation_status); + THROW_IF_NOT_OK(creation_status); AdminFactoryContext factory_context(*this, std::make_shared()); initial_config.initAdminAccessLog(bootstrap_, factory_context); admin_ = std::make_unique(initial_config.admin().address()); @@ -134,7 +136,7 @@ void ValidationInstance::initialize(const Options& options, server_contexts_, stats(), threadLocal(), http_context_, [this]() -> Network::DnsResolverSharedPtr { return this->dnsResolver(); }, sslContextManager(), *secret_manager_, quic_stat_names_, *this); - config_.initialize(bootstrap_, *this, *cluster_manager_factory_); + THROW_IF_NOT_OK(config_.initialize(bootstrap_, *this, *cluster_manager_factory_)); runtime().initialize(clusterManager()); clusterManager().setInitializedCb([this]() -> void { init_manager_.initialize(init_watcher_); }); } diff --git a/source/server/configuration_impl.cc b/source/server/configuration_impl.cc index 6129c61821310..b5c01e101646f 100644 --- a/source/server/configuration_impl.cc +++ b/source/server/configuration_impl.cc @@ -81,13 +81,16 @@ bool FilterChainUtility::buildQuicFilterChain( return true; } -StatsConfigImpl::StatsConfigImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap) +StatsConfigImpl::StatsConfigImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + absl::Status& status) : deferred_stat_options_(bootstrap.deferred_stat_options()) { + status = absl::OkStatus(); if (bootstrap.has_stats_flush_interval() && bootstrap.stats_flush_case() != envoy::config::bootstrap::v3::Bootstrap::STATS_FLUSH_NOT_SET) { - throwEnvoyExceptionOrPanic( + status = absl::InvalidArgumentError( "Only one of stats_flush_interval or stats_flush_on_admin should be set!"); + return; } flush_interval_ = @@ -98,9 +101,9 @@ StatsConfigImpl::StatsConfigImpl(const envoy::config::bootstrap::v3::Bootstrap& } } -void MainImpl::initialize(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, - Instance& server, - Upstream::ClusterManagerFactory& cluster_manager_factory) { +absl::Status MainImpl::initialize(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + Instance& server, + Upstream::ClusterManagerFactory& cluster_manager_factory) { // In order to support dynamic configuration of tracing providers, // a former server-wide Tracer singleton has been replaced by // an Tracer instance per "envoy.filters.network.http_connection_manager" filter. @@ -113,13 +116,15 @@ void MainImpl::initialize(const envoy::config::bootstrap::v3::Bootstrap& bootstr // stats_config_ should be set before creating the ClusterManagers so that it is available // from the ServerFactoryContext when creating the static clusters and stats sinks, where // stats deferred instantiation setting is read. - stats_config_ = std::make_unique(bootstrap); + absl::Status status = absl::OkStatus(); + stats_config_ = std::make_unique(bootstrap, status); + RETURN_IF_NOT_OK(status); const auto& secrets = bootstrap.static_resources().secrets(); ENVOY_LOG(info, "loading {} static secret(s)", secrets.size()); for (ssize_t i = 0; i < secrets.size(); i++) { ENVOY_LOG(debug, "static secret #{}: {}", i, secrets[i].name()); - THROW_IF_NOT_OK(server.secretManager().addStaticSecret(secrets[i])); + RETURN_IF_NOT_OK(server.secretManager().addStaticSecret(secrets[i])); } ENVOY_LOG(info, "loading {} cluster(s)", bootstrap.static_resources().clusters().size()); @@ -131,14 +136,13 @@ void MainImpl::initialize(const envoy::config::bootstrap::v3::Bootstrap& bootstr ENVOY_LOG(debug, "listener #{}:", i); absl::StatusOr update_or_error = server.listenerManager().addOrUpdateListener(listeners[i], "", false); - if (!update_or_error.status().ok()) { - throwEnvoyExceptionOrPanic(std::string(update_or_error.status().message())); - } + RETURN_IF_STATUS_NOT_OK(update_or_error); } - initializeWatchdogs(bootstrap, server); + RETURN_IF_NOT_OK(initializeWatchdogs(bootstrap, server)); // This has to happen after ClusterManager initialization, as it depends on config from // ClusterManager. initializeStatsConfig(bootstrap, server); + return absl::OkStatus(); } void MainImpl::initializeStatsConfig(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, @@ -181,10 +185,10 @@ void MainImpl::initializeTracers(const envoy::config::trace::v3::Tracing& config // is no longer validated in this step. } -void MainImpl::initializeWatchdogs(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, - Instance& server) { +absl::Status MainImpl::initializeWatchdogs(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + Instance& server) { if (bootstrap.has_watchdog() && bootstrap.has_watchdogs()) { - throwEnvoyExceptionOrPanic("Only one of watchdog or watchdogs should be set!"); + return absl::InvalidArgumentError("Only one of watchdog or watchdogs should be set!"); } if (bootstrap.has_watchdog()) { @@ -196,6 +200,7 @@ void MainImpl::initializeWatchdogs(const envoy::config::bootstrap::v3::Bootstrap worker_watchdog_ = std::make_unique(bootstrap.watchdogs().worker_watchdog(), server); } + return absl::OkStatus(); } WatchdogImpl::WatchdogImpl(const envoy::config::bootstrap::v3::Watchdog& watchdog, @@ -225,14 +230,19 @@ WatchdogImpl::WatchdogImpl(const envoy::config::bootstrap::v3::Watchdog& watchdo actions_ = watchdog.actions(); } -InitialImpl::InitialImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap) { +InitialImpl::InitialImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + absl::Status& creation_status) { + creation_status = absl::OkStatus(); const auto& admin = bootstrap.admin(); admin_.profile_path_ = admin.profile_path().empty() ? "/var/log/envoy/envoy.prof" : admin.profile_path(); if (admin.has_address()) { auto address_or_error = Network::Address::resolveProtoAddress(admin.address()); - THROW_IF_STATUS_NOT_OK(address_or_error, throw); + if (!address_or_error.status().ok()) { + creation_status = address_or_error.status(); + return; + } admin_.address_ = std::move(address_or_error.value()); } admin_.socket_options_ = std::make_shared>(); diff --git a/source/server/configuration_impl.h b/source/server/configuration_impl.h index 6b039328a491c..3c95db66888af 100644 --- a/source/server/configuration_impl.h +++ b/source/server/configuration_impl.h @@ -49,7 +49,8 @@ class StatsSinkFactory : public Config::TypedFactory { class StatsConfigImpl : public StatsConfig { public: - StatsConfigImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap); + StatsConfigImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + absl::Status& creation_status); const std::list& sinks() const override { return sinks_; } std::chrono::milliseconds flushInterval() const override { return flush_interval_; } @@ -122,9 +123,11 @@ class MainImpl : Logger::Loggable, public Main { * @param bootstrap v2 bootstrap proto. * @param server supplies the owning server. * @param cluster_manager_factory supplies the cluster manager creation factory. + * @return a status indicating initialization success or failure. */ - void initialize(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, Instance& server, - Upstream::ClusterManagerFactory& cluster_manager_factory); + absl::Status initialize(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + Instance& server, + Upstream::ClusterManagerFactory& cluster_manager_factory); // Server::Configuration::Main Upstream::ClusterManager* clusterManager() override { return cluster_manager_.get(); } @@ -148,8 +151,8 @@ class MainImpl : Logger::Loggable, public Main { /** * Initialize watchdog(s). Call before accessing any watchdog configuration. */ - void initializeWatchdogs(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, - Instance& server); + absl::Status initializeWatchdogs(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + Instance& server); std::unique_ptr cluster_manager_; std::unique_ptr stats_config_; @@ -185,7 +188,8 @@ class WatchdogImpl : public Watchdog { */ class InitialImpl : public Initial { public: - InitialImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap); + InitialImpl(const envoy::config::bootstrap::v3::Bootstrap& bootstrap, + absl::Status& creation_status); // Server::Configuration::Initial Admin& admin() override { return admin_; } diff --git a/source/server/overload_manager_impl.cc b/source/server/overload_manager_impl.cc index 84d00032a2f6f..4ebfd5b5cb151 100644 --- a/source/server/overload_manager_impl.cc +++ b/source/server/overload_manager_impl.cc @@ -420,13 +420,10 @@ OverloadManagerImpl::OverloadManagerImpl(Event::Dispatcher& dispatcher, Stats::S ENVOY_LOG(debug, "Adding overload action {}", name); // Validate that this is a well known overload action. - if (Runtime::runtimeFeatureEnabled( - "envoy.reloadable_features.overload_manager_error_unknown_action")) { - auto& well_known_actions = OverloadActionNames::get().WellKnownActions; - if (std::find(well_known_actions.begin(), well_known_actions.end(), name) == - well_known_actions.end()) { - throw EnvoyException(absl::StrCat("Unknown Overload Manager Action ", name)); - } + const auto& well_known_actions = OverloadActionNames::get().WellKnownActions; + if (std::find(well_known_actions.begin(), well_known_actions.end(), name) == + well_known_actions.end()) { + throw EnvoyException(absl::StrCat("Unknown Overload Manager Action ", name)); } // TODO: use in place construction once https://github.com/abseil/abseil-cpp/issues/388 is diff --git a/source/server/server.cc b/source/server/server.cc index dd2028bb26bdb..ce41536f6563c 100644 --- a/source/server/server.cc +++ b/source/server/server.cc @@ -46,6 +46,7 @@ #include "source/common/runtime/runtime_keys.h" #include "source/common/signal/fatal_error_handler.h" #include "source/common/singleton/manager_impl.h" +#include "source/common/stats/stats_matcher_impl.h" #include "source/common/stats/thread_local_store.h" #include "source/common/stats/timespan_impl.h" #include "source/common/upstream/cluster_manager_impl.h" @@ -500,9 +501,10 @@ void InstanceBase::initializeOrThrow(Network::Address::InstanceConstSharedPtr lo // Needs to happen as early as possible in the instantiation to preempt the objects that require // stats. stats_store_.setTagProducer(Config::Utility::createTagProducer(bootstrap_, options_.statsTags())); - stats_store_.setStatsMatcher( - Config::Utility::createStatsMatcher(bootstrap_, stats_store_.symbolTable())); - stats_store_.setHistogramSettings(Config::Utility::createHistogramSettings(bootstrap_)); + stats_store_.setStatsMatcher(std::make_unique( + bootstrap_.stats_config(), stats_store_.symbolTable())); + stats_store_.setHistogramSettings( + std::make_unique(bootstrap_.stats_config())); const std::string server_stats_prefix = "server."; const std::string server_compilation_settings_stats_prefix = "server.compilation_settings"; @@ -581,7 +583,9 @@ void InstanceBase::initializeOrThrow(Network::Address::InstanceConstSharedPtr lo stats().symbolTable(), bootstrap_.node(), bootstrap_.node_context_params(), local_address, options_.serviceZone(), options_.serviceClusterName(), options_.serviceNodeName()); - Configuration::InitialImpl initial_config(bootstrap_); + absl::Status creation_status; + Configuration::InitialImpl initial_config(bootstrap_, creation_status); + THROW_IF_NOT_OK(creation_status); // Learn original_start_time_ if our parent is still around to inform us of it. const auto parent_admin_shutdown_response = restarter_.sendParentAdminShutdownRequest(); @@ -736,7 +740,7 @@ void InstanceBase::initializeOrThrow(Network::Address::InstanceConstSharedPtr lo // thread local data per above. See MainImpl::initialize() for why ConfigImpl // is constructed as part of the InstanceBase and then populated once // cluster_manager_factory_ is available. - config_.initialize(bootstrap_, *this, *cluster_manager_factory_); + THROW_IF_NOT_OK(config_.initialize(bootstrap_, *this, *cluster_manager_factory_)); // Instruct the listener manager to create the LDS provider if needed. This must be done later // because various items do not yet exist when the listener manager is created. @@ -805,12 +809,13 @@ void InstanceBase::onRuntimeReady() { bootstrap_.grpc_async_client_manager_config()); TRY_ASSERT_MAIN_THREAD { THROW_IF_NOT_OK(Config::Utility::checkTransportVersion(hds_config)); + auto factory_or_error = Config::Utility::factoryForGrpcApiConfigSource( + *async_client_manager_, hds_config, *stats_store_.rootScope(), false); + THROW_IF_STATUS_NOT_OK(factory_or_error, throw); hds_delegate_ = std::make_unique( serverFactoryContext(), *stats_store_.rootScope(), - Config::Utility::factoryForGrpcApiConfigSource(*async_client_manager_, hds_config, - *stats_store_.rootScope(), false) - ->createUncachedRawAsyncClient(), - stats_store_, *ssl_context_manager_, info_factory_); + factory_or_error.value()->createUncachedRawAsyncClient(), stats_store_, + *ssl_context_manager_, info_factory_); } END_TRY CATCH(const EnvoyException& e, { diff --git a/test/common/access_log/access_log_impl_test.cc b/test/common/access_log/access_log_impl_test.cc index d003228f1a295..ed2d4da9a2dea 100644 --- a/test/common/access_log/access_log_impl_test.cc +++ b/test/common/access_log/access_log_impl_test.cc @@ -91,7 +91,7 @@ name: accesslog InstanceSharedPtr log = AccessLogFactory::fromProto(parseAccessLogFromV3Yaml(yaml), context_); EXPECT_CALL(*file_, write(_)); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); request_headers_.addCopy(Http::Headers::get().UserAgent, "user-agent-set"); request_headers_.addCopy(Http::Headers::get().RequestId, "id"); request_headers_.addCopy(Http::Headers::get().Host, "host"); @@ -118,7 +118,7 @@ name: accesslog auto cluster = std::make_shared>(); stream_info_.upstreamInfo()->setUpstreamHost( Upstream::makeTestHostDescription(cluster, "tcp://10.0.0.5:1234", simTime())); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::DownstreamConnectionTermination); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::DownstreamConnectionTermination); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); EXPECT_EQ("[1999-01-01T00:00:00.000Z] \"GET / HTTP/1.1\" 0 DC 1 2 3 - \"-\" \"-\" \"-\" \"-\" " @@ -135,7 +135,7 @@ void AccessLogImplTest::routeNameTest(std::string yaml, bool omit_empty) { route->route_name_ = "route-test-name"; stream_info_.route_ = route; - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure); request_headers_.addCopy(Http::Headers::get().UserAgent, "user-agent-set"); request_headers_.addCopy(Http::Headers::get().RequestId, "id"); request_headers_.addCopy(Http::Headers::get().Host, "host"); @@ -977,7 +977,7 @@ name: accesslog EXPECT_CALL(*file_, write(_)).Times(0); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); EXPECT_CALL(*file_, write(_)); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); } @@ -999,11 +999,11 @@ name: accesslog EXPECT_CALL(*file_, write(_)).Times(0); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); EXPECT_CALL(*file_, write(_)).Times(0); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); EXPECT_CALL(*file_, write(_)); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); } @@ -1026,11 +1026,11 @@ name: accesslog EXPECT_CALL(*file_, write(_)).Times(0); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); EXPECT_CALL(*file_, write(_)).Times(0); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); - stream_info_.setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow); + stream_info_.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow); EXPECT_CALL(*file_, write(_)); log->log({&request_headers_, &response_headers_, &response_trailers_}, stream_info_); } @@ -1076,9 +1076,10 @@ name: accesslog InstanceSharedPtr log = AccessLogFactory::fromProto(parseAccessLogFromV3Yaml(yaml), context_); - for (const auto& [flag_strings, response_flag] : - StreamInfo::ResponseFlagUtils::ALL_RESPONSE_STRINGS_FLAGS) { - UNREFERENCED_PARAMETER(flag_strings); + for (const auto& [short_string, long_string, response_flag] : + StreamInfo::ResponseFlagUtils::CORE_RESPONSE_FLAGS) { + UNREFERENCED_PARAMETER(short_string); + UNREFERENCED_PARAMETER(long_string); TestStreamInfo stream_info(time_source_); stream_info.setResponseFlag(response_flag); diff --git a/test/common/common/BUILD b/test/common/common/BUILD index e179ac4be21ba..853f1b0b5b4d0 100644 --- a/test/common/common/BUILD +++ b/test/common/common/BUILD @@ -511,3 +511,11 @@ envoy_benchmark_test( name = "inline_map_speed_test_benchmark_test", benchmark_binary = "inline_map_speed_test", ) + +envoy_cc_test( + name = "execution_context_test", + srcs = ["execution_context_test.cc"], + deps = [ + "//envoy/common:execution_context", + ], +) diff --git a/test/common/common/execution_context_test.cc b/test/common/common/execution_context_test.cc new file mode 100644 index 0000000000000..25d886314e1ff --- /dev/null +++ b/test/common/common/execution_context_test.cc @@ -0,0 +1,71 @@ +#include "envoy/common/execution_context.h" + +#include "gtest/gtest.h" + +namespace Envoy { + +class TestExecutionContext : public ExecutionContext { +public: + int activationDepth() const { return activation_depth_; } + int activationGenerations() const { return activation_generations_; } + +private: + void activate() override { + if (activation_depth_ == 0) { + activation_generations_++; + } + activation_depth_++; + } + + void deactivate() override { + EXPECT_GE(activation_depth_, 0); + activation_depth_--; + } + + int activation_depth_ = 0; + // How many times |activation_depth_| changed from 0 to 1. + int activation_generations_ = 0; +}; + +TEST(ExecutionContextTest, NullContext) { + ScopedExecutionContext scoped_context(nullptr); + EXPECT_TRUE(scoped_context.isNull()); + + ScopedExecutionContext scoped_context2; + EXPECT_TRUE(scoped_context2.isNull()); +} + +TEST(ExecutionContextTest, NestedScopes) { + TestExecutionContext context; + EXPECT_EQ(context.activationDepth(), 0); + EXPECT_EQ(context.activationGenerations(), 0); + + { + ScopedExecutionContext scoped_context(&context); + EXPECT_EQ(context.activationDepth(), 1); + EXPECT_EQ(context.activationGenerations(), 1); + { + ScopedExecutionContext nested_scoped_context(&context); + EXPECT_EQ(context.activationDepth(), 2); + EXPECT_EQ(context.activationGenerations(), 1); + } + EXPECT_EQ(context.activationDepth(), 1); + EXPECT_EQ(context.activationGenerations(), 1); + } + EXPECT_EQ(context.activationDepth(), 0); + EXPECT_EQ(context.activationGenerations(), 1); +} + +TEST(ExecutionContextTest, DisjointScopes) { + TestExecutionContext context; + + for (int i = 1; i < 5; i++) { + ScopedExecutionContext scoped_context(&context); + EXPECT_EQ(context.activationDepth(), 1); + EXPECT_EQ(context.activationGenerations(), i); + } + + EXPECT_EQ(context.activationDepth(), 0); +} + +} // namespace Envoy diff --git a/test/common/common/scope_tracker_test.cc b/test/common/common/scope_tracker_test.cc index 12b7133a06164..7d928b18019e1 100644 --- a/test/common/common/scope_tracker_test.cc +++ b/test/common/common/scope_tracker_test.cc @@ -11,11 +11,18 @@ #include "gtest/gtest.h" namespace Envoy { -namespace { using testing::_; -TEST(ScopeTrackerScopeStateTest, ShouldManageTrackedObjectOnDispatcherStack) { +class ScopeTrackerScopeStateTest : public testing::Test { +protected: + void setExecutionContextEnabled(bool enabled) { + ScopeTrackerScopeState::executionContextEnabled() = enabled; + } +}; + +TEST_F(ScopeTrackerScopeStateTest, ShouldManageTrackedObjectOnDispatcherStack) { + setExecutionContextEnabled(false); Api::ApiPtr api(Api::createApiForTest()); Event::DispatcherPtr dispatcher(api->allocateDispatcher("test_thread")); MockScopeTrackedObject tracked_object; @@ -33,5 +40,13 @@ TEST(ScopeTrackerScopeStateTest, ShouldManageTrackedObjectOnDispatcherStack) { static_cast(dispatcher.get())->onFatalError(std::cerr); } -} // namespace +TEST_F(ScopeTrackerScopeStateTest, ExecutionContextEnabled) { + setExecutionContextEnabled(true); + Api::ApiPtr api(Api::createApiForTest()); + Event::DispatcherPtr dispatcher(api->allocateDispatcher("test_thread")); + MockScopeTrackedObject tracked_object; + EXPECT_CALL(tracked_object, executionContext()); + ScopeTrackerScopeState scope(&tracked_object, *dispatcher); +} + } // namespace Envoy diff --git a/test/common/config/utility_test.cc b/test/common/config/utility_test.cc index f8a5724dfb201..b4f13d5195c81 100644 --- a/test/common/config/utility_test.cc +++ b/test/common/config/utility_test.cc @@ -28,6 +28,7 @@ #include "udpa/type/v1/typed_struct.pb.h" #include "xds/type/v3/typed_struct.pb.h" +using testing::ContainsRegex; using testing::Eq; using testing::Optional; using testing::Ref; @@ -42,25 +43,6 @@ TEST(UtilityTest, ComputeHashedVersion) { EXPECT_EQ("hash_33bf00a859c4ba3f", Utility::computeHashedVersion("foo").first); } -TEST(UtilityTest, ApiConfigSourceRefreshDelay) { - envoy::config::core::v3::ApiConfigSource api_config_source; - api_config_source.mutable_refresh_delay()->CopyFrom( - Protobuf::util::TimeUtil::MillisecondsToDuration(1234)); - EXPECT_EQ(1234, Utility::apiConfigSourceRefreshDelay(api_config_source).count()); -} - -TEST(UtilityTest, ApiConfigSourceDefaultRequestTimeout) { - envoy::config::core::v3::ApiConfigSource api_config_source; - EXPECT_EQ(1000, Utility::apiConfigSourceRequestTimeout(api_config_source).count()); -} - -TEST(UtilityTest, ApiConfigSourceRequestTimeout) { - envoy::config::core::v3::ApiConfigSource api_config_source; - api_config_source.mutable_request_timeout()->CopyFrom( - Protobuf::util::TimeUtil::MillisecondsToDuration(1234)); - EXPECT_EQ(1234, Utility::apiConfigSourceRequestTimeout(api_config_source).count()); -} - TEST(UtilityTest, ConfigSourceDefaultInitFetchTimeout) { envoy::config::core::v3::ConfigSource config_source; EXPECT_EQ(15000, Utility::configSourceInitialFetchTimeout(config_source).count()); @@ -96,11 +78,10 @@ TEST(UtilityTest, createTagProducerWithDefaultTgs) { TEST(UtilityTest, CheckFilesystemSubscriptionBackingPath) { Api::ApiPtr api = Api::createApiForTest(); - EXPECT_THROW_WITH_MESSAGE( - Utility::checkFilesystemSubscriptionBackingPath("foo", *api), EnvoyException, - "paths must refer to an existing path in the system: 'foo' does not exist"); + EXPECT_EQ(Utility::checkFilesystemSubscriptionBackingPath("foo", *api).message(), + "paths must refer to an existing path in the system: 'foo' does not exist"); std::string test_path = TestEnvironment::temporaryDirectory(); - Utility::checkFilesystemSubscriptionBackingPath(test_path, *api); + EXPECT_TRUE(Utility::checkFilesystemSubscriptionBackingPath(test_path, *api).ok()); } TEST(UtilityTest, ParseDefaultRateLimitSettings) { @@ -142,10 +123,12 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { { envoy::config::core::v3::ApiConfigSource api_config_source; api_config_source.set_api_type(envoy::config::core::v3::ApiConfigSource::GRPC); - EXPECT_THROW_WITH_REGEX( + EXPECT_EQ( Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, scope, - false), - EnvoyException, "API configs must have either a gRPC service or a cluster name defined:"); + false) + .status() + .message(), + "API configs must have either a gRPC service or a cluster name defined: api_type: GRPC\n"); } { @@ -153,12 +136,13 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { api_config_source.set_api_type(envoy::config::core::v3::ApiConfigSource::GRPC); api_config_source.add_grpc_services(); api_config_source.add_grpc_services(); - EXPECT_THROW_WITH_REGEX(Utility::factoryForGrpcApiConfigSource(async_client_manager, - api_config_source, scope, false), - EnvoyException, - fmt::format("{}::.DELTA_.GRPC must have a single gRPC service " - "specified:", - api_config_source.GetTypeName())); + EXPECT_THAT(Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, + scope, false) + .status() + .message(), + ContainsRegex(fmt::format("{}::.DELTA_.GRPC must have a single gRPC service " + "specified:", + api_config_source.GetTypeName()))); } { @@ -166,12 +150,13 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { api_config_source.set_api_type(envoy::config::core::v3::ApiConfigSource::GRPC); api_config_source.add_cluster_names(); // this also logs a warning for setting REST cluster names for a gRPC API config. - EXPECT_THROW_WITH_REGEX(Utility::factoryForGrpcApiConfigSource(async_client_manager, - api_config_source, scope, false), - EnvoyException, - fmt::format("{}::.DELTA_.GRPC must not have a cluster name " - "specified:", - api_config_source.GetTypeName())); + EXPECT_THAT(Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, + scope, false) + .status() + .message(), + ContainsRegex(fmt::format("{}::.DELTA_.GRPC must not have a cluster name " + "specified:", + api_config_source.GetTypeName()))); } { @@ -179,12 +164,13 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { api_config_source.set_api_type(envoy::config::core::v3::ApiConfigSource::GRPC); api_config_source.add_cluster_names(); api_config_source.add_cluster_names(); - EXPECT_THROW_WITH_REGEX(Utility::factoryForGrpcApiConfigSource(async_client_manager, - api_config_source, scope, false), - EnvoyException, - fmt::format("{}::.DELTA_.GRPC must not have a cluster name " - "specified:", - api_config_source.GetTypeName())); + EXPECT_THAT(Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, + scope, false) + .status() + .message(), + ContainsRegex(fmt::format("{}::.DELTA_.GRPC must not have a cluster name " + "specified:", + api_config_source.GetTypeName()))); } { @@ -192,22 +178,25 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { api_config_source.set_api_type(envoy::config::core::v3::ApiConfigSource::REST); api_config_source.add_grpc_services()->mutable_envoy_grpc()->set_cluster_name("foo"); // this also logs a warning for configuring gRPC clusters for a REST API config. - EXPECT_THROW_WITH_REGEX(Utility::factoryForGrpcApiConfigSource(async_client_manager, - api_config_source, scope, false), - EnvoyException, - fmt::format("{}, if not a gRPC type, must not have a gRPC service " - "specified:", - api_config_source.GetTypeName())); + EXPECT_THAT(Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, + scope, false) + .status() + .message(), + ContainsRegex(fmt::format("{}, if not a gRPC type, must not have a gRPC service " + "specified:", + api_config_source.GetTypeName()))); } { envoy::config::core::v3::ApiConfigSource api_config_source; api_config_source.set_api_type(envoy::config::core::v3::ApiConfigSource::REST); api_config_source.add_cluster_names("foo"); - EXPECT_THROW_WITH_REGEX(Utility::factoryForGrpcApiConfigSource(async_client_manager, - api_config_source, scope, false), - EnvoyException, - fmt::format("{} type must be gRPC:", api_config_source.GetTypeName())); + EXPECT_THAT( + Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, scope, + false) + .status() + .message(), + ContainsRegex(fmt::format("{} type must be gRPC:", api_config_source.GetTypeName()))); } { @@ -218,7 +207,9 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { expected_grpc_service.mutable_envoy_grpc()->set_cluster_name("foo"); EXPECT_CALL(async_client_manager, factoryForGrpcService(ProtoEq(expected_grpc_service), Ref(scope), false)); - Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, scope, false); + EXPECT_TRUE(Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, + scope, false) + .ok()); } { @@ -228,7 +219,9 @@ TEST(UtilityTest, FactoryForGrpcApiConfigSource) { EXPECT_CALL( async_client_manager, factoryForGrpcService(ProtoEq(api_config_source.grpc_services(0)), Ref(scope), true)); - Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, scope, true); + EXPECT_TRUE( + Utility::factoryForGrpcApiConfigSource(async_client_manager, api_config_source, scope, true) + .ok()); } } @@ -277,7 +270,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { // valid default base and max interval values JitteredExponentialBackOffStrategyPtr strategy; - strategy = Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, 1000); + strategy = + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, 1000).value(); EXPECT_NE(nullptr, dynamic_cast(strategy.get())); EXPECT_EQ(true, dynamic_cast(strategy.get()) @@ -285,7 +279,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { // only valid base interval value strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt); + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt) + .value(); EXPECT_NE(nullptr, dynamic_cast(strategy.get())); // time limit will be 10 * provided default base interval @@ -293,16 +288,16 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { ->isOverTimeLimit(500 * 10 + 1)); // invalid base interval value - EXPECT_THROW_WITH_MESSAGE( - JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 0, absl::nullopt), - EnvoyException, "default_base_interval_ms must be greater than zero"); + EXPECT_EQ(Utility::prepareJitteredExponentialBackOffStrategy(config, random, 0, absl::nullopt) + .status() + .message(), + "default_base_interval_ms must be greater than zero"); // invalid max interval value < base interval value - EXPECT_THROW_WITH_MESSAGE( - JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 1000, 500), - EnvoyException, + EXPECT_EQ( + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 1000, 500) + .status() + .message(), "default_max_interval_ms must be greater than or equal to the default_base_interval_ms"); } @@ -317,7 +312,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { EXPECT_FALSE(config.has_retry_policy()); JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt); + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt) + .value(); EXPECT_NE(nullptr, dynamic_cast(strategy.get())); // time limit will be 10 * provided default base interval @@ -325,10 +321,10 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { ->isOverTimeLimit(500 * 10 + 1)); // test an invalid default base interval - EXPECT_THROW_WITH_MESSAGE( - JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 0, absl::nullopt), - EnvoyException, "default_base_interval_ms must be greater than zero"); + EXPECT_EQ(Utility::prepareJitteredExponentialBackOffStrategy(config, random, 0, absl::nullopt) + .status() + .message(), + "default_base_interval_ms must be greater than zero"); } // provide ApiConfigSource config without any configured retry values @@ -342,7 +338,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { JitteredExponentialBackOffStrategyPtr strategy = Utility::prepareJitteredExponentialBackOffStrategy(api_config_source, random, 500, - absl::nullopt); + absl::nullopt) + .value(); EXPECT_NE(nullptr, dynamic_cast(strategy.get())); // time limit will be 10 * provided default base interval @@ -350,10 +347,11 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyNoConfig) { ->isOverTimeLimit(500 * 10 + 1)); // test an invalid default base interval - EXPECT_THROW_WITH_MESSAGE(JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy( - api_config_source, random, 0, absl::nullopt), - EnvoyException, "default_base_interval_ms must be greater than zero"); + EXPECT_EQ(Utility::prepareJitteredExponentialBackOffStrategy(api_config_source, random, 0, + absl::nullopt) + .status() + .message(), + "default_base_interval_ms must be greater than zero"); } } @@ -374,7 +372,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyConfigFileValues) { TestUtility::loadFromYaml(config_yaml, config); EXPECT_TRUE(config.has_retry_policy()); JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt); + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt) + .value(); EXPECT_NE(nullptr, dynamic_cast(strategy.get())); EXPECT_EQ( false, @@ -402,7 +401,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyConfigFileValues) { JitteredExponentialBackOffStrategyPtr strategy = Utility::prepareJitteredExponentialBackOffStrategy(api_config_source, random, 500, - absl::nullopt); + absl::nullopt) + .value(); EXPECT_NE(nullptr, dynamic_cast(strategy.get())); @@ -439,7 +439,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyCustomValues) { test_max_interval_ms / 1000); JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt); + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt) + .value(); // provided time limit is equal to max time limit EXPECT_EQ(false, dynamic_cast(strategy.get()) @@ -465,7 +466,8 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyCustomValues) { test_base_interval_ms / 1000); JitteredExponentialBackOffStrategyPtr strategy = - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt); + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt) + .value(); // max_interval should be less than or equal test_base_interval * 10 EXPECT_EQ(false, dynamic_cast(strategy.get()) @@ -491,8 +493,10 @@ TEST(UtilityTest, PrepareJitteredExponentialBackOffStrategyCustomValues) { config.mutable_retry_policy()->mutable_retry_back_off()->mutable_max_interval()->set_seconds( test_max_interval_ms); - EXPECT_ANY_THROW( - Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt)); + EXPECT_FALSE( + Utility::prepareJitteredExponentialBackOffStrategy(config, random, 500, absl::nullopt) + .status() + .ok()); } } } @@ -698,31 +702,34 @@ TEST(CheckApiConfigSourceSubscriptionBackingClusterTest, GrpcClusterTestAcrossTy api_config_source->set_api_type(envoy::config::core::v3::ApiConfigSource::GRPC); // GRPC cluster without GRPC services. - EXPECT_THROW_WITH_REGEX( - Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source), - EnvoyException, "API configs must have either a gRPC service or a cluster name defined:"); + EXPECT_EQ( + Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source) + .message(), + "API configs must have either a gRPC service or a cluster name defined: api_type: GRPC\n"); // Non-existent cluster. api_config_source->add_grpc_services()->mutable_envoy_grpc()->set_cluster_name("foo_cluster"); - EXPECT_THROW_WITH_MESSAGE( - Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source), - EnvoyException, + EXPECT_EQ( + Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source) + .message(), fmt::format("{} must have a statically defined non-EDS cluster: " "'foo_cluster' does not exist, was added via api, or is an EDS cluster", api_config_source->GetTypeName())); // All ok. primary_clusters.insert("foo_cluster"); - Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source); + EXPECT_TRUE( + Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source) + .ok()); // API with cluster_names set should be rejected. api_config_source->add_cluster_names("foo_cluster"); - EXPECT_THROW_WITH_REGEX( - Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source), - EnvoyException, - fmt::format("{}::.DELTA_.GRPC must not have a cluster name " - "specified:", - api_config_source->GetTypeName())); + EXPECT_THAT( + Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source) + .message(), + ContainsRegex(fmt::format("{}::.DELTA_.GRPC must not have a cluster name " + "specified:", + api_config_source->GetTypeName()))); } TEST(CheckApiConfigSourceSubscriptionBackingClusterTest, RestClusterTestAcrossTypes) { @@ -733,16 +740,18 @@ TEST(CheckApiConfigSourceSubscriptionBackingClusterTest, RestClusterTestAcrossTy // Non-existent cluster. api_config_source->add_cluster_names("foo_cluster"); - EXPECT_THROW_WITH_MESSAGE( - Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source), - EnvoyException, + EXPECT_EQ( + Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source) + .message(), fmt::format("{} must have a statically defined non-EDS cluster: " "'foo_cluster' does not exist, was added via api, or is an EDS cluster", api_config_source->GetTypeName())); // All ok. primary_clusters.insert("foo_cluster"); - Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source); + EXPECT_TRUE( + Utility::checkApiConfigSourceSubscriptionBackingCluster(primary_clusters, *api_config_source) + .ok()); } // Validates CheckCluster functionality. @@ -750,21 +759,21 @@ TEST(UtilityTest, CheckCluster) { NiceMock cm; // Validate that proper error is thrown, when cluster is not available. - EXPECT_THROW_WITH_MESSAGE(Utility::checkCluster("prefix", "foo", cm, false), EnvoyException, - "prefix: unknown cluster 'foo'"); + EXPECT_THAT(Utility::checkCluster("prefix", "foo", cm, false).status().message(), + ContainsRegex("prefix: unknown cluster 'foo'")); // Validate that proper error is thrown, when dynamic cluster is passed when it is not expected. cm.initializeClusters({"foo"}, {}); ON_CALL(*cm.active_clusters_["foo"]->info_, addedViaApi()).WillByDefault(Return(true)); - EXPECT_THROW_WITH_MESSAGE(Utility::checkCluster("prefix", "foo", cm, false), EnvoyException, - "prefix: invalid cluster 'foo': currently only " - "static (non-CDS) clusters are supported"); - EXPECT_NO_THROW(Utility::checkCluster("prefix", "foo", cm, true)); + EXPECT_EQ(Utility::checkCluster("prefix", "foo", cm, false).status().message(), + "prefix: invalid cluster 'foo': currently only " + "static (non-CDS) clusters are supported"); + EXPECT_TRUE(Utility::checkCluster("prefix", "foo", cm, true).ok()); // Validate that bootstrap cluster does not throw any exceptions. ON_CALL(*cm.active_clusters_["foo"]->info_, addedViaApi()).WillByDefault(Return(false)); - EXPECT_NO_THROW(Utility::checkCluster("prefix", "foo", cm, true)); - EXPECT_NO_THROW(Utility::checkCluster("prefix", "foo", cm, false)); + EXPECT_TRUE(Utility::checkCluster("prefix", "foo", cm, true).ok()); + EXPECT_TRUE(Utility::checkCluster("prefix", "foo", cm, false).ok()); } // Validates getGrpcControlPlane() functionality. diff --git a/test/common/event/dispatcher_impl_test.cc b/test/common/event/dispatcher_impl_test.cc index 3533be15931af..ecf8cb1de6f87 100644 --- a/test/common/event/dispatcher_impl_test.cc +++ b/test/common/event/dispatcher_impl_test.cc @@ -1377,8 +1377,8 @@ class TimerUtilsTest : public testing::Test { TEST_F(TimerUtilsTest, TimerNegativeValueThrows) { timeval tv; const int negative_sample = -1; - EXPECT_THROW_WITH_MESSAGE( - TimerUtils::durationToTimeval(std::chrono::seconds(negative_sample), tv), EnvoyException, + EXPECT_ENVOY_BUG( + TimerUtils::durationToTimeval(std::chrono::seconds(negative_sample), tv), fmt::format("Negative duration passed to durationToTimeval(): {}", negative_sample)); } diff --git a/test/common/formatter/substitution_formatter_test.cc b/test/common/formatter/substitution_formatter_test.cc index 8d32a486dfad1..8eab441447b55 100644 --- a/test/common/formatter/substitution_formatter_test.cc +++ b/test/common/formatter/substitution_formatter_test.cc @@ -540,8 +540,7 @@ TEST(SubstitutionFormatterTest, streamInfoFormatter) { { StreamInfoFormatter response_flags_format("RESPONSE_FLAGS"); - ON_CALL(stream_info, hasResponseFlag(StreamInfo::ResponseFlag::LocalReset)) - .WillByDefault(Return(true)); + stream_info.setResponseFlag(StreamInfo::CoreResponseFlag::LocalReset); EXPECT_EQ("LR", response_flags_format.formatWithContext({}, stream_info)); EXPECT_THAT(response_flags_format.formatValueWithContext({}, stream_info), ProtoEq(ValueUtil::stringValue("LR"))); @@ -549,8 +548,7 @@ TEST(SubstitutionFormatterTest, streamInfoFormatter) { { StreamInfoFormatter response_flags_format("RESPONSE_FLAGS_LONG"); - ON_CALL(stream_info, hasResponseFlag(StreamInfo::ResponseFlag::LocalReset)) - .WillByDefault(Return(true)); + stream_info.setResponseFlag(StreamInfo::CoreResponseFlag::LocalReset); EXPECT_EQ("LocalReset", response_flags_format.formatWithContext({}, stream_info)); EXPECT_THAT(response_flags_format.formatValueWithContext({}, stream_info), ProtoEq(ValueUtil::stringValue("LocalReset"))); @@ -796,7 +794,14 @@ TEST(SubstitutionFormatterTest, streamInfoFormatter) { EXPECT_THAT(upstream_format.formatValueWithContext({}, stream_info), ProtoEq(ValueUtil::numberValue(id))); } - + { + StreamInfoFormatter upstream_format("UPSTREAM_CONNECTION_ID"); + uint64_t id = 1234; + stream_info.upstreamInfo()->setUpstreamConnectionId(id); + EXPECT_EQ("1234", upstream_format.formatWithContext({}, stream_info)); + EXPECT_THAT(upstream_format.formatValueWithContext({}, stream_info), + ProtoEq(ValueUtil::numberValue(id))); + } { StreamInfoFormatter upstream_format("STREAM_ID"); diff --git a/test/common/http/codec_impl_fuzz_test.cc b/test/common/http/codec_impl_fuzz_test.cc index 6101a2ed88c9f..046dfd7fd9c2a 100644 --- a/test/common/http/codec_impl_fuzz_test.cc +++ b/test/common/http/codec_impl_fuzz_test.cc @@ -79,7 +79,8 @@ envoy::config::core::v3::Http2ProtocolOptions fromHttp2Settings(const test::common::http::Http2Settings& settings) { envoy::config::core::v3::Http2ProtocolOptions options( ::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions())); + envoy::config::core::v3::Http2ProtocolOptions()) + .value()); // We apply an offset and modulo interpretation to settings to ensure that // they are valid. Rejecting invalid settings is orthogonal to the fuzzed // code. diff --git a/test/common/http/conn_manager_impl_test.cc b/test/common/http/conn_manager_impl_test.cc index 7bac6ac9027b3..7f9f1f897d52f 100644 --- a/test/common/http/conn_manager_impl_test.cc +++ b/test/common/http/conn_manager_impl_test.cc @@ -89,6 +89,85 @@ TEST_F(HttpConnectionManagerImplTest, HeaderOnlyRequestAndResponse) { EXPECT_EQ(1U, listener_stats_.downstream_rq_completed_.value()); } +// Similar to HeaderOnlyRequestAndResponse but uses newStreamHandle and has +// lifetime checks. +TEST_F(HttpConnectionManagerImplTest, HandleLifetime) { + setup(false, "envoy-custom-server", false); + Http::RequestDecoderHandlePtr decoder_handle; + + // Store the basic request encoder during filter chain setup. + std::shared_ptr filter(new NiceMock()); + + EXPECT_CALL(*filter, decodeHeaders(_, true)) + .Times(2) + .WillRepeatedly(Invoke([&](RequestHeaderMap& headers, bool) -> FilterHeadersStatus { + EXPECT_NE(nullptr, headers.ForwardedFor()); + EXPECT_EQ("http", headers.getForwardedProtoValue()); + if (headers.Path()->value() == "/healthcheck") { + filter->callbacks_->streamInfo().healthCheck(true); + } + + return FilterHeadersStatus::StopIteration; + })); + + EXPECT_CALL(*filter, setDecoderFilterCallbacks(_)).Times(2); + + EXPECT_CALL(filter_factory_, createFilterChain(_)) + .Times(2) + .WillRepeatedly(Invoke([&](FilterChainManager& manager) -> bool { + auto factory = createDecoderFilterFactoryCb(filter); + manager.applyFilterFactoryCb({}, factory); + return true; + })); + + EXPECT_CALL(filter_callbacks_.connection_.dispatcher_, deferredDelete_(_)).Times(2); + + // When dispatch is called on the codec, we pretend to get a new stream and then fire a headers + // only request into it. Then we respond into the filter. + EXPECT_CALL(*codec_, dispatch(_)) + .Times(2) + .WillRepeatedly(Invoke([&](Buffer::Instance& data) -> Http::Status { + decoder_handle = conn_manager_->newStreamHandle(response_encoder_); + EXPECT_TRUE(decoder_handle->get().has_value()); + decoder_ = &decoder_handle->get().value().get(); + + // Test not charging stats on the second call. + if (data.length() == 4) { + RequestHeaderMapPtr headers{new TestRequestHeaderMapImpl{ + {":authority", "host"}, {":path", "/"}, {":method", "GET"}}}; + decoder_->decodeHeaders(std::move(headers), true); + } else { + RequestHeaderMapPtr headers{new TestRequestHeaderMapImpl{ + {":authority", "host"}, {":path", "/healthcheck"}, {":method", "GET"}}}; + decoder_->decodeHeaders(std::move(headers), true); + } + + ResponseHeaderMapPtr response_headers{new TestResponseHeaderMapImpl{{":status", "200"}}}; + filter->callbacks_->streamInfo().setResponseCodeDetails(""); + filter->callbacks_->encodeHeaders(std::move(response_headers), true, "details"); + response_encoder_.stream_.codec_callbacks_->onCodecEncodeComplete(); + + // Drain 2 so that on the 2nd iteration we will hit zero. + data.drain(2); + return Http::okStatus(); + })); + + // Kick off the incoming data. Use extra data which should cause a redispatch. + Buffer::OwnedImpl fake_input("1234"); + conn_manager_->onData(fake_input, false); + + // At the end of this, the handle is on the deferred delete list but not + // deleted. It should be invalid. + EXPECT_FALSE(decoder_handle->get().has_value()); + filter_callbacks_.connection_.dispatcher_.clearDeferredDeleteList(); + EXPECT_FALSE(decoder_handle->get().has_value()); + + EXPECT_EQ(1U, stats_.named_.downstream_rq_2xx_.value()); + EXPECT_EQ(1U, listener_stats_.downstream_rq_2xx_.value()); + EXPECT_EQ(1U, stats_.named_.downstream_rq_completed_.value()); + EXPECT_EQ(1U, listener_stats_.downstream_rq_completed_.value()); +} + TEST_F(HttpConnectionManagerImplTest, HeaderOnlyRequestAndResponseWithEarlyHeaderMutation) { setup(false, "envoy-custom-server", false); @@ -2253,14 +2332,14 @@ TEST_F(HttpConnectionManagerImplTest, TestRemoteDownstreamDisconnectAccessLog) { })); EXPECT_CALL(*handler, log(_, _)) - .WillOnce(Invoke([](const Formatter::HttpFormatterContext&, - const StreamInfo::StreamInfo& stream_info) { - EXPECT_FALSE(stream_info.responseCode()); - EXPECT_TRUE(stream_info.hasAnyResponseFlag()); - EXPECT_TRUE( - stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DownstreamConnectionTermination)); - EXPECT_EQ("downstream_remote_disconnect", stream_info.responseCodeDetails().value()); - })); + .WillOnce(Invoke( + [](const Formatter::HttpFormatterContext&, const StreamInfo::StreamInfo& stream_info) { + EXPECT_FALSE(stream_info.responseCode()); + EXPECT_TRUE(stream_info.hasAnyResponseFlag()); + EXPECT_TRUE(stream_info.hasResponseFlag( + StreamInfo::CoreResponseFlag::DownstreamConnectionTermination)); + EXPECT_EQ("downstream_remote_disconnect", stream_info.responseCodeDetails().value()); + })); EXPECT_CALL(*codec_, dispatch(_)) .WillRepeatedly(Invoke([&](Buffer::Instance& data) -> Http::Status { @@ -2966,12 +3045,12 @@ TEST_F(HttpConnectionManagerImplTest, TestStreamIdleAccessLog) { EXPECT_CALL(response_encoder_, encodeData(_, true)).WillOnce(AddBufferToString(&response_body)); EXPECT_CALL(*handler, log(_, _)) - .WillOnce(Invoke( - [](const Formatter::HttpFormatterContext&, const StreamInfo::StreamInfo& stream_info) { - EXPECT_TRUE(stream_info.responseCode()); - EXPECT_TRUE(stream_info.hasAnyResponseFlag()); - EXPECT_TRUE(stream_info.hasResponseFlag(StreamInfo::ResponseFlag::StreamIdleTimeout)); - })); + .WillOnce(Invoke([](const Formatter::HttpFormatterContext&, + const StreamInfo::StreamInfo& stream_info) { + EXPECT_TRUE(stream_info.responseCode()); + EXPECT_TRUE(stream_info.hasAnyResponseFlag()); + EXPECT_TRUE(stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::StreamIdleTimeout)); + })); EXPECT_CALL(filter_factory_, createFilterChain(_)) .WillOnce(Invoke([&](FilterChainManager& manager) -> bool { @@ -4283,7 +4362,7 @@ class ProxyStatusTest : public HttpConnectionManagerImplTest { sendRequestHeadersAndData(); } const ResponseHeaderMap* - sendRequestWith(int status, StreamInfo::ResponseFlag response_flag, std::string details, + sendRequestWith(int status, StreamInfo::CoreResponseFlag response_flag, std::string details, absl::optional proxy_status = absl::nullopt) { auto response_headers = new TestResponseHeaderMapImpl{{":status", std::to_string(status)}}; if (proxy_status.has_value()) { @@ -4303,7 +4382,7 @@ TEST_F(ProxyStatusTest, NoPopulateProxyStatus) { initialize(); const ResponseHeaderMap* altered_headers = - sendRequestWith(403, StreamInfo::ResponseFlag::FailedLocalHealthCheck, "foo"); + sendRequestWith(403, StreamInfo::CoreResponseFlag::FailedLocalHealthCheck, "foo"); ASSERT_TRUE(altered_headers); ASSERT_FALSE(altered_headers->ProxyStatus()); EXPECT_EQ(altered_headers->getStatusValue(), "403"); // unchanged from request. @@ -4318,7 +4397,7 @@ TEST_F(ProxyStatusTest, PopulateProxyStatusWithDetailsAndResponseCodeAndServerNa initialize(); const ResponseHeaderMap* altered_headers = - sendRequestWith(403, StreamInfo::ResponseFlag::FailedLocalHealthCheck, /*details=*/"foo"); + sendRequestWith(403, StreamInfo::CoreResponseFlag::FailedLocalHealthCheck, /*details=*/"foo"); ASSERT_TRUE(altered_headers); ASSERT_TRUE(altered_headers->ProxyStatus()); @@ -4340,7 +4419,7 @@ TEST_F(ProxyStatusTest, PopulateProxyStatusWithDetailsAndResponseCode) { initialize(); const ResponseHeaderMap* altered_headers = - sendRequestWith(403, StreamInfo::ResponseFlag::UpstreamRequestTimeout, /*details=*/"bar"); + sendRequestWith(403, StreamInfo::CoreResponseFlag::UpstreamRequestTimeout, /*details=*/"bar"); ASSERT_TRUE(altered_headers); ASSERT_TRUE(altered_headers->ProxyStatus()); @@ -4364,7 +4443,7 @@ TEST_F(ProxyStatusTest, PopulateProxyStatusWithDetails) { initialize(); const ResponseHeaderMap* altered_headers = - sendRequestWith(403, StreamInfo::ResponseFlag::UpstreamRequestTimeout, /*details=*/"bar"); + sendRequestWith(403, StreamInfo::CoreResponseFlag::UpstreamRequestTimeout, /*details=*/"bar"); ASSERT_TRUE(altered_headers); ASSERT_TRUE(altered_headers->ProxyStatus()); @@ -4387,7 +4466,7 @@ TEST_F(ProxyStatusTest, PopulateProxyStatusWithoutDetails) { initialize(); const ResponseHeaderMap* altered_headers = - sendRequestWith(403, StreamInfo::ResponseFlag::UpstreamRequestTimeout, /*details=*/"baz"); + sendRequestWith(403, StreamInfo::CoreResponseFlag::UpstreamRequestTimeout, /*details=*/"baz"); ASSERT_TRUE(altered_headers); ASSERT_TRUE(altered_headers->ProxyStatus()); @@ -4410,7 +4489,7 @@ TEST_F(ProxyStatusTest, PopulateProxyStatusAppendToPreviousValue) { initialize(); const ResponseHeaderMap* altered_headers = - sendRequestWith(403, StreamInfo::ResponseFlag::UpstreamRequestTimeout, /*details=*/"baz", + sendRequestWith(403, StreamInfo::CoreResponseFlag::UpstreamRequestTimeout, /*details=*/"baz", /*proxy_status=*/"SomeCDN"); ASSERT_TRUE(altered_headers); diff --git a/test/common/http/conn_manager_impl_test_2.cc b/test/common/http/conn_manager_impl_test_2.cc index 431bc6d843a8e..287507afa2a11 100644 --- a/test/common/http/conn_manager_impl_test_2.cc +++ b/test/common/http/conn_manager_impl_test_2.cc @@ -228,12 +228,13 @@ TEST_F(HttpConnectionManagerImplTest, TestDownstreamProtocolErrorAccessLog) { setup(false, ""); EXPECT_CALL(*handler, log(_, _)) - .WillOnce(Invoke([](const Formatter::HttpFormatterContext&, - const StreamInfo::StreamInfo& stream_info) { - EXPECT_FALSE(stream_info.responseCode()); - EXPECT_TRUE(stream_info.hasAnyResponseFlag()); - EXPECT_TRUE(stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DownstreamProtocolError)); - })); + .WillOnce(Invoke( + [](const Formatter::HttpFormatterContext&, const StreamInfo::StreamInfo& stream_info) { + EXPECT_FALSE(stream_info.responseCode()); + EXPECT_TRUE(stream_info.hasAnyResponseFlag()); + EXPECT_TRUE( + stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DownstreamProtocolError)); + })); EXPECT_CALL(*codec_, dispatch(_)).WillRepeatedly(Invoke([&](Buffer::Instance&) -> Http::Status { conn_manager_->newStream(response_encoder_); @@ -261,12 +262,13 @@ TEST_F(HttpConnectionManagerImplTest, TestDownstreamProtocolErrorAfterHeadersAcc })); EXPECT_CALL(*handler, log(_, _)) - .WillOnce(Invoke([](const Formatter::HttpFormatterContext&, - const StreamInfo::StreamInfo& stream_info) { - EXPECT_FALSE(stream_info.responseCode()); - EXPECT_TRUE(stream_info.hasAnyResponseFlag()); - EXPECT_TRUE(stream_info.hasResponseFlag(StreamInfo::ResponseFlag::DownstreamProtocolError)); - })); + .WillOnce(Invoke( + [](const Formatter::HttpFormatterContext&, const StreamInfo::StreamInfo& stream_info) { + EXPECT_FALSE(stream_info.responseCode()); + EXPECT_TRUE(stream_info.hasAnyResponseFlag()); + EXPECT_TRUE( + stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::DownstreamProtocolError)); + })); EXPECT_CALL(*codec_, dispatch(_)).WillRepeatedly(Invoke([&](Buffer::Instance&) -> Http::Status { decoder_ = &conn_manager_->newStream(response_encoder_); @@ -314,7 +316,7 @@ TEST_F(HttpConnectionManagerImplTest, FrameFloodError) { conn_manager_->onData(fake_input, false)); EXPECT_TRUE(filter_callbacks_.connection_.streamInfo().hasResponseFlag( - StreamInfo::ResponseFlag::DownstreamProtocolError)); + StreamInfo::CoreResponseFlag::DownstreamProtocolError)); } TEST_F(HttpConnectionManagerImplTest, EnvoyOverloadError) { @@ -347,7 +349,7 @@ TEST_F(HttpConnectionManagerImplTest, EnvoyOverloadError) { conn_manager_->onData(fake_input, false); EXPECT_TRUE(filter_callbacks_.connection_.streamInfo().hasResponseFlag( - StreamInfo::ResponseFlag::OverloadManager)); + StreamInfo::CoreResponseFlag::OverloadManager)); EXPECT_EQ(1U, stats_.named_.downstream_rq_overload_close_.value()); } @@ -420,13 +422,13 @@ TEST_F(HttpConnectionManagerImplTest, ConnectionDurationResponseFlag) { EXPECT_CALL(filter_callbacks_.connection_, close(Network::ConnectionCloseType::FlushWrite, _)); filter_callbacks_.connection_.streamInfo().setResponseFlag( - StreamInfo::ResponseFlag::DurationTimeout); + StreamInfo::CoreResponseFlag::DurationTimeout); EXPECT_CALL(*connection_duration_timer, disableTimer()); connection_duration_timer->invokeCallback(); EXPECT_TRUE(filter_callbacks_.connection_.streamInfo().hasResponseFlag( - StreamInfo::ResponseFlag::DurationTimeout)); + StreamInfo::CoreResponseFlag::DurationTimeout)); EXPECT_EQ(1U, stats_.named_.downstream_cx_max_duration_reached_.value()); } diff --git a/test/common/http/conn_manager_impl_test_base.cc b/test/common/http/conn_manager_impl_test_base.cc index da6d8d8aa9d7e..663c0eddee4b0 100644 --- a/test/common/http/conn_manager_impl_test_base.cc +++ b/test/common/http/conn_manager_impl_test_base.cc @@ -231,8 +231,8 @@ void HttpConnectionManagerImplMixin::sendRequestHeadersAndData() { } ResponseHeaderMap* HttpConnectionManagerImplMixin::sendResponseHeaders( - ResponseHeaderMapPtr&& response_headers, absl::optional response_flag, - std::string response_code_details) { + ResponseHeaderMapPtr&& response_headers, + absl::optional response_flag, std::string response_code_details) { ResponseHeaderMap* altered_response_headers = nullptr; EXPECT_CALL(*encoder_filters_[0], encodeHeaders(_, _)) diff --git a/test/common/http/conn_manager_impl_test_base.h b/test/common/http/conn_manager_impl_test_base.h index ddccd0a773210..0ebaebd46bd13 100644 --- a/test/common/http/conn_manager_impl_test_base.h +++ b/test/common/http/conn_manager_impl_test_base.h @@ -53,7 +53,7 @@ class HttpConnectionManagerImplMixin : public ConnectionManagerConfig { void sendRequestHeadersAndData(); ResponseHeaderMap* sendResponseHeaders(ResponseHeaderMapPtr&& response_headers, - absl::optional response_flag = absl::nullopt, + absl::optional response_flag = absl::nullopt, std::string response_code_details = "details"); void expectOnDestroy(bool deferred = true); void doRemoteClose(bool deferred = true); diff --git a/test/common/http/conn_pool_grid_test.cc b/test/common/http/conn_pool_grid_test.cc index a52a6545ec8e0..afb1fb2c9a70f 100644 --- a/test/common/http/conn_pool_grid_test.cc +++ b/test/common/http/conn_pool_grid_test.cc @@ -67,8 +67,12 @@ class ConnectivityGridForTest : public ConnectivityGrid { "reason", host()); return nullptr; } + if (second_pool_immediate_success_) { + second_pool_immediate_success_ = false; + immediate_success_ = true; + } callbacks_.push_back(&callbacks); - return &cancel_; + return cancel_; })); if (pools_.size() == 1) { EXPECT_CALL(*first(), protocolDescription()) @@ -111,9 +115,10 @@ class ConnectivityGridForTest : public ConnectivityGrid { NiceMock* encoder_; void setDestroying() { destroying_ = true; } std::vector callbacks_; - NiceMock cancel_; + NiceMock* cancel_; bool immediate_success_{}; bool immediate_failure_{}; + bool second_pool_immediate_success_{}; }; namespace { @@ -142,6 +147,7 @@ class ConnectivityGridTest : public Event::TestUsingSimulatedTime, public testin Upstream::ResourcePriority::Default, socket_options_, transport_socket_options_, state_, simTime(), alternate_protocols_, options_, quic_stat_names_, *store_.rootScope(), *quic_connection_persistent_info_); + grid_->cancel_ = &cancel_; host_ = grid_->host(); grid_->info_ = &info_; grid_->encoder_ = &encoder_; @@ -179,6 +185,7 @@ class ConnectivityGridTest : public Event::TestUsingSimulatedTime, public testin Stats::IsolatedStoreImpl store_; Quic::QuicStatNames quic_stat_names_; PersistentQuicInfoPtr quic_connection_persistent_info_; + NiceMock cancel_; std::unique_ptr grid_; Upstream::HostDescriptionConstSharedPtr host_; @@ -549,7 +556,7 @@ TEST_F(ConnectivityGridTest, TestCancel) { EXPECT_NE(grid_->first(), nullptr); // cancel should be passed through the WrapperCallbacks to the connection pool. - EXPECT_CALL(grid_->cancel_, cancel(_)); + EXPECT_CALL(*grid_->cancel_, cancel(_)); cancel->cancel(Envoy::ConnectionPool::CancelPolicy::CloseExcess); } @@ -868,7 +875,7 @@ TEST_F(ConnectivityGridTest, Http3FailedRecentlyThenSucceeds) { ASSERT_NE(grid_->callbacks(0), nullptr); ASSERT_NE(grid_->callbacks(1), nullptr); EXPECT_CALL(callbacks_.pool_ready_, ready()); - EXPECT_CALL(grid_->cancel_, cancel(_)); + EXPECT_CALL(*grid_->cancel_, cancel(_)); grid_->callbacks(0)->onPoolReady(encoder_, host_, info_, absl::nullopt); // Getting onPoolReady() from HTTP/3 pool doesn't change H3 status. EXPECT_TRUE(ConnectivityGridForTest::hasHttp3FailedRecently(*grid_)); @@ -902,6 +909,22 @@ TEST_F(ConnectivityGridTest, Http3FailedRecentlyThenFailsAgain) { EXPECT_TRUE(grid_->isHttp3Broken()); } +TEST_F(ConnectivityGridTest, Http3FailedH2SuceedsInline) { + initialize(); + addHttp3AlternateProtocol(); + grid_->onZeroRttHandshakeFailed(); + EXPECT_TRUE(ConnectivityGridForTest::hasHttp3FailedRecently(*grid_)); + EXPECT_EQ(grid_->first(), nullptr); + + // Force H3 to have no immediate change, but H2 to immediately succeed. + grid_->second_pool_immediate_success_ = true; + // Because the second pool immediately succeeded, newStream should return nullptr. + EXPECT_EQ(grid_->newStream(decoder_, callbacks_, + {/*can_send_early_data_=*/true, + /*can_use_http3_=*/true}), + nullptr); +} + #ifdef ENVOY_ENABLE_QUIC } // namespace diff --git a/test/common/http/http2/codec_impl_test_util.h b/test/common/http/http2/codec_impl_test_util.h index cd93fe8f9c60d..b98cdd410a6ff 100644 --- a/test/common/http/http2/codec_impl_test_util.h +++ b/test/common/http/http2/codec_impl_test_util.h @@ -40,20 +40,17 @@ class TestCodecSettingsProvider { protected: // Stores SETTINGS parameters contained in |settings_frame| to make them available via // getRemoteSettingsParameterValue(). - void onSettingsFrame(const nghttp2_settings& settings_frame) { - for (uint32_t i = 0; i < settings_frame.niv; ++i) { - auto result = settings_.insert( - std::make_pair(settings_frame.iv[i].settings_id, settings_frame.iv[i].value)); + void onSettingsFrame(absl::Span settings) { + for (const auto& [id, value] : settings) { + auto result = settings_.insert(std::make_pair(id, value)); // It is possible to have duplicate settings parameters, each new parameter replaces any // existing value. // https://tools.ietf.org/html/rfc7540#section-6.5 if (!result.second) { - ENVOY_LOG_MISC(debug, "Duplicated settings parameter {} with value {}", - settings_frame.iv[i].settings_id, settings_frame.iv[i].value); + ENVOY_LOG_MISC(debug, "Duplicated settings parameter {} with value {}", id, value); settings_.erase(result.first); // Guaranteed success here. - settings_.insert( - std::make_pair(settings_frame.iv[i].settings_id, settings_frame.iv[i].value)); + settings_.insert(std::make_pair(id, value)); } } } @@ -96,7 +93,9 @@ class TestServerConnectionImpl : public TestCodecStatsProvider, protected: // Overrides ServerConnectionImpl::onSettings(). - void onSettings(const nghttp2_settings& settings) override { onSettingsFrame(settings); } + void onSettings(absl::Span settings) override { + onSettingsFrame(settings); + } testing::NiceMock random_; }; @@ -132,7 +131,9 @@ class TestClientConnectionImpl : public TestCodecStatsProvider, protected: // Overrides ClientConnectionImpl::onSettings(). - void onSettings(const nghttp2_settings& settings) override { onSettingsFrame(settings); } + void onSettings(absl::Span settings) override { + onSettingsFrame(settings); + } }; } // namespace Http2 diff --git a/test/common/http/http2/frame_replay.cc b/test/common/http/http2/frame_replay.cc index c2755a683d403..c8436c4219b2f 100644 --- a/test/common/http/http2/frame_replay.cc +++ b/test/common/http/http2/frame_replay.cc @@ -62,7 +62,8 @@ void FrameUtils::fixupHeaders(Frame& frame) { CodecFrameInjector::CodecFrameInjector(const std::string& injector_name) : options_(::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions())), + envoy::config::core::v3::Http2ProtocolOptions()) + .value()), injector_name_(injector_name) {} ClientCodecFrameInjector::ClientCodecFrameInjector() : CodecFrameInjector("server") { diff --git a/test/common/http/http2/http2_connection_fuzz_test.cc b/test/common/http/http2/http2_connection_fuzz_test.cc index 02c413ace42d2..c9a8561538cc8 100644 --- a/test/common/http/http2/http2_connection_fuzz_test.cc +++ b/test/common/http/http2/http2_connection_fuzz_test.cc @@ -165,7 +165,8 @@ Http2Frame pbToH2Frame(nghttp2_hd_deflater* deflater, envoy::config::core::v3::Http2ProtocolOptions http2Settings() { envoy::config::core::v3::Http2ProtocolOptions options( ::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions())); + envoy::config::core::v3::Http2ProtocolOptions()) + .value()); options.mutable_hpack_table_size()->set_value(MAX_HD_TABLE_BUF_SIZE); options.set_allow_metadata(true); diff --git a/test/common/http/http2/protocol_constraints_test.cc b/test/common/http/http2/protocol_constraints_test.cc index 3d715c7db52c3..4aaf7901d68c7 100644 --- a/test/common/http/http2/protocol_constraints_test.cc +++ b/test/common/http/http2/protocol_constraints_test.cc @@ -94,13 +94,13 @@ TEST_F(ProtocolConstraintsTest, OutboundFrameFloodStatusIsIdempotent) { TEST_F(ProtocolConstraintsTest, InboundZeroLenData) { options_.mutable_max_consecutive_inbound_frames_with_empty_payload()->set_value(2); ProtocolConstraints constraints(http2CodecStats(), options_); - uint8_t type = NGHTTP2_DATA; - size_t length = 0; - uint8_t flags = 0; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE( - isInboundFramesWithEmptyPayloadError(constraints.trackInboundFrames(length, type, flags, 0))); + const uint8_t type = NGHTTP2_DATA; + const bool end_stream = false; + const bool is_empty = true; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(isInboundFramesWithEmptyPayloadError( + constraints.trackInboundFrame(type, end_stream, is_empty))); EXPECT_TRUE(isInboundFramesWithEmptyPayloadError(constraints.status())); EXPECT_EQ(1, stats_store_.counter("http2.inbound_empty_frames_flood").value()); } @@ -113,13 +113,13 @@ TEST_F(ProtocolConstraintsTest, OutboundAndInboundFrameFloodStatusIsIdempotent) options_.mutable_max_consecutive_inbound_frames_with_empty_payload()->set_value(2); ProtocolConstraints constraints(http2CodecStats(), options_); // First trigger inbound frame flood - uint8_t type = NGHTTP2_DATA; - size_t length = 0; - uint8_t flags = 0; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE( - isInboundFramesWithEmptyPayloadError(constraints.trackInboundFrames(length, type, flags, 0))); + const uint8_t type = NGHTTP2_DATA; + const bool end_stream = false; + const bool is_empty = true; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(isInboundFramesWithEmptyPayloadError( + constraints.trackInboundFrame(type, end_stream, is_empty))); // Then trigger outbound control flood constraints.incrementOutboundFrameCount(true); @@ -133,13 +133,13 @@ TEST_F(ProtocolConstraintsTest, OutboundAndInboundFrameFloodStatusIsIdempotent) TEST_F(ProtocolConstraintsTest, InboundZeroLenDataWithPadding) { options_.mutable_max_consecutive_inbound_frames_with_empty_payload()->set_value(2); ProtocolConstraints constraints(http2CodecStats(), options_); - uint8_t type = NGHTTP2_DATA; - size_t length = 8; - uint8_t flags = 0; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 8).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 8).ok()); - EXPECT_TRUE( - isInboundFramesWithEmptyPayloadError(constraints.trackInboundFrames(length, type, flags, 8))); + const uint8_t type = NGHTTP2_DATA; + const bool end_stream = false; + const bool is_empty = true; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(isInboundFramesWithEmptyPayloadError( + constraints.trackInboundFrame(type, end_stream, is_empty))); EXPECT_TRUE(isInboundFramesWithEmptyPayloadError(constraints.status())); EXPECT_EQ(1, stats_store_.counter("http2.inbound_empty_frames_flood").value()); } @@ -147,18 +147,18 @@ TEST_F(ProtocolConstraintsTest, InboundZeroLenDataWithPadding) { TEST_F(ProtocolConstraintsTest, InboundZeroLenDataEndStreamResetCounter) { options_.mutable_max_consecutive_inbound_frames_with_empty_payload()->set_value(2); ProtocolConstraints constraints(http2CodecStats(), options_); - uint8_t type = NGHTTP2_DATA; - size_t length = 0; - uint8_t flags = 0; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - flags = NGHTTP2_FLAG_END_STREAM; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - flags = 0; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE( - isInboundFramesWithEmptyPayloadError(constraints.trackInboundFrames(length, type, flags, 0))); + const uint8_t type = NGHTTP2_DATA; + const bool is_empty = true; + bool end_stream = false; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + end_stream = true; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + end_stream = false; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(isInboundFramesWithEmptyPayloadError( + constraints.trackInboundFrame(type, end_stream, is_empty))); EXPECT_TRUE(isInboundFramesWithEmptyPayloadError(constraints.status())); EXPECT_EQ(1, stats_store_.counter("http2.inbound_empty_frames_flood").value()); } @@ -169,14 +169,14 @@ TEST_F(ProtocolConstraintsTest, Priority) { // Create one stream constraints.incrementOpenedStreamCount(); - size_t length = 5; - uint8_t type = NGHTTP2_PRIORITY; - uint8_t flags = 0; - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); - EXPECT_TRUE(isBufferFloodError(constraints.trackInboundFrames(length, type, flags, 0))); + const uint8_t type = NGHTTP2_PRIORITY; + const bool end_stream = false; + const bool is_empty = false; + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); + EXPECT_TRUE(isBufferFloodError(constraints.trackInboundFrame(type, end_stream, is_empty))); EXPECT_TRUE(isBufferFloodError(constraints.status())); EXPECT_EQ("Too many PRIORITY frames", constraints.status().message()); EXPECT_EQ(1, stats_store_.counter("http2.inbound_priority_frames_flood").value()); @@ -195,13 +195,13 @@ TEST_F(ProtocolConstraintsTest, WindowUpdate) { // max_inbound_window_update_frames_per_data_frame_sent_ * outbound_data_frames_` // formula 5 + 2 * (1 + 2 * 2) = 15 WINDOW_UPDATE frames should NOT fail constraint // check, but 16th should. - size_t length = 4; - uint8_t type = NGHTTP2_WINDOW_UPDATE; - uint8_t flags = 0; + const uint8_t type = NGHTTP2_WINDOW_UPDATE; + const bool end_stream = false; + const bool is_empty = false; for (uint32_t i = 0; i < 15; ++i) { - EXPECT_TRUE(constraints.trackInboundFrames(length, type, flags, 0).ok()); + EXPECT_TRUE(constraints.trackInboundFrame(type, end_stream, is_empty).ok()); } - EXPECT_TRUE(isBufferFloodError(constraints.trackInboundFrames(length, type, flags, 0))); + EXPECT_TRUE(isBufferFloodError(constraints.trackInboundFrame(type, end_stream, is_empty))); EXPECT_TRUE(isBufferFloodError(constraints.status())); EXPECT_EQ("Too many WINDOW_UPDATE frames", constraints.status().message()); EXPECT_EQ(1, stats_store_.counter("http2.inbound_window_update_frames_flood").value()); diff --git a/test/common/http/utility_fuzz_test.cc b/test/common/http/utility_fuzz_test.cc index 6c529b35642b4..a10eda25d0a89 100644 --- a/test/common/http/utility_fuzz_test.cc +++ b/test/common/http/utility_fuzz_test.cc @@ -86,10 +86,9 @@ DEFINE_PROTO_FUZZER(const test::common::http::UtilityTestCase& input) { } case test::common::http::UtilityTestCase::kInitializeAndValidate: { const auto& options = input.initialize_and_validate(); - try { - Http2::Utility::initializeAndValidateOptions(options); - } catch (EnvoyException& e) { - absl::string_view msg = e.what(); + auto options_or_error = Http2::Utility::initializeAndValidateOptions(options); + if (options_or_error.status().ok()) { + absl::string_view msg = options_or_error.status().message(); // initializeAndValidateOptions throws exceptions for 4 different reasons due to malformed // settings, so check for them and allow any other exceptions through if (absl::StartsWith( @@ -103,9 +102,9 @@ DEFINE_PROTO_FUZZER(const test::common::http::UtilityTestCase& input) { absl::EndsWith( msg, "HTTP/2 SETTINGS parameter(s) can not be configured through both named and " "custom parameters")) { - ENVOY_LOG_MISC(trace, "Caught exception {} in initializeAndValidateOptions test", e.what()); + ENVOY_LOG_MISC(trace, "Ignoring error {} in initializeAndValidateOptions", msg); } else { - throw EnvoyException(e.what()); + throw EnvoyException(std::string(msg)); } } break; diff --git a/test/common/http/utility_test.cc b/test/common/http/utility_test.cc index 384ba03471d7f..35b67cd933293 100644 --- a/test/common/http/utility_test.cc +++ b/test/common/http/utility_test.cc @@ -527,23 +527,12 @@ TEST(HttpUtility, updateAuthority) { // Test that we only append to x-forwarded-host if it is not already present. { - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues({{"envoy.reloadable_features.append_xfh_idempotent", "true"}}); TestRequestHeaderMapImpl headers{{":authority", "dns.name"}, {"x-forwarded-host", "host.com,dns.name"}}; Utility::updateAuthority(headers, "newhost.com", true); EXPECT_EQ("newhost.com", headers.get_(":authority")); EXPECT_EQ("host.com,dns.name", headers.get_("x-forwarded-host")); } - { - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues({{"envoy.reloadable_features.append_xfh_idempotent", "false"}}); - TestRequestHeaderMapImpl headers{{":authority", "dns.name"}, - {"x-forwarded-host", "host.com,dns.name"}}; - Utility::updateAuthority(headers, "newhost.com", true); - EXPECT_EQ("newhost.com", headers.get_(":authority")); - EXPECT_EQ("host.com,dns.name,dns.name", headers.get_("x-forwarded-host")); - } } TEST(HttpUtility, createSslRedirectPath) { @@ -558,7 +547,7 @@ namespace { envoy::config::core::v3::Http2ProtocolOptions parseHttp2OptionsFromV3Yaml(const std::string& yaml) { envoy::config::core::v3::Http2ProtocolOptions http2_options; TestUtility::loadFromYamlAndValidate(yaml, http2_options); - return ::Envoy::Http2::Utility::initializeAndValidateOptions(http2_options); + return ::Envoy::Http2::Utility::initializeAndValidateOptions(http2_options).value(); } } // namespace @@ -605,12 +594,14 @@ TEST(HttpUtility, ValidateStreamErrors) { // Both false, the result should be false. envoy::config::core::v3::Http2ProtocolOptions http2_options; EXPECT_FALSE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options) + .value() .override_stream_error_on_invalid_http_message() .value()); // If the new value is not present, the legacy value is respected. http2_options.set_stream_error_on_invalid_http_messaging(true); EXPECT_TRUE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options) + .value() .override_stream_error_on_invalid_http_message() .value()); @@ -618,6 +609,7 @@ TEST(HttpUtility, ValidateStreamErrors) { http2_options.mutable_override_stream_error_on_invalid_http_message()->set_value(true); http2_options.set_stream_error_on_invalid_http_messaging(false); EXPECT_TRUE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options) + .value() .override_stream_error_on_invalid_http_message() .value()); @@ -625,6 +617,7 @@ TEST(HttpUtility, ValidateStreamErrors) { http2_options.mutable_override_stream_error_on_invalid_http_message()->set_value(false); http2_options.set_stream_error_on_invalid_http_messaging(true); EXPECT_FALSE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options) + .value() .override_stream_error_on_invalid_http_message() .value()); } @@ -633,6 +626,7 @@ TEST(HttpUtility, ValidateStreamErrorsWithHcm) { envoy::config::core::v3::Http2ProtocolOptions http2_options; http2_options.set_stream_error_on_invalid_http_messaging(true); EXPECT_TRUE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options) + .value() .override_stream_error_on_invalid_http_message() .value()); @@ -640,10 +634,12 @@ TEST(HttpUtility, ValidateStreamErrorsWithHcm) { ProtobufWkt::BoolValue hcm_value; hcm_value.set_value(false); EXPECT_FALSE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options, true, hcm_value) + .value() .override_stream_error_on_invalid_http_message() .value()); // The HCM value will be ignored if initializeAndValidateOptions is told it is not present. EXPECT_TRUE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options, false, hcm_value) + .value() .override_stream_error_on_invalid_http_message() .value()); @@ -651,6 +647,7 @@ TEST(HttpUtility, ValidateStreamErrorsWithHcm) { // global one. http2_options.mutable_override_stream_error_on_invalid_http_message()->set_value(true); EXPECT_TRUE(Envoy::Http2::Utility::initializeAndValidateOptions(http2_options, true, hcm_value) + .value() .override_stream_error_on_invalid_http_message() .value()); } diff --git a/test/common/listener_manager/BUILD b/test/common/listener_manager/BUILD index 24c62c127ce92..dd452238d0b44 100644 --- a/test/common/listener_manager/BUILD +++ b/test/common/listener_manager/BUILD @@ -17,6 +17,25 @@ envoy_proto_library( srcs = ["config.proto"], ) +envoy_cc_test( + name = "listener_impl_test", + srcs = ["listener_impl_test.cc"], + data = [ + "internal_listener.yaml", + "internal_listener_missing_bootstrap.yaml", + ], + deps = [ + "//source/extensions/bootstrap/internal_listener:config", + "//source/extensions/filters/network/tcp_proxy:config", + "//source/extensions/listener_managers/validation_listener_manager:validation_listener_manager_lib", + "//source/server/config_validation:server_lib", + "//test/integration:http_integration_lib", + "//test/mocks/server:options_mocks", + "//test/test_common:test_runtime_lib", + "//test/test_common:utility_lib", + ], +) + envoy_cc_test_library( name = "listener_manager_impl_test_lib", hdrs = ["listener_manager_impl_test.h"], diff --git a/test/common/listener_manager/internal_listener.yaml b/test/common/listener_manager/internal_listener.yaml new file mode 100644 index 0000000000000..5b46df42ff330 --- /dev/null +++ b/test/common/listener_manager/internal_listener.yaml @@ -0,0 +1,29 @@ +# Regression test for https://github.com/envoyproxy/envoy/issues/28413 +static_resources: + listeners: + - name: singleton_internal_encap + internal_listener: {} + filter_chains: + - filters: + - name: tcp_proxy + typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.network.tcp_proxy.v3.TcpProxy + cluster: singleton_internal_encap + stat_prefix: encap_tcp_proxy + clusters: + - name: singleton_internal_encap + connect_timeout: 3600s + type: STATIC + load_assignment: + cluster_name: "singleton_internal_encap" + endpoints: + - lb_endpoints: + - endpoint: + address: + socket_address: + address: 0.0.0.0 + port_value: 19001 +bootstrap_extensions: +- name: envoy.bootstrap.internal_listener + typed_config: + "@type": "type.googleapis.com/envoy.extensions.bootstrap.internal_listener.v3.InternalListener" diff --git a/test/common/listener_manager/internal_listener_missing_bootstrap.yaml b/test/common/listener_manager/internal_listener_missing_bootstrap.yaml new file mode 100644 index 0000000000000..fc6603e97d5e1 --- /dev/null +++ b/test/common/listener_manager/internal_listener_missing_bootstrap.yaml @@ -0,0 +1,25 @@ +# Regression test for https://github.com/envoyproxy/envoy/issues/28413 +static_resources: + listeners: + - name: singleton_internal_encap + internal_listener: {} + filter_chains: + - filters: + - name: tcp_proxy + typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.network.tcp_proxy.v3.TcpProxy + cluster: singleton_internal_encap + stat_prefix: encap_tcp_proxy + clusters: + - name: singleton_internal_encap + connect_timeout: 3600s + type: STATIC + load_assignment: + cluster_name: "singleton_internal_encap" + endpoints: + - lb_endpoints: + - endpoint: + address: + socket_address: + address: 0.0.0.0 + port_value: 19001 diff --git a/test/common/listener_manager/listener_impl_test.cc b/test/common/listener_manager/listener_impl_test.cc new file mode 100644 index 0000000000000..e7a71541ebc7b --- /dev/null +++ b/test/common/listener_manager/listener_impl_test.cc @@ -0,0 +1,36 @@ +#include "envoy/network/address.h" + +#include "source/server/config_validation/server.h" + +#include "test/integration/server.h" +#include "test/mocks/server/options.h" +#include "test/test_common/environment.h" +#include "test/test_common/file_system_for_test.h" +#include "test/test_common/thread_factory_for_test.h" + +#include "gmock/gmock.h" +#include "gtest/gtest.h" + +namespace Envoy { +namespace Server { +namespace { +// Regression test for https://github.com/envoyproxy/envoy/issues/28413 +TEST(ConfigValidateTest, ValidateGood) { + Server::TestComponentFactory component_factory; + EXPECT_TRUE(validateConfig(testing::NiceMock(TestEnvironment::runfilesPath( + "test/common/listener_manager/internal_listener.yaml")), + Network::Address::InstanceConstSharedPtr(), component_factory, + Thread::threadFactoryForTest(), Filesystem::fileSystemForTest())); +} + +TEST(ConfigValidateTest, ValidateBad) { + Server::TestComponentFactory component_factory; + EXPECT_FALSE(validateConfig(testing::NiceMock(TestEnvironment::runfilesPath( + "test/common/listener_manager/" + "internal_listener_missing_bootstrap.yaml")), + Network::Address::InstanceConstSharedPtr(), component_factory, + Thread::threadFactoryForTest(), Filesystem::fileSystemForTest())); +} +} // namespace +} // namespace Server +} // namespace Envoy diff --git a/test/common/network/BUILD b/test/common/network/BUILD index 6b433fcc8180c..ea59472db9b62 100644 --- a/test/common/network/BUILD +++ b/test/common/network/BUILD @@ -80,6 +80,7 @@ envoy_cc_test( "//source/common/common:empty_string", "//source/common/event:dispatcher_includes", "//source/common/event:dispatcher_lib", + "//source/common/network:common_connection_filter_states_lib", "//source/common/network:connection_lib", "//source/common/network:listen_socket_lib", "//source/common/network:utility_lib", diff --git a/test/common/network/address_impl_test.cc b/test/common/network/address_impl_test.cc index 67551354b7b55..59c2955f503a6 100644 --- a/test/common/network/address_impl_test.cc +++ b/test/common/network/address_impl_test.cc @@ -408,7 +408,7 @@ TEST(PipeInstanceTest, PermissionFail) { EXPECT_CALL(os_sys_calls, bind(_, _, _)).WillOnce(Return(Api::SysCallIntResult{0, 0})); EXPECT_CALL(os_sys_calls, chmod(_, _)).WillOnce(Return(Api::SysCallIntResult{-1, 0})); - EXPECT_THROW_WITH_REGEX(sock.bind(address), EnvoyException, "Failed to create socket with mode"); + EXPECT_NE(sock.bind(address).return_value_, 0); } TEST(PipeInstanceTest, AbstractNamespacePermission) { diff --git a/test/common/network/connection_impl_test.cc b/test/common/network/connection_impl_test.cc index 7f768eea8c21d..ee72edec49b46 100644 --- a/test/common/network/connection_impl_test.cc +++ b/test/common/network/connection_impl_test.cc @@ -15,6 +15,7 @@ #include "source/common/common/utility.h" #include "source/common/event/dispatcher_impl.h" #include "source/common/network/address_impl.h" +#include "source/common/network/common_connection_filter_states.h" #include "source/common/network/connection_impl.h" #include "source/common/network/io_socket_handle_impl.h" #include "source/common/network/listen_socket_impl.h" @@ -66,6 +67,16 @@ class MockInternalListenerManager : public InternalListenerManager { MOCK_METHOD(InternalListenerOptRef, findByAddress, (const Address::InstanceConstSharedPtr&), ()); }; +class NoopConnectionExecutionContext : public ExecutionContext { +public: + NoopConnectionExecutionContext() = default; + ~NoopConnectionExecutionContext() override = default; + +protected: + void activate() override {} + void deactivate() override {} +}; + TEST(RawBufferSocket, TestBasics) { TransportSocketPtr raw_buffer_socket(Network::Test::createRawBufferSocket()); EXPECT_FALSE(raw_buffer_socket->ssl()); @@ -333,6 +344,27 @@ TEST_P(ConnectionImplTest, SetSslConnection) { disconnect(false); } +TEST_P(ConnectionImplTest, SetGetExecutionContextFilterState) { + setUpBasicConnection(); + connect(); + + EXPECT_EQ(getConnectionExecutionContext(*client_connection_), nullptr); + + const StreamInfo::FilterStateSharedPtr& filter_state = + client_connection_->streamInfo().filterState(); + auto connection_execution_context = std::make_unique(); + const NoopConnectionExecutionContext* context_pointer = + connection_execution_context.get(); // Not owned. + auto filter_state_object = std::make_shared( + std::move(connection_execution_context)); + filter_state->setData(kConnectionExecutionContextFilterStateName, filter_state_object, + StreamInfo::FilterState::StateType::ReadOnly, + StreamInfo::FilterState::LifeSpan::Connection); + + EXPECT_EQ(getConnectionExecutionContext(*client_connection_), context_pointer); + disconnect(true); +} + TEST_P(ConnectionImplTest, GetCongestionWindow) { setUpBasicConnection(); connect(); @@ -640,6 +672,7 @@ TEST_P(ConnectionImplTest, SocketOptionsFailureTest) { dispatcher_->run(Event::Dispatcher::RunType::Block); } +#if ENVOY_PLATFORM_ENABLE_SEND_RST // Test that connection is AbortReset closed during callback. TEST_P(ConnectionImplTest, ClientAbortResetDuringCallback) { Network::ClientConnectionPtr upstream_connection_; @@ -786,6 +819,7 @@ TEST_P(ConnectionImplTest, ServerResetCloseRuntimeDisabled) { server_connection_->close(ConnectionCloseType::AbortReset); dispatcher_->run(Event::Dispatcher::RunType::Block); } +#endif struct MockConnectionStats { Connection::ConnectionStats toBufferStats() { @@ -1111,6 +1145,7 @@ TEST_P(ConnectionImplTest, CloseOnReadDisableWithoutCloseDetection) { dispatcher_->run(Event::Dispatcher::RunType::Block); } +#if ENVOY_PLATFORM_ENABLE_SEND_RST // Test normal RST close without readDisable. TEST_P(ConnectionImplTest, RstCloseOnNotReadDisabledConnection) { setUpBasicConnection(); @@ -1188,6 +1223,7 @@ TEST_P(ConnectionImplTest, RstCloseOnReadEarlyCloseDisabledThenWrite) { client_connection_->write(buffer, false); dispatcher_->run(Event::Dispatcher::RunType::Block); } +#endif // Test that connection half-close is sent and received properly. TEST_P(ConnectionImplTest, HalfClose) { @@ -1229,6 +1265,7 @@ TEST_P(ConnectionImplTest, HalfClose) { dispatcher_->run(Event::Dispatcher::RunType::Block); } +#if ENVOY_PLATFORM_ENABLE_SEND_RST // Test that connection is immediately closed when RST is detected even // half-close is enabled TEST_P(ConnectionImplTest, HalfCloseResetClose) { @@ -1346,7 +1383,6 @@ TEST_P(ConnectionImplTest, HalfCloseThenResetClose) { dispatcher_->run(Event::Dispatcher::RunType::Block); } -#if !defined(WIN32) // Test that no remote close event will be propagated back to peer, when a connection is // half-closed and then the connection is RST closed. Writing data to the half closed and then // reset connection will lead to broken pipe error rather than reset error. diff --git a/test/common/network/happy_eyeballs_connection_provider_test.cc b/test/common/network/happy_eyeballs_connection_provider_test.cc index 526cfb14c6799..8f14eaa6f9ab6 100644 --- a/test/common/network/happy_eyeballs_connection_provider_test.cc +++ b/test/common/network/happy_eyeballs_connection_provider_test.cc @@ -1,3 +1,7 @@ +#include + +#include "envoy/network/address.h" + #include "source/common/network/address_impl.h" #include "source/common/network/happy_eyeballs_connection_impl.h" @@ -43,5 +47,72 @@ TEST_F(HappyEyeballsConnectionProviderTest, SortAddresses) { EXPECT_EQ(interleaved3, HappyEyeballsConnectionProvider::sortAddresses(mixed)); } +TEST_F(HappyEyeballsConnectionProviderTest, SortAddressesWithHappyEyeballsConfig) { + auto ip_v4_1 = std::make_shared("127.0.0.1"); + auto ip_v4_2 = std::make_shared("127.0.0.2"); + auto ip_v4_3 = std::make_shared("127.0.0.3"); + auto ip_v4_4 = std::make_shared("127.0.0.4"); + + auto ip_v6_1 = std::make_shared("ff02::1", 0); + auto ip_v6_2 = std::make_shared("ff02::2", 0); + auto ip_v6_3 = std::make_shared("ff02::3", 0); + auto ip_v6_4 = std::make_shared("ff02::4", 0); + + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig he_config; + he_config.set_first_address_family_version( + envoy::config::cluster::v3::UpstreamConnectionOptions::V4); + he_config.mutable_first_address_family_count()->set_value(2); + auto config = absl::make_optional(he_config); + + // All v4 address so unchanged. + std::vector v4_list = {ip_v4_1, ip_v4_2, ip_v4_3, ip_v4_4}; + EXPECT_EQ(v4_list, HappyEyeballsConnectionProvider::sortAddressesWithConfig(v4_list, config)); + + // All v6 address so unchanged. + std::vector v6_list = {ip_v6_1, ip_v6_2, ip_v6_3, ip_v6_4}; + EXPECT_EQ(v6_list, HappyEyeballsConnectionProvider::sortAddressesWithConfig(v6_list, config)); + + // v6 then v4, return interleaved list. + std::vector v6_then_v4 = {ip_v6_1, ip_v4_1, ip_v6_2, ip_v4_2}; + std::vector interleaved2 = {ip_v4_1, ip_v4_2, ip_v6_1, ip_v6_2}; + EXPECT_EQ(interleaved2, + HappyEyeballsConnectionProvider::sortAddressesWithConfig(v6_then_v4, config)); + + // v6 then single v4, return v4 first interleaved list. + std::vector v6_then_single_v4 = {ip_v6_1, ip_v6_2, ip_v6_3, + ip_v4_1}; + std::vector interleaved = {ip_v4_1, ip_v6_1, ip_v6_2, ip_v6_3}; + EXPECT_EQ(interleaved, + HappyEyeballsConnectionProvider::sortAddressesWithConfig(v6_then_single_v4, config)); + + // mixed + std::vector mixed = {ip_v6_1, ip_v6_2, ip_v6_3, ip_v4_1, + ip_v4_2, ip_v4_3, ip_v4_4, ip_v6_4}; + std::vector interleaved3 = {ip_v4_1, ip_v4_2, ip_v6_1, ip_v4_3, + ip_v4_4, ip_v6_2, ip_v6_3, ip_v6_4}; + EXPECT_EQ(interleaved3, HappyEyeballsConnectionProvider::sortAddressesWithConfig(mixed, config)); + + // missing first_address_family_version + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig he_config_no_version; + he_config_no_version.mutable_first_address_family_count()->set_value(2); + auto config_no_version = absl::make_optional(he_config_no_version); + // first_address_family_version should default to DEFAULT when absent. + // v6 then v4, return interleaved list. + std::vector interleaved4 = {ip_v6_1, ip_v6_2, ip_v4_1, ip_v4_2}; + EXPECT_EQ(interleaved4, HappyEyeballsConnectionProvider::sortAddressesWithConfig( + v6_then_v4, config_no_version)); + + // missing first_address_family_count + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig he_config_no_count; + he_config_no_count.set_first_address_family_version( + envoy::config::cluster::v3::UpstreamConnectionOptions::V4); + auto config_no_count = absl::make_optional(he_config_no_count); + // first_address_family_count should default to 1 when absent. + // v6 then v4, return interleaved list. + std::vector interleaved5 = {ip_v4_1, ip_v6_1, ip_v4_2, ip_v6_2}; + EXPECT_EQ(interleaved5, + HappyEyeballsConnectionProvider::sortAddressesWithConfig(v6_then_v4, config_no_count)); +} + } // namespace Network } // namespace Envoy diff --git a/test/common/network/resolver_impl_test.cc b/test/common/network/resolver_impl_test.cc index 3574414e62980..1f2accbc98404 100644 --- a/test/common/network/resolver_impl_test.cc +++ b/test/common/network/resolver_impl_test.cc @@ -73,9 +73,8 @@ TEST(ResolverTest, InternalListenerNameFromProtoAddress) { TEST(ResolverTest, UninitializedInternalAddressFromProtoAddress) { envoy::config::core::v3::Address internal_address; internal_address.mutable_envoy_internal_address(); - EXPECT_THROW_WITH_MESSAGE( - resolveProtoAddress(internal_address).IgnoreError(), EnvoyException, - fmt::format("Failed to resolve address:{}", internal_address.DebugString())); + EXPECT_EQ(resolveProtoAddress(internal_address).status().message(), + fmt::format("Failed to resolve address:{}", internal_address.DebugString())); } // Validate correct handling of ipv4_compat field. @@ -171,8 +170,7 @@ TEST(ResolverTest, NonStandardResolver) { TEST(ResolverTest, UninitializedAddress) { envoy::config::core::v3::Address address; - EXPECT_THROW_WITH_MESSAGE(resolveProtoAddress(address).IgnoreError(), EnvoyException, - "Address must be set: "); + EXPECT_EQ(resolveProtoAddress(address).status().message(), "Address must be set: "); } TEST(ResolverTest, NoSuchResolver) { @@ -181,8 +179,8 @@ TEST(ResolverTest, NoSuchResolver) { socket->set_address("foo"); socket->set_port_value(5); socket->set_resolver_name("envoy.test.resolver"); - EXPECT_THROW_WITH_MESSAGE(resolveProtoAddress(address).IgnoreError(), EnvoyException, - "Unknown address resolver: envoy.test.resolver"); + EXPECT_EQ(resolveProtoAddress(address).status().message(), + "Unknown address resolver: envoy.test.resolver"); } } // namespace diff --git a/test/common/quic/envoy_quic_client_session_test.cc b/test/common/quic/envoy_quic_client_session_test.cc index 153316969de0a..23a105888b101 100644 --- a/test/common/quic/envoy_quic_client_session_test.cc +++ b/test/common/quic/envoy_quic_client_session_test.cc @@ -16,6 +16,7 @@ #include "test/mocks/network/mocks.h" #include "test/mocks/stats/mocks.h" #include "test/test_common/logging.h" +#include "test/test_common/network_utility.h" #include "test/test_common/simulated_time_system.h" #include "gmock/gmock.h" @@ -67,9 +68,10 @@ class EnvoyQuicClientSessionTest : public testing::TestWithParamallocateDispatcher("test_thread")), connection_helper_(*dispatcher_), alarm_factory_(*dispatcher_, *connection_helper_.GetClock()), quic_version_({GetParam()}), peer_addr_( - Network::Utility::getAddressWithPort(*Network::Utility::getIpv6LoopbackAddress(), 0)), - self_addr_(Network::Utility::getAddressWithPort(*Network::Utility::getIpv6LoopbackAddress(), - 54321)), + Network::Test::getCanonicalLoopbackAddress(TestEnvironment::getIpVersionsForTest()[0])), + self_addr_(Network::Utility::getAddressWithPort( + *Network::Test::getCanonicalLoopbackAddress(TestEnvironment::getIpVersionsForTest()[0]), + 54321)), peer_socket_(createConnectionSocket(self_addr_, peer_addr_, nullptr)), quic_connection_(new TestEnvoyQuicClientConnection( quic::test::TestConnectionId(), connection_helper_, alarm_factory_, writer_, diff --git a/test/common/quic/envoy_quic_h3_fuzz_helper.cc b/test/common/quic/envoy_quic_h3_fuzz_helper.cc index 1994e83c7f404..30f4f69e66e12 100644 --- a/test/common/quic/envoy_quic_h3_fuzz_helper.cc +++ b/test/common/quic/envoy_quic_h3_fuzz_helper.cc @@ -27,7 +27,7 @@ class Delegate : public quic::QpackEncoder::DecoderStreamErrorDelegate { static std::string encodeHeaders(const spdy::Http2HeaderBlock& headers) { static Delegate delegate; - quic::QpackEncoder encoder(&delegate); + quic::QpackEncoder encoder(&delegate, quic::HuffmanEncoding::kEnabled); return encoder.EncodeHeaderList(0, headers, nullptr); } diff --git a/test/common/quic/platform/quiche_test_impl.h b/test/common/quic/platform/quiche_test_impl.h index 9ba6263bc6385..eee24fc881d1a 100644 --- a/test/common/quic/platform/quiche_test_impl.h +++ b/test/common/quic/platform/quiche_test_impl.h @@ -40,5 +40,17 @@ inline std::string QuicheGetCommonSourcePathImpl() { return absl::StrCat(test_srcdir, "/external/com_github_google_quiche/quiche/common"); } +class QuicheScopedDisableExitOnDFatalImpl { +public: + explicit QuicheScopedDisableExitOnDFatalImpl() {} + + // This type is neither copyable nor movable. + QuicheScopedDisableExitOnDFatalImpl(const QuicheScopedDisableExitOnDFatalImpl&) = delete; + QuicheScopedDisableExitOnDFatalImpl& + operator=(const QuicheScopedDisableExitOnDFatalImpl&) = delete; + + ~QuicheScopedDisableExitOnDFatalImpl() {} +}; + } // namespace test } // namespace quiche diff --git a/test/common/quic/test_utils.h b/test/common/quic/test_utils.h index 7a760158e4112..0a1a5938eab42 100644 --- a/test/common/quic/test_utils.h +++ b/test/common/quic/test_utils.h @@ -270,7 +270,8 @@ void setQuicConfigWithDefaultValues(quic::QuicConfig* config) { std::string spdyHeaderToHttp3StreamPayload(const spdy::Http2HeaderBlock& header) { quic::test::NoopQpackStreamSenderDelegate encoder_stream_sender_delegate; quic::NoopDecoderStreamErrorDelegate decoder_stream_error_delegate; - auto qpack_encoder = std::make_unique(&decoder_stream_error_delegate); + auto qpack_encoder = std::make_unique(&decoder_stream_error_delegate, + quic::HuffmanEncoding::kEnabled); qpack_encoder->set_qpack_stream_sender_delegate(&encoder_stream_sender_delegate); // QpackEncoder does not use the dynamic table by default, // therefore the value of |stream_id| does not matter. diff --git a/test/common/router/header_formatter_test.cc b/test/common/router/header_formatter_test.cc index dbe46e5b11a84..60e82764d7fb5 100644 --- a/test/common/router/header_formatter_test.cc +++ b/test/common/router/header_formatter_test.cc @@ -204,8 +204,7 @@ TEST(HeaderParserTest, TestParse) { ON_CALL(stream_info, filterState()).WillByDefault(ReturnRef(filter_state)); ON_CALL(Const(stream_info), filterState()).WillByDefault(ReturnRef(*filter_state)); - ON_CALL(stream_info, hasResponseFlag(StreamInfo::ResponseFlag::LocalReset)) - .WillByDefault(Return(true)); + stream_info.setResponseFlag(StreamInfo::CoreResponseFlag::LocalReset); absl::optional rc_details{"via_upstream"}; ON_CALL(stream_info, responseCodeDetails()).WillByDefault(ReturnRef(rc_details)); diff --git a/test/common/router/router_2_test.cc b/test/common/router/router_2_test.cc index 4186a2f13607c..4c0fbba8d1312 100644 --- a/test/common/router/router_2_test.cc +++ b/test/common/router/router_2_test.cc @@ -50,7 +50,8 @@ TEST_F(RouterTestSuppressEnvoyHeaders, MaintenanceMode) { {":status", "503"}, {"content-length", "16"}, {"content-type", "text/plain"}}; EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow)); + EXPECT_CALL(callbacks_.stream_info_, + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -98,7 +99,8 @@ TEST_F(RouterTestSuppressEnvoyHeaders, EnvoyAttemptCountInResponseNotPresent) { {":status", "503"}, {"content-length", "16"}, {"content-type", "text/plain"}}; EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow)); + EXPECT_CALL(callbacks_.stream_info_, + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -371,7 +373,7 @@ TEST_F(WatermarkTest, RetryRequestNotComplete) { expectNewStreamWithImmediateEncoder(encoder1, &response_decoder, Http::Protocol::Http10); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRemoteReset)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRemoteReset)); Http::TestRequestHeaderMapImpl headers{{"x-envoy-retry-on", "5xx"}, {"x-envoy-internal", "true"}}; HttpTestUtility::addDefaultHeaders(headers); @@ -731,7 +733,7 @@ TEST_P(RouterTestStrictCheckOneHeader, SingleInvalidHeader) { auto checked_header = GetParam(); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::InvalidEnvoyRequestHeaders)); + setResponseFlag(StreamInfo::CoreResponseFlag::InvalidEnvoyRequestHeaders)); EXPECT_CALL(callbacks_, encodeHeaders_(_, _)) .WillOnce(Invoke([&](Http::ResponseHeaderMap& response_headers, bool end_stream) -> void { @@ -808,7 +810,7 @@ TEST_P(RouterTestStrictCheckAllHeaders, MultipleInvalidHeaders) { HttpTestUtility::addDefaultHeaders(headers); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::InvalidEnvoyRequestHeaders)); + setResponseFlag(StreamInfo::CoreResponseFlag::InvalidEnvoyRequestHeaders)); EXPECT_CALL(callbacks_, encodeHeaders_(_, _)) .WillOnce(Invoke([&](Http::ResponseHeaderMap& response_headers, bool end_stream) -> void { @@ -892,7 +894,7 @@ TEST_F(RouterTestSupressGRPCStatsEnabled, ExcludeTimeoutHttpStats) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -945,7 +947,7 @@ TEST_F(RouterTestSupressGRPCStatsDisabled, IncludeHttpTimeoutStats) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; diff --git a/test/common/router/router_test.cc b/test/common/router/router_test.cc index 743e761ea83be..1fce4783c62ac 100644 --- a/test/common/router/router_test.cc +++ b/test/common/router/router_test.cc @@ -316,7 +316,7 @@ TEST_F(RouterTest, UpdateSubjectAltNamesFilterStateWithIpHeaderOverride) { } TEST_F(RouterTest, RouteNotFound) { - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound)); + EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -355,7 +355,8 @@ TEST_F(RouterTest, MissingRequiredHeaders) { } TEST_F(RouterTest, ClusterNotFound) { - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::NoClusterFound)); + EXPECT_CALL(callbacks_.stream_info_, + setResponseFlag(StreamInfo::CoreResponseFlag::NoClusterFound)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -387,7 +388,7 @@ TEST_F(RouterTest, PoolFailureWithPriority) { EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -420,7 +421,7 @@ TEST_F(RouterTest, PoolFailureDueToConnectTimeout) { EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -747,7 +748,7 @@ TEST_F(RouterTest, NoHost) { EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream)); + setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -770,7 +771,8 @@ TEST_F(RouterTest, MaintenanceMode) { {"x-envoy-overloaded", "true"}}; EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow)); + EXPECT_CALL(callbacks_.stream_info_, + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -817,7 +819,7 @@ TEST_F(RouterTest, DropOverloadDropped) { {"x-envoy-drop-overload", "true"}}; EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::DropOverLoad)); + EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::CoreResponseFlag::DropOverLoad)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -1035,7 +1037,7 @@ TEST_F(RouterTest, EnvoyAttemptCountInResponsePresentWithLocalReply) { EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamConnectionFailure)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamConnectionFailure)); Http::TestRequestHeaderMapImpl headers; HttpTestUtility::addDefaultHeaders(headers); @@ -1201,7 +1203,8 @@ TEST_F(RouterTest, NoRetriesOverflow) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); // RetryOverflow kicks in. - EXPECT_CALL(callbacks_.stream_info_, setResponseFlag(StreamInfo::ResponseFlag::UpstreamOverflow)); + EXPECT_CALL(callbacks_.stream_info_, + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamOverflow)); EXPECT_CALL(*router_->retry_state_, shouldRetryHeaders(_, _, _)) .WillOnce(Return(RetryStatus::NoOverflow)); EXPECT_CALL(cm_.thread_local_cluster_.conn_pool_.host_->health_checker_, setUnhealthy(_)) @@ -1259,7 +1262,7 @@ TEST_F(RouterTest, UpstreamTimeoutAllStatsEmission) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::ResponseHeaderMapPtr response_headers( new Http::TestResponseHeaderMapImpl{{":status", "503"}}); @@ -1291,7 +1294,7 @@ TEST_F(RouterTest, UpstreamTimeout) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -1481,7 +1484,7 @@ TEST_F(RouterTest, TimeoutBudgetHistogramStatDuringRetries) { // Trigger second request failure. EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder2.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -1564,7 +1567,7 @@ TEST_F(RouterTest, TimeoutBudgetHistogramStatDuringGlobalTimeout) { // Trigger global timeout. EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder2.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -1800,7 +1803,7 @@ TEST_F(RouterTest, UpstreamTimeoutWithAltResponse) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{{":status", "204"}}; EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), true)); @@ -1829,7 +1832,7 @@ TEST_F(RouterTest, UpstreamPerTryIdleTimeout) { router_->config().upstream_logs_.push_back( std::make_shared([&](const auto& stream_info) { filter_state_verified = - stream_info.hasResponseFlag(StreamInfo::ResponseFlag::StreamIdleTimeout); + stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::StreamIdleTimeout); })); NiceMock encoder; @@ -1871,7 +1874,7 @@ TEST_F(RouterTest, UpstreamPerTryIdleTimeout) { putResult(Upstream::Outlier::Result::LocalOriginTimeout, _)); EXPECT_CALL(*per_try_idle_timeout_, disableTimer()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(*response_timeout_, disableTimer()); EXPECT_CALL(callbacks_.stream_info_, setResponseCodeDetails("upstream_per_try_idle_timeout")); Http::TestResponseHeaderMapImpl response_headers{ @@ -1964,7 +1967,7 @@ TEST_F(RouterTest, UpstreamPerTryTimeout) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -2018,7 +2021,7 @@ TEST_F(RouterTest, UpstreamPerTryTimeoutDelayedPoolReady) { callbacks_.route_->route_entry_.virtual_cluster_.stats().upstream_rq_total_.value()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(encoder.stream_, resetStream(Http::StreamResetReason::LocalReset)); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -2077,7 +2080,7 @@ TEST_F(RouterTest, UpstreamPerTryTimeoutExcludesNewStream) { putResult(Upstream::Outlier::Result::LocalOriginTimeout, _)); EXPECT_CALL(*per_try_timeout_, disableTimer()); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(*response_timeout_, disableTimer()); Http::TestResponseHeaderMapImpl response_headers{ {":status", "504"}, {"content-length", "24"}, {"content-type", "text/plain"}}; @@ -3214,7 +3217,7 @@ TEST_F(RouterTest, RetryNoneHealthy) { EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(callbacks_, encodeData(_, true)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::NoHealthyUpstream)); + setResponseFlag(StreamInfo::CoreResponseFlag::NoHealthyUpstream)); router_->retry_state_->callback_(); EXPECT_TRUE(verifyHostUpstreamStats(0, 1)); // Pool failure for the first try, so only 1 upstream request was made. @@ -3666,7 +3669,7 @@ TEST_F(RouterTest, RetryTimeoutDuringRetryDelay) { // Fire timeout. EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(cm_.thread_local_cluster_.conn_pool_.host_->outlier_detector_, putResponseTime(_)) .Times(0); @@ -3815,7 +3818,7 @@ TEST_F(RouterTest, RetryTimeoutDuringRetryDelayWithUpstreamRequestNoHost) { // Fire timeout. EXPECT_CALL(cancellable, cancel(_)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(cm_.thread_local_cluster_.conn_pool_.host_->outlier_detector_, putResponseTime(_)) .Times(0); @@ -3868,7 +3871,7 @@ TEST_F(RouterTest, RetryTimeoutDuringRetryDelayWithUpstreamRequestNoHostAltRespo // Fire timeout. EXPECT_CALL(cancellable, cancel(_)); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout)); EXPECT_CALL(cm_.thread_local_cluster_.conn_pool_.host_->outlier_detector_, putResponseTime(_)) .Times(0); diff --git a/test/common/router/vhds_test.cc b/test/common/router/vhds_test.cc index 4b2f65be16c53..7330f59f3134f 100644 --- a/test/common/router/vhds_test.cc +++ b/test/common/router/vhds_test.cc @@ -100,7 +100,10 @@ TEST_F(VhdsTest, VhdsInstantiationShouldSucceedWithDELTA_GRPC) { TestUtility::parseYaml(default_vhds_config_); RouteConfigUpdatePtr config_update_info = makeRouteConfigUpdate(route_config); - EXPECT_NO_THROW(VhdsSubscription(config_update_info, factory_context_, context_, provider_)); + EXPECT_TRUE(VhdsSubscription::createVhdsSubscription(config_update_info, factory_context_, + context_, provider_) + .status() + .ok()); } // verify that api_type: GRPC fails validation @@ -118,8 +121,10 @@ name: my_route )EOF"); RouteConfigUpdatePtr config_update_info = makeRouteConfigUpdate(route_config); - EXPECT_THROW(VhdsSubscription(config_update_info, factory_context_, context_, provider_), - EnvoyException); + EXPECT_FALSE(VhdsSubscription::createVhdsSubscription(config_update_info, factory_context_, + context_, provider_) + .status() + .ok()); } // verify addition/updating of virtual hosts @@ -128,7 +133,9 @@ TEST_F(VhdsTest, VhdsAddsVirtualHosts) { TestUtility::parseYaml(default_vhds_config_); RouteConfigUpdatePtr config_update_info = makeRouteConfigUpdate(route_config); - VhdsSubscription subscription(config_update_info, factory_context_, context_, provider_); + VhdsSubscriptionPtr subscription = VhdsSubscription::createVhdsSubscription( + config_update_info, factory_context_, context_, provider_) + .value(); EXPECT_EQ(0UL, config_update_info->protobufConfigurationCast().virtual_hosts_size()); auto vhost = buildVirtualHost("vhost1", "vhost.first"); @@ -188,7 +195,9 @@ name: my_route )EOF"); RouteConfigUpdatePtr config_update_info = makeRouteConfigUpdate(route_config); - VhdsSubscription subscription(config_update_info, factory_context_, context_, provider_); + VhdsSubscriptionPtr subscription = VhdsSubscription::createVhdsSubscription( + config_update_info, factory_context_, context_, provider_) + .value(); EXPECT_EQ(1UL, config_update_info->protobufConfigurationCast().virtual_hosts_size()); EXPECT_EQ("vhost_rds1", config_update_info->protobufConfigurationCast().virtual_hosts(0).name()); diff --git a/test/common/stats/thread_local_store_test.cc b/test/common/stats/thread_local_store_test.cc index 7939224a88556..36c0ea4bf253f 100644 --- a/test/common/stats/thread_local_store_test.cc +++ b/test/common/stats/thread_local_store_test.cc @@ -1536,7 +1536,7 @@ TEST_F(StatsThreadLocalStoreTestNoFixture, MemoryWithTlsRealSymbolTable) { TestUtil::forEachSampleStat( 100, true, [this](absl::string_view name) { scope_.counterFromString(std::string(name)); }); EXPECT_MEMORY_EQ(memory_test.consumedBytes(), 827616); // Sep 25, 2020 - EXPECT_MEMORY_LE(memory_test.consumedBytes(), 0.97 * million_); + EXPECT_MEMORY_LE(memory_test.consumedBytes(), 0.99 * million_); } TEST_F(StatsThreadLocalStoreTest, ShuttingDown) { diff --git a/test/common/stream_info/stream_info_impl_test.cc b/test/common/stream_info/stream_info_impl_test.cc index dcb0dcfe34d92..9b1280a5d03f2 100644 --- a/test/common/stream_info/stream_info_impl_test.cc +++ b/test/common/stream_info/stream_info_impl_test.cc @@ -27,6 +27,9 @@ namespace Envoy { namespace StreamInfo { namespace { +REGISTER_CUSTOM_RESPONSE_FLAG(CF, CustomFlag); +REGISTER_CUSTOM_RESPONSE_FLAG(CF2, CustomFlag2); + std::chrono::nanoseconds checkDuration(std::chrono::nanoseconds last, absl::optional timing) { EXPECT_TRUE(timing); @@ -41,7 +44,7 @@ class StreamInfoImplTest : public testing::Test { sizeof(stream_info) == 840 || sizeof(stream_info) == 856 || sizeof(stream_info) == 888 || sizeof(stream_info) == 776 || sizeof(stream_info) == 728 || sizeof(stream_info) == 744 || sizeof(stream_info) == 680 || sizeof(stream_info) == 696 || sizeof(stream_info) == 688 || - sizeof(stream_info) == 720 || sizeof(stream_info) == 704) + sizeof(stream_info) == 736 || sizeof(stream_info) == 728 || sizeof(stream_info) == 712) << "If adding fields to StreamInfoImpl, please check to see if you " "need to add them to setFromForRecreateStream or setFrom! Current size " << sizeof(stream_info); @@ -121,39 +124,141 @@ TEST_F(StreamInfoImplTest, BytesTest) { EXPECT_EQ(bytes_received, stream_info.bytesReceived()); } -TEST_F(StreamInfoImplTest, ResponseFlagTest) { - const std::vector responseFlags = {FailedLocalHealthCheck, - NoHealthyUpstream, - UpstreamRequestTimeout, - LocalReset, - UpstreamRemoteReset, - UpstreamConnectionFailure, - UpstreamConnectionTermination, - UpstreamOverflow, - NoRouteFound, - DelayInjected, - FaultInjected, - RateLimited}; +// This is used to ensure the new extendable response flags are compatible with the legacy one +// and the legacyResponseFlags() method works as expected. +// TODO(wbpcode): remove this class and related test after the legacyResponseFlags() method is +// removed. +enum LegacyResponseFlag { + // Local server healthcheck failed. + FailedLocalHealthCheck = 0x1, + // No healthy upstream. + NoHealthyUpstream = 0x2, + // Request timeout on upstream. + UpstreamRequestTimeout = 0x4, + // Local codec level reset was sent on the stream. + LocalReset = 0x8, + // Remote codec level reset was received on the stream. + UpstreamRemoteReset = 0x10, + // Local reset by a connection pool due to an initial connection failure. + UpstreamConnectionFailure = 0x20, + // If the stream was locally reset due to connection termination. + UpstreamConnectionTermination = 0x40, + // The stream was reset because of a resource overflow. + UpstreamOverflow = 0x80, + // No route found for a given request. + NoRouteFound = 0x100, + // Request was delayed before proxying. + DelayInjected = 0x200, + // Abort with error code was injected. + FaultInjected = 0x400, + // Request was ratelimited locally by rate limit filter. + RateLimited = 0x800, + // Request was unauthorized by external authorization service. + UnauthorizedExternalService = 0x1000, + // Unable to call Ratelimit service. + RateLimitServiceError = 0x2000, + // If the stream was reset due to a downstream connection termination. + DownstreamConnectionTermination = 0x4000, + // Exceeded upstream retry limit. + UpstreamRetryLimitExceeded = 0x8000, + // Request hit the stream idle timeout, triggering a 408. + StreamIdleTimeout = 0x10000, + // Request specified x-envoy-* header values that failed strict header checks. + InvalidEnvoyRequestHeaders = 0x20000, + // Downstream request had an HTTP protocol error + DownstreamProtocolError = 0x40000, + // Upstream request reached to user defined max stream duration. + UpstreamMaxStreamDurationReached = 0x80000, + // True if the response was served from an Envoy cache filter. + ResponseFromCacheFilter = 0x100000, + // Filter config was not received within the permitted warming deadline. + NoFilterConfigFound = 0x200000, + // Request or connection exceeded the downstream connection duration. + DurationTimeout = 0x400000, + // Upstream response had an HTTP protocol error + UpstreamProtocolError = 0x800000, + // No cluster found for a given request. + NoClusterFound = 0x1000000, + // Overload Manager terminated the stream. + OverloadManager = 0x2000000, + // DNS resolution failed. + DnsResolutionFailed = 0x4000000, + // Drop certain percentage of overloaded traffic. + DropOverLoad = 0x8000000, + // ATTENTION: MAKE SURE THIS REMAINS EQUAL TO THE LAST FLAG. + LastFlag = DropOverLoad, +}; + +TEST_F(StreamInfoImplTest, LegacyResponseFlagTest) { + StreamInfoImpl stream_info(Http::Protocol::Http2, test_time_.timeSystem(), nullptr); + absl::flat_hash_map flags = { + {LegacyResponseFlag::FailedLocalHealthCheck, CoreResponseFlag::FailedLocalHealthCheck}, + {LegacyResponseFlag::NoHealthyUpstream, CoreResponseFlag::NoHealthyUpstream}, + {LegacyResponseFlag::UpstreamRequestTimeout, CoreResponseFlag::UpstreamRequestTimeout}, + {LegacyResponseFlag::LocalReset, CoreResponseFlag::LocalReset}, + {LegacyResponseFlag::UpstreamRemoteReset, CoreResponseFlag::UpstreamRemoteReset}, + {LegacyResponseFlag::UpstreamConnectionFailure, CoreResponseFlag::UpstreamConnectionFailure}, + {LegacyResponseFlag::UpstreamConnectionTermination, + CoreResponseFlag::UpstreamConnectionTermination}, + {LegacyResponseFlag::UpstreamOverflow, CoreResponseFlag::UpstreamOverflow}, + {LegacyResponseFlag::NoRouteFound, CoreResponseFlag::NoRouteFound}, + {LegacyResponseFlag::DelayInjected, CoreResponseFlag::DelayInjected}, + {LegacyResponseFlag::FaultInjected, CoreResponseFlag::FaultInjected}, + {LegacyResponseFlag::RateLimited, CoreResponseFlag::RateLimited}, + {LegacyResponseFlag::UnauthorizedExternalService, + CoreResponseFlag::UnauthorizedExternalService}, + {LegacyResponseFlag::RateLimitServiceError, CoreResponseFlag::RateLimitServiceError}, + {LegacyResponseFlag::DownstreamConnectionTermination, + CoreResponseFlag::DownstreamConnectionTermination}, + {LegacyResponseFlag::UpstreamRetryLimitExceeded, + CoreResponseFlag::UpstreamRetryLimitExceeded}, + {LegacyResponseFlag::StreamIdleTimeout, CoreResponseFlag::StreamIdleTimeout}, + {LegacyResponseFlag::InvalidEnvoyRequestHeaders, + CoreResponseFlag::InvalidEnvoyRequestHeaders}, + {LegacyResponseFlag::DownstreamProtocolError, CoreResponseFlag::DownstreamProtocolError}, + {LegacyResponseFlag::UpstreamMaxStreamDurationReached, + CoreResponseFlag::UpstreamMaxStreamDurationReached}, + {LegacyResponseFlag::ResponseFromCacheFilter, CoreResponseFlag::ResponseFromCacheFilter}, + {LegacyResponseFlag::NoFilterConfigFound, CoreResponseFlag::NoFilterConfigFound}, + {LegacyResponseFlag::DurationTimeout, CoreResponseFlag::DurationTimeout}, + {LegacyResponseFlag::UpstreamProtocolError, CoreResponseFlag::UpstreamProtocolError}, + {LegacyResponseFlag::NoClusterFound, CoreResponseFlag::NoClusterFound}, + {LegacyResponseFlag::OverloadManager, CoreResponseFlag::OverloadManager}, + {LegacyResponseFlag::DnsResolutionFailed, CoreResponseFlag::DnsResolutionFailed}, + {LegacyResponseFlag::DropOverLoad, CoreResponseFlag::DropOverLoad}, + }; + + for (auto& flag : flags) { + stream_info.setResponseFlag(flag.second); + EXPECT_TRUE(stream_info.hasResponseFlag(flag.second)); + + EXPECT_EQ(static_cast(flag.first), stream_info.legacyResponseFlags()); + + stream_info.response_flags_.clear(); + } +} + +TEST_F(StreamInfoImplTest, ResponseFlagTest) { StreamInfoImpl stream_info(Http::Protocol::Http2, test_time_.timeSystem(), nullptr); EXPECT_FALSE(stream_info.hasAnyResponseFlag()); - EXPECT_FALSE(stream_info.intersectResponseFlags(0)); - for (ResponseFlag flag : responseFlags) { + for (auto& flag : ResponseFlagUtils::responseFlagsVec()) { // Test cumulative setting of response flags. - EXPECT_FALSE(stream_info.hasResponseFlag(flag)) - << fmt::format("Flag: {} was already set", flag); - stream_info.setResponseFlag(flag); - EXPECT_TRUE(stream_info.hasResponseFlag(flag)) - << fmt::format("Flag: {} was expected to be set", flag); + EXPECT_FALSE(stream_info.hasResponseFlag(flag.flag_)) + << fmt::format("Flag: {} was already set", flag.short_string_); + stream_info.setResponseFlag(flag.flag_); + EXPECT_TRUE(stream_info.hasResponseFlag(flag.flag_)) + << fmt::format("Flag: {} was expected to be set", flag.short_string_); } EXPECT_TRUE(stream_info.hasAnyResponseFlag()); - EXPECT_EQ(0xFFF, stream_info.responseFlags()); - StreamInfoImpl stream_info2(Http::Protocol::Http2, test_time_.timeSystem(), nullptr); - stream_info2.setResponseFlag(FailedLocalHealthCheck); + for (size_t i = 0; i < ResponseFlagUtils::responseFlagsVec().size(); i++) { + EXPECT_EQ(ResponseFlagUtils::responseFlagsVec()[i].flag_.value(), + stream_info.responseFlags()[i].value()); + } - EXPECT_TRUE(stream_info2.intersectResponseFlags(FailedLocalHealthCheck)); + EXPECT_EQ(0xFFFFFFF, stream_info.legacyResponseFlags()); } TEST_F(StreamInfoImplTest, MiscSettersAndGetters) { @@ -290,7 +395,7 @@ TEST_F(StreamInfoImplTest, SetFrom) { s1.setUpstreamInfo(std::make_shared()); s1.upstreamInfo()->upstreamTiming().onLastUpstreamTxByteSent(test_time_.timeSystem()); s1.onRequestComplete(); - s1.setResponseFlag(FailedLocalHealthCheck); + s1.setResponseFlag(CoreResponseFlag::FailedLocalHealthCheck); s1.healthCheck(true); s1.route_ = std::make_shared>(); s1.setDynamicMetadata("com.test", MessageUtil::keyValueStruct("test_key", "test_value")); diff --git a/test/common/stream_info/utility_test.cc b/test/common/stream_info/utility_test.cc index 9e7dabfdf72ac..21e6f69c6877e 100644 --- a/test/common/stream_info/utility_test.cc +++ b/test/common/stream_info/utility_test.cc @@ -22,18 +22,68 @@ namespace { using envoy::extensions::filters::network::http_connection_manager::v3::HttpConnectionManager; +REGISTER_CUSTOM_RESPONSE_FLAG(CF, CustomFlag); +REGISTER_CUSTOM_RESPONSE_FLAG(CF2, CustomFlag2); + TEST(ResponseFlagUtilsTest, toShortStringConversion) { - for (const auto& [flag_strings, flag_enum] : ResponseFlagUtils::ALL_RESPONSE_STRINGS_FLAGS) { + for (const auto& [short_string, long_string, flag] : ResponseFlagUtils::responseFlagsVec()) { + NiceMock stream_info; + stream_info.response_flags_.clear(); + stream_info.response_flags_.push_back(flag); + EXPECT_EQ(short_string, ResponseFlagUtils::toShortString(stream_info)); + EXPECT_EQ(long_string, ResponseFlagUtils::toString(stream_info)); + } + + // Custom flag. + { + EXPECT_EQ(ResponseFlagUtils::responseFlagsVec().size(), + ResponseFlagUtils::responseFlagsMap().size()); + + // There are two custom flags are registered. + EXPECT_EQ(ResponseFlagUtils::CORE_RESPONSE_FLAGS.size() + 2, + ResponseFlagUtils::responseFlagsMap().size()); + + EXPECT_EQ(CUSTOM_RESPONSE_FLAG(CF).value(), CoreResponseFlag::LastFlag + 1); + EXPECT_EQ(CUSTOM_RESPONSE_FLAG(CF2).value(), CoreResponseFlag::LastFlag + 2); + + // Verify the custom flags are registered correctly. + EXPECT_EQ(CUSTOM_RESPONSE_FLAG(CF), ResponseFlagUtils::responseFlagsMap().at("CF").flag_); + EXPECT_EQ(CUSTOM_RESPONSE_FLAG(CF2), ResponseFlagUtils::responseFlagsMap().at("CF2").flag_); + EXPECT_EQ(ResponseFlagUtils::responseFlagsVec()[CUSTOM_RESPONSE_FLAG(CF).value()].short_string_, + "CF"); + EXPECT_EQ(ResponseFlagUtils::responseFlagsVec()[CUSTOM_RESPONSE_FLAG(CF).value()].long_string_, + "CustomFlag"); + EXPECT_EQ( + ResponseFlagUtils::responseFlagsVec()[CUSTOM_RESPONSE_FLAG(CF2).value()].short_string_, + "CF2"); + EXPECT_EQ(ResponseFlagUtils::responseFlagsVec()[CUSTOM_RESPONSE_FLAG(CF2).value()].long_string_, + "CustomFlag2"); + + // Verify the custom flag could work as expected. + NiceMock stream_info; - ON_CALL(stream_info, hasResponseFlag(flag_enum)).WillByDefault(Return(true)); - EXPECT_EQ(flag_strings.short_string_, ResponseFlagUtils::toShortString(stream_info)); - EXPECT_EQ(flag_strings.long_string_, ResponseFlagUtils::toString(stream_info)); + stream_info.response_flags_.clear(); + + stream_info.setResponseFlag(CUSTOM_RESPONSE_FLAG(CF)); + EXPECT_TRUE(stream_info.hasAnyResponseFlag()); + EXPECT_TRUE(stream_info.hasResponseFlag(CUSTOM_RESPONSE_FLAG(CF))); + + EXPECT_EQ("CF", ResponseFlagUtils::toShortString(stream_info)); + EXPECT_EQ("CustomFlag", ResponseFlagUtils::toString(stream_info)); + + stream_info.response_flags_.push_back(CUSTOM_RESPONSE_FLAG(CF2)); + + EXPECT_TRUE(stream_info.hasAnyResponseFlag()); + EXPECT_TRUE(stream_info.hasResponseFlag(CUSTOM_RESPONSE_FLAG(CF))); + EXPECT_TRUE(stream_info.hasResponseFlag(CUSTOM_RESPONSE_FLAG(CF2))); + + EXPECT_EQ("CF,CF2", ResponseFlagUtils::toShortString(stream_info)); + EXPECT_EQ("CustomFlag,CustomFlag2", ResponseFlagUtils::toString(stream_info)); } // No flag is set. { NiceMock stream_info; - ON_CALL(stream_info, hasResponseFlag(_)).WillByDefault(Return(false)); EXPECT_EQ("-", ResponseFlagUtils::toShortString(stream_info)); EXPECT_EQ("-", ResponseFlagUtils::toString(stream_info)); } @@ -42,10 +92,11 @@ TEST(ResponseFlagUtilsTest, toShortStringConversion) { // These are not real use cases, but are used to cover multiple response flags case. { NiceMock stream_info; - ON_CALL(stream_info, hasResponseFlag(ResponseFlag::DelayInjected)).WillByDefault(Return(true)); - ON_CALL(stream_info, hasResponseFlag(ResponseFlag::FaultInjected)).WillByDefault(Return(true)); - ON_CALL(stream_info, hasResponseFlag(ResponseFlag::UpstreamRequestTimeout)) - .WillByDefault(Return(true)); + stream_info.response_flags_.clear(); + stream_info.response_flags_.push_back(CoreResponseFlag::UpstreamRequestTimeout); + stream_info.response_flags_.push_back(CoreResponseFlag::DelayInjected); + stream_info.response_flags_.push_back(CoreResponseFlag::FaultInjected); + EXPECT_EQ("UT,DI,FI", ResponseFlagUtils::toShortString(stream_info)); EXPECT_EQ("UpstreamRequestTimeout,DelayInjected,FaultInjected", ResponseFlagUtils::toString(stream_info)); @@ -55,11 +106,10 @@ TEST(ResponseFlagUtilsTest, toShortStringConversion) { TEST(ResponseFlagsUtilsTest, toResponseFlagConversion) { EXPECT_FALSE(ResponseFlagUtils::toResponseFlag("NonExistentFlag").has_value()); - for (const auto& [flag_strings, flag_enum] : ResponseFlagUtils::ALL_RESPONSE_STRINGS_FLAGS) { - absl::optional response_flag = - ResponseFlagUtils::toResponseFlag(flag_strings.short_string_); + for (const auto& [short_string, _, flag] : ResponseFlagUtils::CORE_RESPONSE_FLAGS) { + auto response_flag = ResponseFlagUtils::toResponseFlag(short_string); EXPECT_TRUE(response_flag.has_value()); - EXPECT_EQ(flag_enum, response_flag.value()); + EXPECT_EQ(flag, response_flag.value()); } } @@ -90,8 +140,7 @@ class ProxyStatusTest : public ::testing::Test { void SetUp() override { proxy_status_config_.set_remove_details(false); - ON_CALL(stream_info_, hasAnyResponseFlag()).WillByDefault(Return(true)); - ON_CALL(stream_info_, hasResponseFlag(ResponseFlag::DelayInjected)).WillByDefault(Return(true)); + stream_info_.response_flags_.push_back(CoreResponseFlag::DelayInjected); } HttpConnectionManager::ProxyStatusConfig proxy_status_config_; @@ -321,26 +370,28 @@ TEST(ProxyStatusFromStreamInfo, TestAll) { {{"envoy.reloadable_features.proxy_status_upstream_request_timeout", "true"}}); for (const auto& [response_flag, proxy_status_error] : std::vector>{ - {ResponseFlag::FailedLocalHealthCheck, ProxyStatusError::DestinationUnavailable}, - {ResponseFlag::NoHealthyUpstream, ProxyStatusError::DestinationUnavailable}, - {ResponseFlag::UpstreamRequestTimeout, ProxyStatusError::HttpResponseTimeout}, - {ResponseFlag::LocalReset, ProxyStatusError::ConnectionTimeout}, - {ResponseFlag::UpstreamRemoteReset, ProxyStatusError::ConnectionTerminated}, - {ResponseFlag::UpstreamConnectionFailure, ProxyStatusError::ConnectionRefused}, - {ResponseFlag::UpstreamConnectionTermination, ProxyStatusError::ConnectionTerminated}, - {ResponseFlag::UpstreamOverflow, ProxyStatusError::ConnectionLimitReached}, - {ResponseFlag::NoRouteFound, ProxyStatusError::DestinationNotFound}, - {ResponseFlag::RateLimited, ProxyStatusError::ConnectionLimitReached}, - {ResponseFlag::RateLimitServiceError, ProxyStatusError::ConnectionLimitReached}, - {ResponseFlag::UpstreamRetryLimitExceeded, ProxyStatusError::DestinationUnavailable}, - {ResponseFlag::StreamIdleTimeout, ProxyStatusError::HttpResponseTimeout}, - {ResponseFlag::InvalidEnvoyRequestHeaders, ProxyStatusError::HttpRequestError}, - {ResponseFlag::DownstreamProtocolError, ProxyStatusError::HttpRequestError}, - {ResponseFlag::UpstreamMaxStreamDurationReached, ProxyStatusError::HttpResponseTimeout}, - {ResponseFlag::NoFilterConfigFound, ProxyStatusError::ProxyConfigurationError}, - {ResponseFlag::UpstreamProtocolError, ProxyStatusError::HttpProtocolError}, - {ResponseFlag::NoClusterFound, ProxyStatusError::DestinationUnavailable}, - {ResponseFlag::DnsResolutionFailed, ProxyStatusError::DnsError}}) { + {CoreResponseFlag::FailedLocalHealthCheck, ProxyStatusError::DestinationUnavailable}, + {CoreResponseFlag::NoHealthyUpstream, ProxyStatusError::DestinationUnavailable}, + {CoreResponseFlag::UpstreamRequestTimeout, ProxyStatusError::HttpResponseTimeout}, + {CoreResponseFlag::LocalReset, ProxyStatusError::ConnectionTimeout}, + {CoreResponseFlag::UpstreamRemoteReset, ProxyStatusError::ConnectionTerminated}, + {CoreResponseFlag::UpstreamConnectionFailure, ProxyStatusError::ConnectionRefused}, + {CoreResponseFlag::UpstreamConnectionTermination, + ProxyStatusError::ConnectionTerminated}, + {CoreResponseFlag::UpstreamOverflow, ProxyStatusError::ConnectionLimitReached}, + {CoreResponseFlag::NoRouteFound, ProxyStatusError::DestinationNotFound}, + {CoreResponseFlag::RateLimited, ProxyStatusError::ConnectionLimitReached}, + {CoreResponseFlag::RateLimitServiceError, ProxyStatusError::ConnectionLimitReached}, + {CoreResponseFlag::UpstreamRetryLimitExceeded, ProxyStatusError::DestinationUnavailable}, + {CoreResponseFlag::StreamIdleTimeout, ProxyStatusError::HttpResponseTimeout}, + {CoreResponseFlag::InvalidEnvoyRequestHeaders, ProxyStatusError::HttpRequestError}, + {CoreResponseFlag::DownstreamProtocolError, ProxyStatusError::HttpRequestError}, + {CoreResponseFlag::UpstreamMaxStreamDurationReached, + ProxyStatusError::HttpResponseTimeout}, + {CoreResponseFlag::NoFilterConfigFound, ProxyStatusError::ProxyConfigurationError}, + {CoreResponseFlag::UpstreamProtocolError, ProxyStatusError::HttpProtocolError}, + {CoreResponseFlag::NoClusterFound, ProxyStatusError::DestinationUnavailable}, + {CoreResponseFlag::DnsResolutionFailed, ProxyStatusError::DnsError}}) { NiceMock stream_info; ON_CALL(stream_info, hasResponseFlag(response_flag)).WillByDefault(Return(true)); EXPECT_THAT(ProxyStatusUtils::fromStreamInfo(stream_info), proxy_status_error); @@ -352,7 +403,7 @@ TEST(ProxyStatusFromStreamInfo, TestUpstreamRequestTimeout) { scoped_runtime.mergeValues( {{"envoy.reloadable_features.proxy_status_upstream_request_timeout", "false"}}); NiceMock stream_info; - ON_CALL(stream_info, hasResponseFlag(ResponseFlag::UpstreamRequestTimeout)) + ON_CALL(stream_info, hasResponseFlag(ResponseFlag(CoreResponseFlag::UpstreamRequestTimeout))) .WillByDefault(Return(true)); EXPECT_THAT(ProxyStatusUtils::fromStreamInfo(stream_info), ProxyStatusError::ConnectionTimeout); } diff --git a/test/common/tracing/http_tracer_impl_test.cc b/test/common/tracing/http_tracer_impl_test.cc index b0d325833943a..7a3f6c3bce8c4 100644 --- a/test/common/tracing/http_tracer_impl_test.cc +++ b/test/common/tracing/http_tracer_impl_test.cc @@ -519,9 +519,7 @@ TEST_F(HttpConnManFinalizerImplTest, SpanPopulatedFailureResponse) { absl::optional response_code(503); EXPECT_CALL(stream_info, responseCode()).WillRepeatedly(ReturnPointee(&response_code)); EXPECT_CALL(stream_info, bytesSent()).WillOnce(Return(100)); - ON_CALL(stream_info, hasResponseFlag(StreamInfo::ResponseFlag::UpstreamRequestTimeout)) - .WillByDefault(Return(true)); - stream_info.upstreamInfo()->setUpstreamHost(nullptr); + stream_info.setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRequestTimeout); EXPECT_CALL(span, setTag(Eq(Tracing::Tags::get().Error), Eq(Tracing::Tags::get().True))); EXPECT_CALL(span, setTag(Eq(Tracing::Tags::get().HttpStatusCode), Eq("503"))); diff --git a/test/common/upstream/BUILD b/test/common/upstream/BUILD index 12fe0396553a7..6301b964332ae 100644 --- a/test/common/upstream/BUILD +++ b/test/common/upstream/BUILD @@ -168,7 +168,10 @@ envoy_cc_test( envoy_cc_test( name = "edf_scheduler_test", srcs = ["edf_scheduler_test.cc"], - deps = ["//source/common/upstream:scheduler_lib"], + deps = [ + "//source/common/upstream:scheduler_lib", + "//test/test_common:utility_lib", + ], ) envoy_cc_test_library( @@ -265,6 +268,7 @@ envoy_cc_test( srcs = ["load_balancer_impl_test.cc"], deps = [ ":utility_lib", + "//source/common/common:random_generator_lib", "//source/common/network:utility_lib", "//source/common/upstream:load_balancer_lib", "//source/common/upstream:upstream_includes", @@ -563,6 +567,7 @@ envoy_cc_test( "//source/extensions/load_balancing_policies/round_robin:config", "//source/extensions/load_balancing_policies/subset:config", "//test/test_common:registry_lib", + "//test/test_common:test_runtime_lib", "//test/test_common:utility_lib", ] + envoy_select_enable_http3([ "//source/common/quic:quic_transport_socket_factory_lib", diff --git a/test/common/upstream/cluster_manager_impl_test.cc b/test/common/upstream/cluster_manager_impl_test.cc index 9da16fb69b908..04b65bd5c1db8 100644 --- a/test/common/upstream/cluster_manager_impl_test.cc +++ b/test/common/upstream/cluster_manager_impl_test.cc @@ -2389,7 +2389,7 @@ TEST_P(ClusterManagerLifecycleTest, HostsPostedToTlsCluster) { cluster1->priority_set_.updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, hosts, {}, - true, 100); + 123, true, 100); auto* tls_cluster = cluster_manager_->getThreadLocalCluster(cluster1->info_->name()); @@ -4150,7 +4150,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdates) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_merge_cancelled").value()); @@ -4161,12 +4161,12 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdates) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); cluster.prioritySet().updateHosts( 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_merge_cancelled").value()); @@ -4184,7 +4184,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdates) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(2, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_merge_cancelled").value()); @@ -4197,21 +4197,21 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdates) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); (*hosts)[0]->healthFlagSet(Host::HealthFlag::FAILED_EDS_HEALTH); cluster.prioritySet().updateHosts( 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); (*hosts)[0]->weight(100); cluster.prioritySet().updateHosts( 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); // Updates not delivered yet. EXPECT_EQ(2, factory_.stats_.counter("cluster_manager.cluster_updated").value()); @@ -4224,7 +4224,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdates) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(3, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); @@ -4267,7 +4267,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdatesOutOfWindow) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.update_out_of_merge_window").value()); @@ -4302,7 +4302,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdatesInsideWindow) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_out_of_merge_window").value()); @@ -4344,7 +4344,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdatesOutOfWindowDisabled) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_out_of_merge_window").value()); @@ -4421,7 +4421,7 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdatesDestroyedOnUpdate) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_merge_cancelled").value()); @@ -4432,12 +4432,12 @@ TEST_P(ClusterManagerLifecycleTest, MergedUpdatesDestroyedOnUpdate) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); cluster.prioritySet().updateHosts( 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_merge_cancelled").value()); @@ -4760,7 +4760,7 @@ TEST_P(ClusterManagerLifecycleTest, CrossPriorityHostMapSyncTest) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); @@ -4777,7 +4777,7 @@ TEST_P(ClusterManagerLifecycleTest, CrossPriorityHostMapSyncTest) { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, 123, absl::nullopt, absl::nullopt); EXPECT_EQ(2, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.update_merge_cancelled").value()); @@ -5870,7 +5870,7 @@ TEST_P(ClusterManagerLifecycleTest, DrainConnectionsPredicate) { // Sending non-mergeable updates. cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, hosts, {}, - absl::nullopt, 100); + 123, absl::nullopt, 100); // Using RR LB get a pool for each host. EXPECT_CALL(factory_, allocateConnPool_(_, _, _, _, _)) @@ -5942,7 +5942,7 @@ TEST_P(ClusterManagerLifecycleTest, ConnPoolsDrainedOnHostSetChange) { // Sending non-mergeable updates. cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, hosts, {}, - absl::nullopt, 100); + 123, absl::nullopt, 100); EXPECT_EQ(1, factory_.stats_.counter("cluster_manager.cluster_updated").value()); EXPECT_EQ(0, factory_.stats_.counter("cluster_manager.cluster_updated_via_merge").value()); @@ -6003,7 +6003,7 @@ TEST_P(ClusterManagerLifecycleTest, ConnPoolsDrainedOnHostSetChange) { // This update should drain all connection pools (host1, host2). cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, {}, - hosts_removed, absl::nullopt, 100); + hosts_removed, 123, absl::nullopt, 100); // Recreate connection pool for host1. cp1 = HttpPoolDataPeer::getPool( @@ -6032,7 +6032,7 @@ TEST_P(ClusterManagerLifecycleTest, ConnPoolsDrainedOnHostSetChange) { // Adding host3 should drain connection pool for host1. cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, - hosts_added, {}, absl::nullopt, 100); + hosts_added, {}, 123, absl::nullopt, 100); } TEST_P(ClusterManagerLifecycleTest, ConnPoolsNotDrainedOnHostSetChange) { @@ -6067,7 +6067,7 @@ TEST_P(ClusterManagerLifecycleTest, ConnPoolsNotDrainedOnHostSetChange) { // Sending non-mergeable updates. cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, hosts, {}, - absl::nullopt, 100); + 123, absl::nullopt, 100); EXPECT_CALL(factory_, allocateConnPool_(_, _, _, _, _)) .Times(1) @@ -6101,7 +6101,7 @@ TEST_P(ClusterManagerLifecycleTest, ConnPoolsNotDrainedOnHostSetChange) { // No connection pools should be drained. cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, - hosts_added, {}, absl::nullopt, 100); + hosts_added, {}, 123, absl::nullopt, 100); } TEST_P(ClusterManagerLifecycleTest, ConnPoolsIdleDeleted) { @@ -6138,7 +6138,7 @@ TEST_P(ClusterManagerLifecycleTest, ConnPoolsIdleDeleted) { // Sending non-mergeable updates. cluster.prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, hosts, {}, - absl::nullopt, 100); + 123, absl::nullopt, 100); { auto* cp1 = new NiceMock(); @@ -6440,7 +6440,7 @@ class PreconnectTest : public ClusterManagerImplTest { // Sending non-mergeable updates. cluster_->prioritySet().updateHosts( 0, HostSetImpl::partitionHosts(hosts_ptr, HostsPerLocalityImpl::empty()), nullptr, hosts, - {}, absl::nullopt, 100); + {}, 123, absl::nullopt, 100); } Cluster* cluster_{}; diff --git a/test/common/upstream/edf_scheduler_test.cc b/test/common/upstream/edf_scheduler_test.cc index 7eac13bc8153e..e9ecdfd4565ff 100644 --- a/test/common/upstream/edf_scheduler_test.cc +++ b/test/common/upstream/edf_scheduler_test.cc @@ -1,19 +1,60 @@ #include "source/common/upstream/edf_scheduler.h" +#include "test/test_common/test_random_generator.h" + #include "gtest/gtest.h" namespace Envoy { namespace Upstream { -namespace { -TEST(EdfSchedulerTest, Empty) { +class EdfSchedulerTest : public testing::Test { +public: + template + static void compareEdfSchedulers(EdfScheduler& scheduler1, EdfScheduler& scheduler2) { + // Compares that the given EdfSchedulers internal queues are equal up + // (ignoring the order_offset_ values). + EXPECT_EQ(scheduler1.queue_.size(), scheduler2.queue_.size()); + // Cannot iterate over std::priority_queue directly, so need to copy the + // contents to a vector first. + auto copyFunc = [](EdfScheduler& scheduler) { + std::vector::EdfEntry> result; + result.reserve(scheduler.queue_.size()); + while (!scheduler.empty()) { + result.emplace_back(std::move(scheduler.queue_.top())); + scheduler.queue_.pop(); + } + // Re-add all elements so the contents of the input scheduler isn't + // changed. + for (auto& entry : result) { + scheduler.queue_.push(entry); + } + return result; + }; + std::vector::EdfEntry> contents1 = copyFunc(scheduler1); + std::vector::EdfEntry> contents2 = copyFunc(scheduler2); + for (size_t i = 0; i < contents1.size(); ++i) { + // Given 2 queues and some number of picks P, where one queue is created empty + // and P picks are performed, and the other queue is created using + // `EdfScheduler::createWithPicks()` their deadlines may be a bit different + // due to floating point arithmetic differences. The comparison code uses + // a NEAR comparison to account for such differences. + EXPECT_NEAR(contents1[i].deadline_, contents2[i].deadline_, 1e-5) + << "inequal deadline in element " << i; + std::shared_ptr entry1 = contents1[i].entry_.lock(); + std::shared_ptr entry2 = contents2[i].entry_.lock(); + EXPECT_EQ(*entry1, *entry2) << "inequal entry in element " << i; + } + } +}; + +TEST_F(EdfSchedulerTest, Empty) { EdfScheduler sched; EXPECT_EQ(nullptr, sched.peekAgain([](const double&) { return 0; })); EXPECT_EQ(nullptr, sched.pickAndAdd([](const double&) { return 0; })); } // Validate we get regular RR behavior when all weights are the same. -TEST(EdfSchedulerTest, Unweighted) { +TEST_F(EdfSchedulerTest, Unweighted) { EdfScheduler sched; constexpr uint32_t num_entries = 128; std::shared_ptr entries[num_entries]; @@ -34,7 +75,7 @@ TEST(EdfSchedulerTest, Unweighted) { } // Validate we get weighted RR behavior when weights are distinct. -TEST(EdfSchedulerTest, Weighted) { +TEST_F(EdfSchedulerTest, Weighted) { EdfScheduler sched; constexpr uint32_t num_entries = 128; std::shared_ptr entries[num_entries]; @@ -59,7 +100,7 @@ TEST(EdfSchedulerTest, Weighted) { } // Validate that expired entries are ignored. -TEST(EdfSchedulerTest, Expired) { +TEST_F(EdfSchedulerTest, Expired) { EdfScheduler sched; auto second_entry = std::make_shared(42); @@ -77,7 +118,7 @@ TEST(EdfSchedulerTest, Expired) { } // Validate that expired entries are not peeked. -TEST(EdfSchedulerTest, ExpiredPeek) { +TEST_F(EdfSchedulerTest, ExpiredPeek) { EdfScheduler sched; { @@ -93,7 +134,7 @@ TEST(EdfSchedulerTest, ExpiredPeek) { } // Validate that expired entries are ignored. -TEST(EdfSchedulerTest, ExpiredPeekedIsNotPicked) { +TEST_F(EdfSchedulerTest, ExpiredPeekedIsNotPicked) { EdfScheduler sched; { @@ -110,7 +151,7 @@ TEST(EdfSchedulerTest, ExpiredPeekedIsNotPicked) { EXPECT_TRUE(sched.pickAndAdd([](const double&) { return 1; }) == nullptr); } -TEST(EdfSchedulerTest, ManyPeekahead) { +TEST_F(EdfSchedulerTest, ManyPeekahead) { EdfScheduler sched1; EdfScheduler sched2; constexpr uint32_t num_entries = 128; @@ -134,6 +175,154 @@ TEST(EdfSchedulerTest, ManyPeekahead) { } } -} // namespace +// Validates that creating a scheduler using the createWithPicks (with 0 picks) +// is equal to creating an empty scheduler and adding entries one after the other. +TEST_F(EdfSchedulerTest, SchedulerWithZeroPicksEqualToEmptyWithAddedEntries) { + constexpr uint32_t num_entries = 128; + std::vector> entries; + entries.reserve(num_entries); + + // Populate sched1 one entry after the other. + EdfScheduler sched1; + for (uint32_t i = 0; i < num_entries; ++i) { + entries.emplace_back(std::make_shared(i + 1)); + sched1.add(i + 1, entries.back()); + } + + EdfScheduler sched2 = EdfScheduler::createWithPicks( + entries, [](const double& w) { return w; }, 0); + + compareEdfSchedulers(sched1, sched2); +} + +// Validates that creating a scheduler using the createWithPicks (with 5 picks) +// is equal to creating an empty scheduler and adding entries one after the other, +// and then performing some number of picks. +TEST_F(EdfSchedulerTest, SchedulerWithSomePicksEqualToEmptyWithAddedEntries) { + constexpr uint32_t num_entries = 128; + // Use double-precision weights from the range [0.01, 100.5]. + // Using different weights to avoid a case where entries with the same weight + // will be chosen in different order. + std::vector> entries; + entries.reserve(num_entries); + for (uint32_t i = 0; i < num_entries; ++i) { + const double entry_weight = (100.5 - 0.01) / num_entries * i + 0.01; + entries.emplace_back(std::make_shared(entry_weight)); + } + + const std::vector all_picks{5, 140, 501, 123456, 894571}; + for (const auto picks : all_picks) { + // Populate sched1 one entry after the other. + EdfScheduler sched1; + for (uint32_t i = 0; i < num_entries; ++i) { + sched1.add(*entries[i], entries[i]); + } + // Perform the picks on sched1. + for (uint32_t i = 0; i < picks; ++i) { + sched1.pickAndAdd([](const double& w) { return w; }); + } + + // Create sched2 with pre-built and pre-picked entries. + EdfScheduler sched2 = EdfScheduler::createWithPicks( + entries, [](const double& w) { return w; }, picks); + + compareEdfSchedulers(sched1, sched2); + } +} + +// Validating that calling `createWithPicks()` with no entries returns an empty +// scheduler. +TEST_F(EdfSchedulerTest, SchedulerWithSomePicksEmptyEntries) { + EdfScheduler sched = EdfScheduler::createWithPicks( + {}, [](const double& w) { return w; }, 123); + EXPECT_EQ(nullptr, sched.peekAgain([](const double&) { return 0; })); + EXPECT_EQ(nullptr, sched.pickAndAdd([](const double&) { return 0; })); +} + +// Emulates first-pick scenarios by creating a scheduler with the given +// weights and a random number of pre-picks, and validates that the next pick +// of all the weights is close to the given weights. +void firstPickTest(const std::vector weights) { + TestRandomGenerator rand; + ASSERT(std::accumulate(weights.begin(), weights.end(), 0.) == 100.0); + // To be able to converge to the expected weights, a decent number of iterations + // should be used. If the number of weights is large, the number of iterations + // should be larger than 10000. + constexpr uint64_t iterations = 4e5; + // The expected range of the weights is [0,100). If this is no longer the + // case, this value may need to be updated. + constexpr double tolerance_pct = 1.0; + + // Set up the entries as simple integers. + std::vector> entries; + entries.reserve(weights.size()); + for (size_t i = 0; i < weights.size(); ++i) { + entries.emplace_back(std::make_shared(i)); + } + + absl::flat_hash_map sched_picks; + auto calc_weight = [&weights](const size_t& i) -> double { return weights[i]; }; + + for (uint64_t i = 0; i < iterations; ++i) { + // Create a scheduler with the given weights with a random number of + // emulated pre-picks. + uint32_t r = rand.random(); + auto sched = EdfScheduler::createWithPicks(entries, calc_weight, r); + + // Perform a "first-pick" from that scheduler, and increase the counter for + // that entry. + sched_picks[*sched.pickAndAdd(calc_weight)]++; + } + + // Validate that the observed distribution and expected weights are close. + ASSERT_EQ(weights.size(), sched_picks.size()); + for (const auto& it : sched_picks) { + const double expected = calc_weight(it.first); + const double observed = 100 * static_cast(it.second) / iterations; + EXPECT_NEAR(expected, observed, tolerance_pct); + } +} + +// Validates that after creating schedulers using the createWithPicks (with random picks) +// and then performing a "first-pick", the distribution of the "first-picks" is +// equal to the weights. +TEST_F(EdfSchedulerTest, SchedulerWithRandomPicksFirstPickDistribution) { + firstPickTest({25.0, 75.0}); + firstPickTest({1.0, 99.0}); + firstPickTest({50.0, 50.0}); + firstPickTest({1.0, 20.0, 79.0}); +} + +constexpr uint64_t BATCH_SIZE = 50; +static std::vector picksStarts() { + std::vector start_idxs; + // Add the first range, as it starts at 1 (and not 0). + start_idxs.emplace_back(1); + // The weight delta between iterations is 0.001, so to cover the range + // from 0 to 100, the largest start_idx will be 100 / 0.001. + for (uint64_t i = 50; i < 100 * 1000; i += BATCH_SIZE) { + start_idxs.emplace_back(i); + } + return start_idxs; +} + +class EdfSchedulerSpecialTest : public testing::TestWithParam {}; +// Validates that after creating schedulers using the createWithPicks (with random picks) +// and then performing a "first-pick", the distribution of the "first-picks" is +// equal to the weights. Trying the case of 2 weights between 0 to 100, in steps +// of 0.001. This test takes too long, and therefore it is disabled by default. +// If the EDF scheduler is enable, it can be manually executed. +TEST_P(EdfSchedulerSpecialTest, DISABLED_ExhaustiveValidator) { + const uint64_t start_idx = GetParam(); + for (uint64_t i = start_idx; i < start_idx + BATCH_SIZE; ++i) { + const double w1 = 0.001 * i; + ENVOY_LOG_MISC(trace, "Testing weights: w1={}, w2={}", w1, 100.0 - w1); + firstPickTest({w1, 100.0 - w1}); + } +} + +INSTANTIATE_TEST_SUITE_P(ExhustiveValidator, EdfSchedulerSpecialTest, + testing::ValuesIn(picksStarts())); + } // namespace Upstream } // namespace Envoy diff --git a/test/common/upstream/host_utility_test.cc b/test/common/upstream/host_utility_test.cc index e0df8d442fd60..af6580e41f382 100644 --- a/test/common/upstream/host_utility_test.cc +++ b/test/common/upstream/host_utility_test.cc @@ -61,7 +61,7 @@ TEST(HostUtilityTest, All) { #undef SET_HEALTH_FLAG EXPECT_EQ("/failed_active_hc/failed_outlier_check/failed_eds_health/degraded_active_hc/" "degraded_eds_health/pending_dynamic_removal/pending_active_hc/" - "excluded_via_immediate_hc_fail/active_hc_timeout", + "excluded_via_immediate_hc_fail/active_hc_timeout/eds_status_draining", HostUtility::healthFlagsToString(*host)); } diff --git a/test/common/upstream/load_balancer_benchmark.cc b/test/common/upstream/load_balancer_benchmark.cc index cc49c23f55947..9c12760cc17b3 100644 --- a/test/common/upstream/load_balancer_benchmark.cc +++ b/test/common/upstream/load_balancer_benchmark.cc @@ -51,10 +51,10 @@ class BaseTester : public Event::TestUsingSimulatedTime { HostVectorConstSharedPtr updated_hosts = std::make_shared(hosts); HostsPerLocalityConstSharedPtr hosts_per_locality = makeHostsPerLocality({hosts}); priority_set_.updateHosts(0, HostSetImpl::partitionHosts(updated_hosts, hosts_per_locality), {}, - hosts, {}, absl::nullopt); + hosts, {}, random_.random(), absl::nullopt); local_priority_set_.updateHosts(0, HostSetImpl::partitionHosts(updated_hosts, hosts_per_locality), - {}, hosts, {}, absl::nullopt); + {}, hosts, {}, random_.random(), absl::nullopt); } Envoy::Thread::MutexBasicLockable lock_; diff --git a/test/common/upstream/load_balancer_impl_test.cc b/test/common/upstream/load_balancer_impl_test.cc index 518f2a4de1d00..4ed88b7652e03 100644 --- a/test/common/upstream/load_balancer_impl_test.cc +++ b/test/common/upstream/load_balancer_impl_test.cc @@ -11,6 +11,7 @@ #include "envoy/config/core/v3/base.pb.h" #include "envoy/config/core/v3/health_check.pb.h" +#include "source/common/common/random_generator.h" #include "source/common/network/utility.h" #include "source/common/upstream/load_balancer_impl.h" #include "source/common/upstream/upstream_impl.h" @@ -728,7 +729,7 @@ class RoundRobinLoadBalancerTest : public LoadBalancerTestBase { 0, updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, empty_host_vector_, empty_host_vector_, absl::nullopt); + {}, empty_host_vector_, empty_host_vector_, random_.random(), absl::nullopt); } void peekThenPick(std::vector picks) { @@ -2880,6 +2881,96 @@ TEST_P(LeastRequestLoadBalancerTest, PNC) { EXPECT_EQ(hostSet().healthy_hosts_[3], lb_5.chooseHost(nullptr)); } +TEST_P(LeastRequestLoadBalancerTest, DefaultSelectionMethod) { + envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest lr_lb_config; + EXPECT_EQ(lr_lb_config.selection_method(), + envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest::N_CHOICES); +} + +TEST_P(LeastRequestLoadBalancerTest, FullScanOneHostWithLeastRequests) { + hostSet().healthy_hosts_ = {makeTestHost(info_, "tcp://127.0.0.1:80", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:81", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:82", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:83", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:84", simTime())}; + hostSet().hosts_ = hostSet().healthy_hosts_; + hostSet().runCallbacks({}, {}); // Trigger callbacks. The added/removed lists are not relevant. + + hostSet().healthy_hosts_[0]->stats().rq_active_.set(4); + hostSet().healthy_hosts_[1]->stats().rq_active_.set(3); + hostSet().healthy_hosts_[2]->stats().rq_active_.set(2); + hostSet().healthy_hosts_[3]->stats().rq_active_.set(1); + hostSet().healthy_hosts_[4]->stats().rq_active_.set(5); + + envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest lr_lb_config; + + // Enable FULL_SCAN on hosts. + lr_lb_config.set_selection_method( + envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest::FULL_SCAN); + + LeastRequestLoadBalancer lb{priority_set_, nullptr, stats_, runtime_, + random_, 1, lr_lb_config, simTime()}; + + // With FULL_SCAN we will always choose the host with least number of active requests. + EXPECT_EQ(hostSet().healthy_hosts_[3], lb.chooseHost(nullptr)); +} + +TEST_P(LeastRequestLoadBalancerTest, FullScanMultipleHostsWithLeastRequests) { + hostSet().healthy_hosts_ = {makeTestHost(info_, "tcp://127.0.0.1:80", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:81", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:82", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:83", simTime()), + makeTestHost(info_, "tcp://127.0.0.1:84", simTime())}; + hostSet().hosts_ = hostSet().healthy_hosts_; + hostSet().runCallbacks({}, {}); // Trigger callbacks. The added/removed lists are not relevant. + + hostSet().healthy_hosts_[0]->stats().rq_active_.set(3); + hostSet().healthy_hosts_[1]->stats().rq_active_.set(3); + hostSet().healthy_hosts_[2]->stats().rq_active_.set(1); + hostSet().healthy_hosts_[3]->stats().rq_active_.set(1); + hostSet().healthy_hosts_[4]->stats().rq_active_.set(1); + + envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest lr_lb_config; + + // Enable FULL_SCAN on hosts. + lr_lb_config.set_selection_method( + envoy::extensions::load_balancing_policies::least_request::v3::LeastRequest::FULL_SCAN); + + auto random = Random::RandomGeneratorImpl(); + + LeastRequestLoadBalancer lb{priority_set_, nullptr, stats_, runtime_, + random, 1, lr_lb_config, simTime()}; + + // Make 1 million selections. Then, check that the selection probability is + // approximately equal among the 3 hosts tied for least requests. + // Accept a +/-0.5% deviation from the expected selection probability (33.3..%). + size_t num_selections = 1000000; + size_t expected_approx_selections_per_tied_host = num_selections / 3; + size_t abs_error = 5000; + + size_t host_2_counts = 0; + size_t host_3_counts = 0; + size_t host_4_counts = 0; + + for (size_t i = 0; i < num_selections; ++i) { + auto selected_host = lb.chooseHost(nullptr); + + if (selected_host == hostSet().healthy_hosts_[2]) { + ++host_2_counts; + } else if (selected_host == hostSet().healthy_hosts_[3]) { + ++host_3_counts; + } else if (selected_host == hostSet().healthy_hosts_[4]) { + ++host_4_counts; + } else { + FAIL() << "Must only select hosts with least requests"; + } + } + + EXPECT_NEAR(expected_approx_selections_per_tied_host, host_2_counts, abs_error); + EXPECT_NEAR(expected_approx_selections_per_tied_host, host_3_counts, abs_error); + EXPECT_NEAR(expected_approx_selections_per_tied_host, host_4_counts, abs_error); +} + TEST_P(LeastRequestLoadBalancerTest, WeightImbalance) { hostSet().healthy_hosts_ = {makeTestHost(info_, "tcp://127.0.0.1:80", simTime(), 1), makeTestHost(info_, "tcp://127.0.0.1:81", simTime(), 2)}; diff --git a/test/common/upstream/load_balancer_simulation_test.cc b/test/common/upstream/load_balancer_simulation_test.cc index 1ec475438a881..d223b5c48ea65 100644 --- a/test/common/upstream/load_balancer_simulation_test.cc +++ b/test/common/upstream/load_balancer_simulation_test.cc @@ -93,20 +93,20 @@ void leastRequestLBWeightTest(LRLBTestParams params) { } HostVectorConstSharedPtr updated_hosts{new HostVector(hosts)}; HostsPerLocalitySharedPtr updated_locality_hosts{new HostsPerLocalityImpl(hosts)}; + Random::RandomGeneratorImpl random; PrioritySetImpl priority_set; priority_set.updateHosts( 0, updateHostsParams(updated_hosts, updated_locality_hosts, std::make_shared(*updated_hosts), updated_locality_hosts), - {}, hosts, {}, absl::nullopt); + {}, hosts, {}, random.random(), absl::nullopt); Stats::IsolatedStoreImpl stats_store; ClusterLbStatNames stat_names(stats_store.symbolTable()); ClusterLbStats lb_stats{stat_names, *stats_store.rootScope()}; NiceMock runtime; auto time_source = std::make_unique>(); - Random::RandomGeneratorImpl random; envoy::config::cluster::v3::Cluster::LeastRequestLbConfig least_request_lb_config; envoy::config::cluster::v3::Cluster::CommonLbConfig common_config; LeastRequestLoadBalancer lb_{ @@ -264,7 +264,7 @@ class DISABLED_SimulationTest : public testing::Test { // NOLINT(readability-ide updateHostsParams(originating_hosts, per_zone_local_shared, std::make_shared(*originating_hosts), per_zone_local_shared), - {}, empty_vector_, empty_vector_, absl::nullopt); + {}, empty_vector_, empty_vector_, random_.random(), absl::nullopt); HostConstSharedPtr selected = lb.chooseHost(nullptr); hits[selected->address()->asString()]++; diff --git a/test/common/upstream/upstream_impl_test.cc b/test/common/upstream/upstream_impl_test.cc index a825d39cadd01..1d13955a2ca8b 100644 --- a/test/common/upstream/upstream_impl_test.cc +++ b/test/common/upstream/upstream_impl_test.cc @@ -50,6 +50,7 @@ #include "test/mocks/upstream/typed_load_balancer_factory.h" #include "test/test_common/environment.h" #include "test/test_common/registry.h" +#include "test/test_common/test_runtime.h" #include "test/test_common/utility.h" #include "gmock/gmock.h" @@ -1616,6 +1617,115 @@ TEST_F(HostImplTest, ProxyOverridesHappyEyeballs) { EXPECT_EQ(connection, connection_data.connection_.get()); } +TEST_F(HostImplTest, CreateConnectionHappyEyeballsWithConfig) { + TestScopedRuntime scoped_runtime; + scoped_runtime.mergeValues({{"envoy.reloadable_features.use_config_in_happy_eyeballs", "true"}}); + MockClusterMockPrioritySet cluster; + + // pass in custom happy_eyeballs_config + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig config; + config.set_first_address_family_version( + envoy::config::cluster::v3::UpstreamConnectionOptions::V4); + config.mutable_first_address_family_count()->set_value(2); + EXPECT_CALL(*(cluster.info_), happyEyeballsConfig()) + .WillRepeatedly(Return(absl::make_optional(config))); + + envoy::config::core::v3::Metadata metadata; + Config::Metadata::mutableMetadataValue(metadata, Config::MetadataFilters::get().ENVOY_LB, + Config::MetadataEnvoyLbKeys::get().CANARY) + .set_bool_value(true); + envoy::config::core::v3::Locality locality; + locality.set_region("oceania"); + locality.set_zone("hello"); + locality.set_sub_zone("world"); + Network::Address::InstanceConstSharedPtr address = + Network::Utility::resolveUrl("tcp://[1:2:3::4]:8"); + auto host = std::make_shared( + cluster.info_, "lyft.com", address, + std::make_shared(metadata), 1, locality, + envoy::config::endpoint::v3::Endpoint::HealthCheckConfig::default_instance(), 1, + envoy::config::core::v3::UNKNOWN, simTime()); + + testing::StrictMock dispatcher; + Network::TransportSocketOptionsConstSharedPtr transport_socket_options; + Network::ConnectionSocket::OptionsSharedPtr options; + Network::MockTransportSocketFactory socket_factory; + + std::vector address_list = { + address, + Network::Utility::resolveUrl("tcp://10.0.0.1:1235"), + }; + host->setAddressList(address_list); + auto connection = new testing::StrictMock(); + EXPECT_CALL(*connection, setBufferLimits(0)); + EXPECT_CALL(*connection, addConnectionCallbacks(_)); + EXPECT_CALL(*connection, connectionInfoSetter()); + // Happy eyeballs config specifies the first address family is V4 + // The underlying connection should be created with the second address(V4) in the + // list. + EXPECT_CALL(dispatcher, createClientConnection_(address_list[1], _, _, _)) + .WillOnce(Return(connection)); + EXPECT_CALL(dispatcher, createTimer_(_)); + + Envoy::Upstream::Host::CreateConnectionData connection_data = + host->createConnection(dispatcher, options, transport_socket_options); + // The created connection will be wrapped in a HappyEyeballsConnectionImpl. + EXPECT_NE(connection, connection_data.connection_.get()); +} + +TEST_F(HostImplTest, CreateConnectionHappyEyeballsWithEmptyConfig) { + TestScopedRuntime scoped_runtime; + scoped_runtime.mergeValues({{"envoy.reloadable_features.use_config_in_happy_eyeballs", "true"}}); + MockClusterMockPrioritySet cluster; + + // pass in empty happy_eyeballs_config + // a default config will be created when flag turned on + EXPECT_CALL(*(cluster.info_), happyEyeballsConfig()).WillRepeatedly(Return(absl::nullopt)); + + envoy::config::core::v3::Metadata metadata; + Config::Metadata::mutableMetadataValue(metadata, Config::MetadataFilters::get().ENVOY_LB, + Config::MetadataEnvoyLbKeys::get().CANARY) + .set_bool_value(true); + envoy::config::core::v3::Locality locality; + locality.set_region("oceania"); + locality.set_zone("hello"); + locality.set_sub_zone("world"); + Network::Address::InstanceConstSharedPtr address = + Network::Utility::resolveUrl("tcp://[1:2:3::4]:8"); + auto host = std::make_shared( + cluster.info_, "lyft.com", address, + std::make_shared(metadata), 1, locality, + envoy::config::endpoint::v3::Endpoint::HealthCheckConfig::default_instance(), 1, + envoy::config::core::v3::UNKNOWN, simTime()); + + testing::StrictMock dispatcher; + Network::TransportSocketOptionsConstSharedPtr transport_socket_options; + Network::ConnectionSocket::OptionsSharedPtr options; + Network::MockTransportSocketFactory socket_factory; + + std::vector address_list = { + address, + Network::Utility::resolveUrl("tcp://10.0.0.1:1235"), + }; + host->setAddressList(address_list); + auto connection = new testing::StrictMock(); + EXPECT_CALL(*connection, setBufferLimits(0)); + EXPECT_CALL(*connection, addConnectionCallbacks(_)); + EXPECT_CALL(*connection, connectionInfoSetter()); + // Happy eyeballs config is empty, the default behavior is respecting the + // native order of returned destination addresses. + // The underlying connection should be created with the first address in the + // list. + EXPECT_CALL(dispatcher, createClientConnection_(address_list[0], _, _, _)) + .WillOnce(Return(connection)); + EXPECT_CALL(dispatcher, createTimer_(_)); + + Envoy::Upstream::Host::CreateConnectionData connection_data = + host->createConnection(dispatcher, options, transport_socket_options); + // The created connection will be wrapped in a HappyEyeballsConnectionImpl. + EXPECT_NE(connection, connection_data.connection_.get()); +} + TEST_F(HostImplTest, HealthFlags) { MockClusterMockPrioritySet cluster; HostSharedPtr host = makeTestHost(cluster.info_, "tcp://10.0.0.1:1234", simTime(), 1); @@ -1673,7 +1783,7 @@ TEST_F(HostImplTest, HealthStatus) { EXPECT_EQ(Host::HealthStatus::DRAINING, host->edsHealthStatus()); EXPECT_EQ(Host::Health::Unhealthy, host->coarseHealth()); // Old EDS flags should be cleared and new flag will be set. - EXPECT_TRUE(host->healthFlagGet(Host::HealthFlag::FAILED_EDS_HEALTH)); + EXPECT_TRUE(host->healthFlagGet(Host::HealthFlag::EDS_STATUS_DRAINING)); // Setting an active unhealthy flag make the host unhealthy. host->healthFlagSet(Host::HealthFlag::FAILED_ACTIVE_HC); @@ -3463,6 +3573,35 @@ TEST_F(StaticClusterImplTest, CustomUpstreamLocalAddressSelector) { .address_->asString()); } +TEST_F(StaticClusterImplTest, HappyEyeballsConfig) { + const std::string yaml = R"EOF( + name: name + connect_timeout: 0.25s + type: STATIC + lb_policy: ROUND_ROBIN + upstream_connection_options: + happy_eyeballs_config: + first_address_family_version: V4 + first_address_family_count: 1 + )EOF"; + auto cluster_config = parseClusterFromV3Yaml(yaml); + Envoy::Upstream::ClusterFactoryContextImpl factory_context( + server_context_, server_context_.cluster_manager_, nullptr, ssl_context_manager_, nullptr, + false); + std::shared_ptr cluster = createCluster(cluster_config, factory_context); + cluster->initialize([] {}); + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig expected_config; + expected_config.set_first_address_family_version( + envoy::config::cluster::v3::UpstreamConnectionOptions::V4); + uint32_t expected_count(1); + expected_config.mutable_first_address_family_count()->set_value(expected_count); + EXPECT_TRUE(cluster->info()->happyEyeballsConfig().has_value()); + EXPECT_EQ(cluster->info()->happyEyeballsConfig().value().first_address_family_version(), + envoy::config::cluster::v3::UpstreamConnectionOptions::V4); + EXPECT_EQ(cluster->info()->happyEyeballsConfig().value().first_address_family_count().value(), + expected_count); +} + class ClusterImplTest : public testing::Test, public UpstreamImplTestBase {}; // Test that the correct feature() is set when close_connections_on_host_health_failure is @@ -3512,7 +3651,7 @@ class TestBatchUpdateCb : public PrioritySet::BatchUpdateCb { updateHostsParams(hosts_, hosts_per_locality_, std::make_shared(*hosts_), hosts_per_locality_), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, random_.random(), absl::nullopt, absl::nullopt); } // Remove the host from P1. @@ -3525,12 +3664,13 @@ class TestBatchUpdateCb : public PrioritySet::BatchUpdateCb { updateHostsParams(empty_hosts, HostsPerLocalityImpl::empty(), std::make_shared(*empty_hosts), HostsPerLocalityImpl::empty()), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt); + {}, hosts_added, hosts_removed, random_.random(), absl::nullopt, absl::nullopt); } } HostVectorSharedPtr hosts_; HostsPerLocalitySharedPtr hosts_per_locality_; + TestRandomGenerator random_; }; // Test creating and extending a priority set. @@ -3578,11 +3718,12 @@ TEST(PrioritySet, Extend) { HostVector hosts_added{hosts->front()}; HostVector hosts_removed{}; - priority_set.updateHosts( - 1, - updateHostsParams(hosts, hosts_per_locality, - std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt, absl::nullopt, fake_cross_priority_host_map); + priority_set.updateHosts(1, + updateHostsParams(hosts, hosts_per_locality, + std::make_shared(*hosts), + hosts_per_locality), + {}, hosts_added, hosts_removed, 0, absl::nullopt, absl::nullopt, + fake_cross_priority_host_map); } EXPECT_EQ(1, priority_changes); EXPECT_EQ(1, membership_changes); @@ -3647,7 +3788,7 @@ TEST(PrioritySet, MainPrioritySetTest) { updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt); + {}, hosts_added, hosts_removed, 0, absl::nullopt); } // Only mutable host map can be updated directly. Read only host map will not be updated before @@ -3668,7 +3809,7 @@ TEST(PrioritySet, MainPrioritySetTest) { updateHostsParams(hosts, hosts_per_locality, std::make_shared(*hosts), hosts_per_locality), - {}, hosts_added, hosts_removed, absl::nullopt); + {}, hosts_added, hosts_removed, 0, absl::nullopt); } // New mutable host map will be created and all update will be applied to new mutable host map. @@ -4394,7 +4535,7 @@ class TestFilterConfigFactoryBase { : empty_proto_(empty_proto), config_(config) {} ProtobufTypes::MessagePtr createEmptyProtocolOptionsProto() { return empty_proto_(); } - Upstream::ProtocolOptionsConfigConstSharedPtr + absl::StatusOr createProtocolOptionsConfig(const Protobuf::Message& msg) { return config_(msg); } @@ -4418,7 +4559,7 @@ class TestNetworkFilterConfigFactory ProtobufTypes::MessagePtr createEmptyProtocolOptionsProto() override { return parent_.createEmptyProtocolOptionsProto(); } - Upstream::ProtocolOptionsConfigConstSharedPtr + absl::StatusOr createProtocolOptionsConfig(const Protobuf::Message& msg, Server::Configuration::ProtocolOptionsFactoryContext&) override { return parent_.createProtocolOptionsConfig(msg); @@ -4451,7 +4592,7 @@ class TestHttpFilterConfigFactory : public Server::Configuration::NamedHttpFilte ProtobufTypes::MessagePtr createEmptyProtocolOptionsProto() override { return parent_.createEmptyProtocolOptionsProto(); } - Upstream::ProtocolOptionsConfigConstSharedPtr + absl::StatusOr createProtocolOptionsConfig(const Protobuf::Message& msg, Server::Configuration::ProtocolOptionsFactoryContext&) override { return parent_.createProtocolOptionsConfig(msg); @@ -5400,7 +5541,7 @@ TEST_F(HostSetImplLocalityTest, AllUnhealthy) { LocalityWeightsConstSharedPtr locality_weights{new LocalityWeights{1, 1, 1}}; auto hosts_const_shared = std::make_shared(hosts); host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality), locality_weights, - {}, {}, absl::nullopt); + {}, {}, 0, absl::nullopt); EXPECT_FALSE(host_set_.chooseHealthyLocality().has_value()); } @@ -5436,7 +5577,7 @@ TEST_F(HostSetImplLocalityTest, NotWarmedHostsLocality) { HostsPerLocalityImpl::empty(), makeHostsFromHostsPerLocality(excluded_hosts_per_locality), excluded_hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); // We should RR between localities with equal weight. EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); @@ -5459,7 +5600,7 @@ TEST_F(HostSetImplLocalityTest, EmptyLocality) { host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, std::make_shared(hosts), hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); // Verify that we are not RRing between localities. EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); @@ -5480,7 +5621,7 @@ TEST_F(HostSetImplLocalityTest, AllZeroWeights) { host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, std::make_shared(hosts), hosts_per_locality), - locality_weights, {}, {}); + locality_weights, {}, {}, 0); EXPECT_FALSE(host_set_.chooseHealthyLocality().has_value()); } @@ -5503,7 +5644,7 @@ TEST_F(HostSetImplLocalityTest, Unweighted) { host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, std::make_shared(hosts), hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(2, host_set_.chooseHealthyLocality().value()); @@ -5527,7 +5668,7 @@ TEST_F(HostSetImplLocalityTest, Weighted) { host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, std::make_shared(hosts), hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); @@ -5555,7 +5696,7 @@ TEST_F(HostSetImplLocalityTest, MissingWeight) { host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, std::make_shared(hosts), hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(2, host_set_.chooseHealthyLocality().value()); EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); @@ -5564,6 +5705,77 @@ TEST_F(HostSetImplLocalityTest, MissingWeight) { EXPECT_EQ(2, host_set_.chooseHealthyLocality().value()); } +// Validates that with weighted initialization all localities are chosen +// proportionally to their weight. +TEST_F(HostSetImplLocalityTest, WeightedAllChosen) { + // This test should remain when envoy.reloadable_features.edf_lb_locality_scheduler_init_fix + // is deprecated. + TestScopedRuntime scoped_runtime; + scoped_runtime.mergeValues( + {{"envoy.reloadable_features.edf_lb_locality_scheduler_init_fix", "true"}}); + envoy::config::core::v3::Locality zone_a; + zone_a.set_zone("A"); + envoy::config::core::v3::Locality zone_b; + zone_b.set_zone("B"); + envoy::config::core::v3::Locality zone_c; + zone_b.set_zone("C"); + HostVector hosts{makeTestHost(info_, "tcp://127.0.0.1:80", simTime(), zone_a), + makeTestHost(info_, "tcp://127.0.0.1:81", simTime(), zone_b), + makeTestHost(info_, "tcp://127.0.0.1:82", simTime(), zone_c)}; + + HostsPerLocalitySharedPtr hosts_per_locality = + makeHostsPerLocality({{hosts[0]}, {hosts[1]}, {hosts[2]}}); + // Set weights of 10%, 60% and 30% to the three zones. + LocalityWeightsConstSharedPtr locality_weights{new LocalityWeights{1, 6, 3}}; + + // Keep track of how many times each locality is picked, initialized to 0. + uint32_t locality_picked_count[] = {0, 0, 0}; + + // Create the load-balancer 10 times, each with a different seed number (from + // 0 to 10), do a single pick, and validate that the number of picks equals + // to the weights assigned to the localities. + auto hosts_const_shared = std::make_shared(hosts); + for (uint32_t i = 0; i < 10; ++i) { + host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, + std::make_shared(hosts), + hosts_per_locality), + locality_weights, {}, {}, i, absl::nullopt); + locality_picked_count[host_set_.chooseHealthyLocality().value()]++; + } + EXPECT_EQ(locality_picked_count[0], 1); + EXPECT_EQ(locality_picked_count[1], 6); + EXPECT_EQ(locality_picked_count[2], 3); +} + +// Validates that the non-randomized initialization works. This test should be +// removed when envoy.reloadable_features.edf_lb_locality_scheduler_init_fix +// is deprecated. +TEST_F(HostSetImplLocalityTest, WeightedNoRandomization) { + TestScopedRuntime scoped_runtime; + scoped_runtime.mergeValues( + {{"envoy.reloadable_features.edf_lb_locality_scheduler_init_fix", "false"}}); + envoy::config::core::v3::Locality zone_a; + zone_a.set_zone("A"); + envoy::config::core::v3::Locality zone_b; + zone_b.set_zone("B"); + HostVector hosts{makeTestHost(info_, "tcp://127.0.0.1:80", simTime(), zone_a), + makeTestHost(info_, "tcp://127.0.0.1:81", simTime(), zone_b)}; + + HostsPerLocalitySharedPtr hosts_per_locality = makeHostsPerLocality({{hosts[0]}, {hosts[1]}}); + LocalityWeightsConstSharedPtr locality_weights{new LocalityWeights{1, 2}}; + auto hosts_const_shared = std::make_shared(hosts); + host_set_.updateHosts(updateHostsParams(hosts_const_shared, hosts_per_locality, + std::make_shared(hosts), + hosts_per_locality), + locality_weights, {}, {}, 0, absl::nullopt); + EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); + EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); + EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); + EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); + EXPECT_EQ(0, host_set_.chooseHealthyLocality().value()); + EXPECT_EQ(1, host_set_.chooseHealthyLocality().value()); +} + // Gentle failover between localities as health diminishes. TEST_F(HostSetImplLocalityTest, UnhealthyFailover) { envoy::config::core::v3::Locality zone_a; @@ -5593,7 +5805,7 @@ TEST_F(HostSetImplLocalityTest, UnhealthyFailover) { makeHostsFromHostsPerLocality( healthy_hosts_per_locality), healthy_hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); }; const auto expectPicks = [this](uint32_t locality_0_picks, uint32_t locality_1_picks) { @@ -5646,7 +5858,7 @@ TEST(OverProvisioningFactorTest, LocalityPickChanges) { host_set.updateHosts(updateHostsParams(std::make_shared(hosts), hosts_per_locality, healthy_hosts, healthy_hosts_per_locality), - locality_weights, {}, {}, absl::nullopt); + locality_weights, {}, {}, 0, absl::nullopt); uint32_t cnts[] = {0, 0}; for (uint32_t i = 0; i < 100; ++i) { absl::optional locality_index = host_set.chooseHealthyLocality(); @@ -5682,6 +5894,7 @@ TEST(HostPartitionTest, PartitionHosts) { makeTestHost(info, "tcp://127.0.0.1:81", *time_source, zone_a), makeTestHost(info, "tcp://127.0.0.1:82", *time_source, zone_b), makeTestHost(info, "tcp://127.0.0.1:83", *time_source, zone_b), + makeTestHost(info, "tcp://127.0.0.1:84", *time_source, zone_b), makeTestHost(info, "tcp://127.0.0.1:84", *time_source, zone_b)}; hosts[0]->healthFlagSet(Host::HealthFlag::FAILED_ACTIVE_HC); @@ -5690,24 +5903,26 @@ TEST(HostPartitionTest, PartitionHosts) { hosts[2]->healthFlagSet(Host::HealthFlag::FAILED_ACTIVE_HC); hosts[4]->healthFlagSet(Host::HealthFlag::EXCLUDED_VIA_IMMEDIATE_HC_FAIL); hosts[4]->healthFlagSet(Host::HealthFlag::FAILED_ACTIVE_HC); + hosts[5]->healthFlagSet(Host::HealthFlag::EDS_STATUS_DRAINING); auto hosts_per_locality = - makeHostsPerLocality({{hosts[0], hosts[1]}, {hosts[2], hosts[3], hosts[4]}}); + makeHostsPerLocality({{hosts[0], hosts[1]}, {hosts[2], hosts[3], hosts[4], hosts[5]}}); auto update_hosts_params = HostSetImpl::partitionHosts(std::make_shared(hosts), hosts_per_locality); - EXPECT_EQ(5, update_hosts_params.hosts->size()); + EXPECT_EQ(6, update_hosts_params.hosts->size()); EXPECT_EQ(1, update_hosts_params.healthy_hosts->get().size()); EXPECT_EQ(hosts[3], update_hosts_params.healthy_hosts->get()[0]); EXPECT_EQ(1, update_hosts_params.degraded_hosts->get().size()); EXPECT_EQ(hosts[1], update_hosts_params.degraded_hosts->get()[0]); - EXPECT_EQ(2, update_hosts_params.excluded_hosts->get().size()); + EXPECT_EQ(3, update_hosts_params.excluded_hosts->get().size()); EXPECT_EQ(hosts[2], update_hosts_params.excluded_hosts->get()[0]); EXPECT_EQ(hosts[4], update_hosts_params.excluded_hosts->get()[1]); + EXPECT_EQ(hosts[5], update_hosts_params.excluded_hosts->get()[2]); EXPECT_EQ(2, update_hosts_params.hosts_per_locality->get()[0].size()); - EXPECT_EQ(3, update_hosts_params.hosts_per_locality->get()[1].size()); + EXPECT_EQ(4, update_hosts_params.hosts_per_locality->get()[1].size()); EXPECT_EQ(0, update_hosts_params.healthy_hosts_per_locality->get()[0].size()); EXPECT_EQ(1, update_hosts_params.healthy_hosts_per_locality->get()[1].size()); @@ -5718,9 +5933,10 @@ TEST(HostPartitionTest, PartitionHosts) { EXPECT_EQ(hosts[1], update_hosts_params.degraded_hosts_per_locality->get()[0][0]); EXPECT_EQ(0, update_hosts_params.excluded_hosts_per_locality->get()[0].size()); - EXPECT_EQ(2, update_hosts_params.excluded_hosts_per_locality->get()[1].size()); + EXPECT_EQ(3, update_hosts_params.excluded_hosts_per_locality->get()[1].size()); EXPECT_EQ(hosts[2], update_hosts_params.excluded_hosts_per_locality->get()[1][0]); EXPECT_EQ(hosts[4], update_hosts_params.excluded_hosts_per_locality->get()[1][1]); + EXPECT_EQ(hosts[5], update_hosts_params.excluded_hosts_per_locality->get()[1][2]); } TEST_F(ClusterInfoImplTest, MaxRequestsPerConnectionValidation) { @@ -5814,9 +6030,11 @@ TEST_F(PriorityStateManagerTest, LocalityClusterUpdate) { cluster->initialize([] {}); EXPECT_EQ(1UL, cluster->prioritySet().hostSetsPerPriority()[0]->hosts().size()); + NiceMock random; // Make priority state manager and fill it with the initial state of the cluster and the added // hosts - PriorityStateManager priority_state_manager(*cluster, server_context_.local_info_, nullptr); + PriorityStateManager priority_state_manager(*cluster, server_context_.local_info_, nullptr, + random); auto current_hosts = cluster->prioritySet().hostSetsPerPriority()[0]->hosts(); HostVector hosts_added{makeTestHost(cluster->info(), "tcp://127.0.0.1:81", simTime(), zone_b), diff --git a/test/common/upstream/zone_aware_load_balancer_fuzz_base.cc b/test/common/upstream/zone_aware_load_balancer_fuzz_base.cc index e9ed21b67094c..16eb8dc0fad33 100644 --- a/test/common/upstream/zone_aware_load_balancer_fuzz_base.cc +++ b/test/common/upstream/zone_aware_load_balancer_fuzz_base.cc @@ -17,7 +17,7 @@ void ZoneAwareLoadBalancerFuzzBase::initializeASingleHostSet( const MockHostSet& host_set = *priority_set_.getMockHostSet(priority_level); const HostVector empty_host_vector; local_priority_set_->updateHosts(0, HostSetImpl::updateHostsParams(host_set), {}, - empty_host_vector, empty_host_vector, absl::nullopt); + empty_host_vector, empty_host_vector, 123, absl::nullopt); } } @@ -34,7 +34,7 @@ void ZoneAwareLoadBalancerFuzzBase::updateHealthFlagsForAHostSet( const MockHostSet& host_set = *priority_set_.getMockHostSet(priority_of_host_set); const HostVector empty_host_vector; local_priority_set_->updateHosts(0, HostSetImpl::updateHostsParams(host_set), {}, - empty_host_vector, empty_host_vector, absl::nullopt); + empty_host_vector, empty_host_vector, 123, absl::nullopt); } } diff --git a/test/config/utility.cc b/test/config/utility.cc index aef14b5bfbd0b..43f40bd93aeff 100644 --- a/test/config/utility.cc +++ b/test/config/utility.cc @@ -1712,7 +1712,7 @@ void ConfigHelper::adjustUpstreamTimeoutForTsan( auto* timeout = route->mutable_timeout(); // QUIC stream processing is slow under TSAN. Use larger timeout to prevent // response_timeout. - timeout->set_seconds(TSAN_TIMEOUT_FACTOR * timeout_ms / 1000); + timeout->set_seconds(TIMEOUT_FACTOR * timeout_ms / 1000); } envoy::config::core::v3::Http3ProtocolOptions ConfigHelper::http2ToHttp3ProtocolOptions( diff --git a/test/config_test/config_test.cc b/test/config_test/config_test.cc index c411375262901..c61c3168e8b80 100644 --- a/test/config_test/config_test.cc +++ b/test/config_test/config_test.cc @@ -99,7 +99,9 @@ class ConfigTest { envoy::config::bootstrap::v3::Bootstrap bootstrap; Server::InstanceUtil::loadBootstrapConfig( bootstrap, options_, server_.messageValidationContext().staticValidationVisitor(), *api_); - Server::Configuration::InitialImpl initial_config(bootstrap); + absl::Status creation_status; + Server::Configuration::InitialImpl initial_config(bootstrap, creation_status); + THROW_IF_NOT_OK(creation_status); Server::Configuration::MainImpl main_config; // Emulate main implementation of initializing bootstrap extensions. @@ -156,7 +158,7 @@ class ConfigTest { ON_CALL(server_, serverFactoryContext()).WillByDefault(ReturnRef(server_factory_context_)); try { - main_config.initialize(bootstrap, server_, *cluster_manager_factory_); + THROW_IF_NOT_OK(main_config.initialize(bootstrap, server_, *cluster_manager_factory_)); } catch (const EnvoyException& ex) { ADD_FAILURE() << fmt::format("'{}' config failed. Error: {}", options_.configPath(), ex.what()); diff --git a/test/extensions/access_loggers/grpc/http_grpc_access_log_impl_test.cc b/test/extensions/access_loggers/grpc/http_grpc_access_log_impl_test.cc index af156223967cf..9b095752ae50f 100644 --- a/test/extensions/access_loggers/grpc/http_grpc_access_log_impl_test.cc +++ b/test/extensions/access_loggers/grpc/http_grpc_access_log_impl_test.cc @@ -321,7 +321,7 @@ response: {} const std::string route_name("route-name-test"); ON_CALL(stream_info, getRouteName()).WillByDefault(ReturnRef(route_name)); - ON_CALL(stream_info, hasResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + ON_CALL(stream_info, hasResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .WillByDefault(Return(true)); stream_info.onRequestComplete(); diff --git a/test/extensions/clusters/aggregate/cluster_test.cc b/test/extensions/clusters/aggregate/cluster_test.cc index f78ccb511a338..cd844a4c91674 100644 --- a/test/extensions/clusters/aggregate/cluster_test.cc +++ b/test/extensions/clusters/aggregate/cluster_test.cc @@ -74,7 +74,7 @@ class AggregateClusterTest : public Event::TestUsingSimulatedTime, public testin priority, Upstream::HostSetImpl::partitionHosts(std::make_shared(hosts), Upstream::HostsPerLocalityImpl::empty()), - nullptr, hosts, {}, absl::nullopt, 100); + nullptr, hosts, {}, 123, absl::nullopt, 100); } void setupSecondary(int priority, int healthy_hosts, int degraded_hosts, int unhealthy_hosts) { @@ -84,7 +84,7 @@ class AggregateClusterTest : public Event::TestUsingSimulatedTime, public testin priority, Upstream::HostSetImpl::partitionHosts(std::make_shared(hosts), Upstream::HostsPerLocalityImpl::empty()), - nullptr, hosts, {}, absl::nullopt, 100); + nullptr, hosts, {}, 123, absl::nullopt, 100); } void setupPrioritySet() { @@ -180,7 +180,7 @@ TEST_F(AggregateClusterTest, LoadBalancerTest) { EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(nullptr)); for (int i = 0; i <= 65; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); EXPECT_TRUE(lb_->peekAnotherHost(nullptr) == nullptr); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); OptRef lifetime_callbacks = @@ -196,7 +196,7 @@ TEST_F(AggregateClusterTest, LoadBalancerTest) { EXPECT_CALL(primary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(nullptr)); EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(host)); for (int i = 66; i < 100; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -215,7 +215,7 @@ TEST_F(AggregateClusterTest, LoadBalancerTest) { EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(nullptr)); for (int i = 0; i <= 57; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -223,7 +223,7 @@ TEST_F(AggregateClusterTest, LoadBalancerTest) { EXPECT_CALL(primary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(nullptr)); EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(host)); for (int i = 58; i < 100; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -252,7 +252,7 @@ TEST_F(AggregateClusterTest, AllHostAreUnhealthyTest) { // Choose the first cluster as the second one is unavailable. for (int i = 0; i < 50; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -262,7 +262,7 @@ TEST_F(AggregateClusterTest, AllHostAreUnhealthyTest) { // Choose the second cluster as the first one is unavailable. for (int i = 50; i < 100; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -288,7 +288,7 @@ TEST_F(AggregateClusterTest, ClusterInPanicTest) { EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(nullptr)); for (int i = 0; i < 50; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -297,7 +297,7 @@ TEST_F(AggregateClusterTest, ClusterInPanicTest) { EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(host)); for (int i = 50; i < 100; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -317,7 +317,7 @@ TEST_F(AggregateClusterTest, ClusterInPanicTest) { EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(nullptr)); for (int i = 0; i <= 25; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } @@ -326,7 +326,7 @@ TEST_F(AggregateClusterTest, ClusterInPanicTest) { EXPECT_CALL(secondary_load_balancer_, chooseHost(_)).WillRepeatedly(Return(host)); for (int i = 26; i < 100; ++i) { - EXPECT_CALL(random_, random()).WillOnce(Return(i)); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(i)); Upstream::HostConstSharedPtr target = lb_->chooseHost(nullptr); EXPECT_EQ(host.get(), target.get()); } diff --git a/test/extensions/clusters/aggregate/cluster_update_test.cc b/test/extensions/clusters/aggregate/cluster_update_test.cc index 67c029b527990..281cd49b87e52 100644 --- a/test/extensions/clusters/aggregate/cluster_update_test.cc +++ b/test/extensions/clusters/aggregate/cluster_update_test.cc @@ -162,7 +162,7 @@ TEST_P(AggregateClusterUpdateTest, LoadBalancingTest) { Upstream::HostSetImpl::partitionHosts( std::make_shared(Upstream::HostVector{host1, host2, host3}), Upstream::HostsPerLocalityImpl::empty()), - nullptr, {host1, host2, host3}, {}, absl::nullopt, 100); + nullptr, {host1, host2, host3}, {}, 0, absl::nullopt, 100); // Set up the HostSet with 1 healthy, 1 degraded and 1 unhealthy. Upstream::HostSharedPtr host4 = @@ -179,7 +179,7 @@ TEST_P(AggregateClusterUpdateTest, LoadBalancingTest) { Upstream::HostSetImpl::partitionHosts( std::make_shared(Upstream::HostVector{host4, host5, host6}), Upstream::HostsPerLocalityImpl::empty()), - nullptr, {host4, host5, host6}, {}, absl::nullopt, 100); + nullptr, {host4, host5, host6}, {}, 0, absl::nullopt, 100); Upstream::HostConstSharedPtr host; for (int i = 0; i < 33; ++i) { @@ -219,7 +219,7 @@ TEST_P(AggregateClusterUpdateTest, LoadBalancingTest) { Upstream::HostSetImpl::partitionHosts( std::make_shared(Upstream::HostVector{host7, host8, host9}), Upstream::HostsPerLocalityImpl::empty()), - nullptr, {host7, host8, host9}, {}, absl::nullopt, 100); + nullptr, {host7, host8, host9}, {}, 0, absl::nullopt, 100); // Priority set // Priority 0: 1/3 healthy, 1/3 degraded @@ -306,7 +306,7 @@ TEST_P(AggregateClusterUpdateTest, InitializeAggregateClusterAfterOtherClusters) Upstream::HostSetImpl::partitionHosts( std::make_shared(Upstream::HostVector{host1, host2, host3}), Upstream::HostsPerLocalityImpl::empty()), - nullptr, {host1, host2, host3}, {}, absl::nullopt, 100); + nullptr, {host1, host2, host3}, {}, 0, absl::nullopt, 100); for (int i = 0; i < 50; ++i) { EXPECT_CALL(factory_.random_, random()).WillRepeatedly(Return(i)); diff --git a/test/extensions/clusters/dynamic_forward_proxy/cluster_test.cc b/test/extensions/clusters/dynamic_forward_proxy/cluster_test.cc index 75f48aadfdf73..7143bebb6da34 100644 --- a/test/extensions/clusters/dynamic_forward_proxy/cluster_test.cc +++ b/test/extensions/clusters/dynamic_forward_proxy/cluster_test.cc @@ -86,7 +86,7 @@ class ClusterTest : public testing::Test, } })); if (!existing_hosts.empty()) { - EXPECT_CALL(*this, onMemberUpdateCb(SizeIs(existing_hosts.size()), SizeIs(0))); + EXPECT_CALL(*this, onMemberUpdateCb(SizeIs(1), SizeIs(0))).Times(existing_hosts.size()); } cluster_->initialize([] {}); } @@ -257,6 +257,7 @@ TEST_F(ClusterTest, BasicFlow) { // After changing the address, LB will immediately resolve the new address with a refresh. updateTestHostAddress("host1:0", "2.3.4.5"); + EXPECT_CALL(*this, onMemberUpdateCb(SizeIs(1), SizeIs(1))); update_callbacks_->onDnsHostAddOrUpdate("host1:0", host_map_["host1:0"]); EXPECT_EQ(1UL, cluster_->prioritySet().hostSetsPerPriority()[0]->hosts().size()); EXPECT_EQ("2.3.4.5:0", diff --git a/test/extensions/clusters/original_dst/original_dst_cluster_test.cc b/test/extensions/clusters/original_dst/original_dst_cluster_test.cc index ae5d1a65de9a1..46d2e3c4211f0 100644 --- a/test/extensions/clusters/original_dst/original_dst_cluster_test.cc +++ b/test/extensions/clusters/original_dst/original_dst_cluster_test.cc @@ -661,7 +661,7 @@ TEST_F(OriginalDstClusterTest, MultipleClusters) { second.updateHosts(0, updateHostsParams(new_hosts, empty_hosts_per_locality, healthy_hosts, empty_hosts_per_locality), - {}, added, removed, absl::nullopt); + {}, added, removed, 0, absl::nullopt); }); EXPECT_CALL(membership_updated_, ready()); diff --git a/test/extensions/filters/common/expr/context_test.cc b/test/extensions/filters/common/expr/context_test.cc index 556424e8c3cc1..bd2b347ad7cc8 100644 --- a/test/extensions/filters/common/expr/context_test.cc +++ b/test/extensions/filters/common/expr/context_test.cc @@ -289,7 +289,7 @@ TEST(Context, ResponseAttributes) { EXPECT_CALL(info, responseCode()).WillRepeatedly(Return(404)); EXPECT_CALL(info, bytesSent()).WillRepeatedly(Return(123)); - EXPECT_CALL(info, responseFlags()).WillRepeatedly(Return(0x1)); + EXPECT_CALL(info, legacyResponseFlags()).WillRepeatedly(Return(0x1)); const absl::optional code_details = "unauthorized"; EXPECT_CALL(info, responseCodeDetails()).WillRepeatedly(ReturnRef(code_details)); @@ -856,7 +856,7 @@ TEST(Context, XDSAttributes) { info.downstream_connection_info_provider_->setListenerInfo(listener_info); Protobuf::Arena arena; - XDSWrapper wrapper(arena, info, &local_info); + XDSWrapper wrapper(arena, &info, &local_info); { const auto value = wrapper[CelValue::CreateStringView(ClusterName)]; diff --git a/test/extensions/filters/common/rbac/matchers_test.cc b/test/extensions/filters/common/rbac/matchers_test.cc index c1a1dd37fb18a..2ef2b577fceae 100644 --- a/test/extensions/filters/common/rbac/matchers_test.cc +++ b/test/extensions/filters/common/rbac/matchers_test.cc @@ -538,6 +538,50 @@ TEST(FilterStateMatcher, FilterStateMatcher) { checkMatcher(FilterStateMatcher(matcher), true, conn, header, info); } +TEST(UriTemplateMatcher, UriTemplateMatcherFactory) { + const std::string yaml_string = R"EOF( + name: envoy.path.match.uri_template.uri_template_matcher + typed_config: + "@type": type.googleapis.com/envoy.extensions.path.match.uri_template.v3.UriTemplateMatchConfig + path_template: "/bar/{lang}/{country}" +)EOF"; + Envoy::Http::TestRequestHeaderMapImpl headers; + headers.setPath("/bar/lang/country"); + + envoy::config::core::v3::TypedExtensionConfig config; + TestUtility::loadFromYaml(yaml_string, config); + + const auto& factory = + &Envoy::Config::Utility::getAndCheckFactory(config); + + EXPECT_NE(nullptr, factory); + EXPECT_EQ(factory->name(), "envoy.path.match.uri_template.uri_template_matcher"); + EXPECT_EQ(factory->category(), "envoy.path.match"); + + auto message = Envoy::Config::Utility::translateAnyToFactoryConfig( + config.typed_config(), ProtobufMessage::getStrictValidationVisitor(), *factory); + + const auto uri_template_matcher = UriTemplateMatcher(factory->createPathMatcher(*message)); + + checkMatcher(uri_template_matcher, true, Envoy::Network::MockConnection(), headers); +} + +TEST(UriTemplateMatcher, NoPathInHeader) { + Envoy::Http::TestRequestHeaderMapImpl headers; + envoy::extensions::path::match::uri_template::v3::UriTemplateMatchConfig + uri_template_match_config; + const std::string path_template = "/{foo}"; + uri_template_match_config.set_path_template(path_template); + Router::PathMatcherSharedPtr matcher = + std::make_shared( + uri_template_match_config); + + headers.setPath("/foo"); + checkMatcher(UriTemplateMatcher(matcher), true, Envoy::Network::MockConnection(), headers); + headers.removePath(); + checkMatcher(UriTemplateMatcher(matcher), false, Envoy::Network::MockConnection(), headers); +} + } // namespace } // namespace RBAC } // namespace Common diff --git a/test/extensions/filters/http/alternate_protocols_cache/filter_integration_test.cc b/test/extensions/filters/http/alternate_protocols_cache/filter_integration_test.cc index 984133f882159..6994b20314ab3 100644 --- a/test/extensions/filters/http/alternate_protocols_cache/filter_integration_test.cc +++ b/test/extensions/filters/http/alternate_protocols_cache/filter_integration_test.cc @@ -59,6 +59,16 @@ name: alternate_protocols_cache filename); config_helper_.prependFilter(filter); + // Set resource tracking on connection pools so we can explicitly check when + // they're created and torn down. + config_helper_.addConfigModifier([](envoy::config::bootstrap::v3::Bootstrap& bootstrap) { + auto* static_resources = bootstrap.mutable_static_resources(); + auto* cluster = static_resources->mutable_clusters(0); + auto* circuit_breakers = cluster->mutable_circuit_breakers(); + circuit_breakers->add_thresholds()->mutable_max_connection_pools()->set_value(100); + circuit_breakers->mutable_thresholds(0)->set_track_remaining(true); + }); + upstream_tls_ = true; // This configures the upstream to use the connection grid (automatically // selecting protocol and allowing HTTP/3) @@ -217,6 +227,8 @@ TEST_P(FilterIntegrationTest, AltSvcCachedH3Slow) { FakeHttpConnectionPtr h3_connection; waitForNextUpstreamConnection(std::vector{1}, TestUtility::DefaultTimeout, h3_connection); + // Of the 100 connection pools configured, the grid registers as taking up one. + test_server_->waitForGaugeEq("cluster.cluster_0.circuit_breakers.default.remaining_cx_pools", 99); // The created stream will reset. FakeStreamPtr upstream_request2; @@ -242,9 +254,15 @@ TEST_P(FilterIntegrationTest, AltSvcCachedH3Slow) { checkSimpleRequestSuccess(request_size, response_size, response.get()); test_server_->waitForCounterEq("cluster.cluster_0.upstream_cx_http3_total", 1); + + cleanupUpstreamAndDownstream(); + // Wait for the grid to be torn down to make sure it is not problematic. + test_server_->waitForGaugeEq("cluster.cluster_0.circuit_breakers.default.remaining_cx_pools", + 100); } -TEST_P(FilterIntegrationTest, AltSvcCachedH2Slow) { +// TODO(32151): Figure out why it's flaky and re-enable. +TEST_P(FilterIntegrationTest, DISABLED_AltSvcCachedH2Slow) { #ifdef WIN32 // TODO: sort out what race only happens on windows and GCC. GTEST_SKIP() << "Skipping on Windows"; @@ -254,6 +272,7 @@ TEST_P(FilterIntegrationTest, AltSvcCachedH2Slow) { #endif // Start with the alt-svc header in the cache. write_alt_svc_to_file_ = true; + config_helper_.setConnectTimeout(std::chrono::seconds(1)); const uint64_t request_size = 0; const uint64_t response_size = 0; @@ -286,6 +305,8 @@ TEST_P(FilterIntegrationTest, AltSvcCachedH2Slow) { // Wait for both connections to be attempted. test_server_->waitForCounterEq("cluster.cluster_0.upstream_cx_total", 2); + // Of the 100 connection pools configured, the grid registers as taking up one. + test_server_->waitForGaugeEq("cluster.cluster_0.circuit_breakers.default.remaining_cx_pools", 99); // Unblock Http3. block_http3.Notify(); @@ -299,6 +320,11 @@ TEST_P(FilterIntegrationTest, AltSvcCachedH2Slow) { // Make sure the response is completed. ASSERT_TRUE(response->waitForEndStream(timeout)); checkSimpleRequestSuccess(request_size, response_size, response.get()); + + cleanupUpstreamAndDownstream(); + // Wait for the grid to be torn down to make sure it is not problematic. + test_server_->waitForGaugeEq("cluster.cluster_0.circuit_breakers.default.remaining_cx_pools", + 100); } TEST_P(FilterIntegrationTest, AltSvcIgnoredWithProxyConfig) { diff --git a/test/extensions/filters/http/aws_request_signing/BUILD b/test/extensions/filters/http/aws_request_signing/BUILD index 50a1c90cdbd5e..8d2f213cc31d2 100644 --- a/test/extensions/filters/http/aws_request_signing/BUILD +++ b/test/extensions/filters/http/aws_request_signing/BUILD @@ -32,3 +32,16 @@ envoy_extension_cc_test( "@envoy_api//envoy/extensions/filters/http/aws_request_signing/v3:pkg_cc_proto", ], ) + +envoy_extension_cc_test( + name = "aws_request_signing_integration_test", + srcs = ["aws_request_signing_integration_test.cc"], + extension_names = ["envoy.filters.http.aws_request_signing"], + deps = [ + "//source/extensions/filters/http/aws_request_signing:aws_request_signing_filter_lib", + "//source/extensions/filters/http/aws_request_signing:config", + "//test/extensions/common/aws:aws_mocks", + "//test/integration:http_integration_lib", + "//test/test_common:utility_lib", + ], +) diff --git a/test/extensions/filters/http/aws_request_signing/aws_request_signing_integration_test.cc b/test/extensions/filters/http/aws_request_signing/aws_request_signing_integration_test.cc new file mode 100644 index 0000000000000..df84a1a6fbd7d --- /dev/null +++ b/test/extensions/filters/http/aws_request_signing/aws_request_signing_integration_test.cc @@ -0,0 +1,187 @@ +// #include + +#include "source/common/common/logger.h" + +#include "test/extensions/common/aws/mocks.h" +#include "test/integration/http_integration.h" +#include "test/test_common/utility.h" + +namespace Envoy { +namespace Extensions { +namespace Common { +namespace Aws { +namespace { + +const std::string AWS_REQUEST_SIGNING_CONFIG_SIGV4 = R"EOF( +name: envoy.filters.http.aws_request_signing +typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.http.aws_request_signing.v3.AwsRequestSigning + service_name: vpc-lattice-svcs + region: us-east-1 + signing_algorithm: aws_sigv4 + use_unsigned_payload: true + match_excluded_headers: + - prefix: x-envoy + - prefix: x-forwarded + - exact: x-amzn-trace-id +)EOF"; + +const std::string AWS_REQUEST_SIGNING_CONFIG_SIGV4A = R"EOF( +name: envoy.filters.http.aws_request_signing +typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.http.aws_request_signing.v3.AwsRequestSigning + service_name: vpc-lattice-svcs + region: '*' + signing_algorithm: aws_sigv4a + use_unsigned_payload: true + match_excluded_headers: + - prefix: x-envoy + - prefix: x-forwarded + - exact: x-amzn-trace-id +)EOF"; + +using Headers = std::vector>; + +class AwsRequestSigningIntegrationTest : public testing::TestWithParam, + public HttpIntegrationTest { +public: + AwsRequestSigningIntegrationTest() + : HttpIntegrationTest(Http::CodecClient::Type::HTTP1, GetParam()) { + skipPortUsageValidation(); + // set some environment credentials so the test cases perform signing correctly + TestEnvironment::setEnvVar("AWS_ACCESS_KEY_ID", "akid", 1); + TestEnvironment::setEnvVar("AWS_SECRET_ACCESS_KEY", "secret", 1); + TestEnvironment::setEnvVar("AWS_SESSION_TOKEN", "token", 1); + } + + ~AwsRequestSigningIntegrationTest() override { + TestEnvironment::unsetEnvVar("AWS_ACCESS_KEY_ID"); + TestEnvironment::unsetEnvVar("AWS_SECRET_ACCESS_KEY"); + TestEnvironment::unsetEnvVar("AWS_SESSION_TOKEN"); + } + + void createUpstreams() override { + HttpIntegrationTest::createUpstreams(); + addFakeUpstream(Http::CodecType::HTTP2); + } + + void addUpstreamProtocolOptions() { + config_helper_.addConfigModifier([&](envoy::config::bootstrap::v3::Bootstrap& bootstrap) { + auto* cluster = bootstrap.mutable_static_resources()->mutable_clusters(0); + + ConfigHelper::HttpProtocolOptions protocol_options; + protocol_options.mutable_upstream_http_protocol_options()->set_auto_sni(true); + protocol_options.mutable_upstream_http_protocol_options()->set_auto_san_validation(true); + protocol_options.mutable_explicit_http_config()->mutable_http_protocol_options(); + ConfigHelper::setProtocolOptions(*cluster, protocol_options); + }); + } + +protected: + bool downstream_filter_ = true; +}; + +INSTANTIATE_TEST_SUITE_P(IpVersions, AwsRequestSigningIntegrationTest, + testing::ValuesIn({Network::Address::IpVersion::v4})); + +TEST_P(AwsRequestSigningIntegrationTest, SigV4IntegrationDownstream) { + + config_helper_.prependFilter(AWS_REQUEST_SIGNING_CONFIG_SIGV4, true); + HttpIntegrationTest::initialize(); + + codec_client_ = makeHttpConnection(makeClientConnection((lookupPort("http")))); + + Http::TestRequestHeaderMapImpl request_headers{ + {":method", "GET"}, {":path", "/test/path"}, {":scheme", "http"}, {":authority", "host"}}; + + auto response = sendRequestAndWaitForResponse(request_headers, 0, default_response_headers_, 0); + + EXPECT_TRUE(upstream_request_->complete()); + EXPECT_TRUE(response->complete()); + // check that our headers have been correctly added upstream + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("authorization")).empty()); + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("x-amz-date")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-security-token")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-content-sha256")).empty()); +} + +TEST_P(AwsRequestSigningIntegrationTest, SigV4AIntegrationDownstream) { + + config_helper_.prependFilter(AWS_REQUEST_SIGNING_CONFIG_SIGV4A, true); + HttpIntegrationTest::initialize(); + + codec_client_ = makeHttpConnection(makeClientConnection((lookupPort("http")))); + + Http::TestRequestHeaderMapImpl request_headers{ + {":method", "GET"}, {":path", "/test/path"}, {":scheme", "http"}, {":authority", "host"}}; + + auto response = sendRequestAndWaitForResponse(request_headers, 0, default_response_headers_, 0); + + EXPECT_TRUE(upstream_request_->complete()); + EXPECT_TRUE(response->complete()); + // check that our headers have been correctly added upstream + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("authorization")).empty()); + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("x-amz-date")).empty()); + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("x-amz-region-set")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-security-token")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-content-sha256")).empty()); +} + +TEST_P(AwsRequestSigningIntegrationTest, SigV4IntegrationUpstream) { + + config_helper_.prependFilter(AWS_REQUEST_SIGNING_CONFIG_SIGV4, false); + addUpstreamProtocolOptions(); + HttpIntegrationTest::initialize(); + + codec_client_ = makeHttpConnection(makeClientConnection((lookupPort("http")))); + + Http::TestRequestHeaderMapImpl request_headers{ + {":method", "GET"}, {":path", "/test/path"}, {":scheme", "http"}, {":authority", "host"}}; + + auto response = sendRequestAndWaitForResponse(request_headers, 0, default_response_headers_, 0); + + EXPECT_TRUE(upstream_request_->complete()); + EXPECT_TRUE(response->complete()); + // check that our headers have been correctly added upstream + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("authorization")).empty()); + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("x-amz-date")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-security-token")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-content-sha256")).empty()); +} + +TEST_P(AwsRequestSigningIntegrationTest, SigV4AIntegrationUpstream) { + + config_helper_.prependFilter(AWS_REQUEST_SIGNING_CONFIG_SIGV4A, false); + addUpstreamProtocolOptions(); + HttpIntegrationTest::initialize(); + + codec_client_ = makeHttpConnection(makeClientConnection((lookupPort("http")))); + + Http::TestRequestHeaderMapImpl request_headers{ + {":method", "GET"}, {":path", "/test/path"}, {":scheme", "http"}, {":authority", "host"}}; + + auto response = sendRequestAndWaitForResponse(request_headers, 0, default_response_headers_, 0); + + EXPECT_TRUE(upstream_request_->complete()); + EXPECT_TRUE(response->complete()); + // check that our headers have been correctly added upstream + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("authorization")).empty()); + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("x-amz-date")).empty()); + EXPECT_FALSE(upstream_request_->headers().get(Http::LowerCaseString("x-amz-region-set")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-security-token")).empty()); + EXPECT_FALSE( + upstream_request_->headers().get(Http::LowerCaseString("x-amz-content-sha256")).empty()); +} + +} // namespace +} // namespace Aws +} // namespace Common +} // namespace Extensions +} // namespace Envoy diff --git a/test/extensions/filters/http/aws_request_signing/config_test.cc b/test/extensions/filters/http/aws_request_signing/config_test.cc index 6194f7c1771bc..902ea64442697 100644 --- a/test/extensions/filters/http/aws_request_signing/config_test.cc +++ b/test/extensions/filters/http/aws_request_signing/config_test.cc @@ -238,6 +238,14 @@ stat_prefix: foo_prefix EnvoyException); } +TEST(AwsRequestSigningFilterConfigTest, UpstreamFactoryTest) { + + auto* factory = + Registry::FactoryRegistry::getFactory( + "envoy.filters.http.aws_request_signing"); + ASSERT_NE(factory, nullptr); +} + } // namespace AwsRequestSigningFilter } // namespace HttpFilters } // namespace Extensions diff --git a/test/extensions/filters/http/dynamic_forward_proxy/proxy_filter_integration_test.cc b/test/extensions/filters/http/dynamic_forward_proxy/proxy_filter_integration_test.cc index df443ae619cc6..1193b7379c074 100644 --- a/test/extensions/filters/http/dynamic_forward_proxy/proxy_filter_integration_test.cc +++ b/test/extensions/filters/http/dynamic_forward_proxy/proxy_filter_integration_test.cc @@ -50,9 +50,11 @@ name: dynamic_forward_proxy typed_config: "@type": type.googleapis.com/envoy.extensions.filters.http.dynamic_forward_proxy.v3.FilterConfig dns_cache_config: + dns_min_refresh_rate: 1s name: foo dns_lookup_family: {} max_hosts: {} + host_ttl: 1s dns_cache_circuit_breaker: max_pending_requests: {}{}{} )EOF", @@ -127,9 +129,11 @@ name: envoy.clusters.dynamic_forward_proxy typed_config: "@type": type.googleapis.com/envoy.extensions.clusters.dynamic_forward_proxy.v3.ClusterConfig dns_cache_config: + dns_min_refresh_rate: 1s name: foo dns_lookup_family: {} max_hosts: {} + host_ttl: 1s dns_cache_circuit_breaker: max_pending_requests: {}{}{} )EOF", @@ -162,9 +166,9 @@ name: envoy.clusters.dynamic_forward_proxy if (use_cache_file_) { cache_file_value_contents_ += absl::StrCat(Network::Test::getLoopbackAddressUrlString(version_), ":", - fake_upstreams_[0]->localAddress()->ip()->port(), "|1000000|0"); + fake_upstreams_[0]->localAddress()->ip()->port(), "|", dns_cache_ttl_, "|0"); std::string host = - fmt::format("localhost:{}", fake_upstreams_[0]->localAddress()->ip()->port()); + fmt::format("{}:{}", dns_hostname_, fake_upstreams_[0]->localAddress()->ip()->port()); TestEnvironment::writeStringToFileForTest("dns_cache.txt", absl::StrCat(host.length(), "\n", host, cache_file_value_contents_.length(), @@ -254,8 +258,10 @@ name: envoy.clusters.dynamic_forward_proxy envoy::config::cluster::v3::Cluster cluster_; std::string cache_file_value_contents_; bool use_cache_file_{}; + uint32_t dns_cache_ttl_{1000000}; std::string filename_; std::string key_value_config_; + std::string dns_hostname_{"localhost"}; }; int64_t getHeaderValue(const Http::ResponseHeaderMap& headers, absl::string_view name) { @@ -646,6 +652,61 @@ TEST_P(ProxyFilterIntegrationTest, UseCacheFile) { EXPECT_EQ(1, test_server_->counter("cluster.cluster_0.upstream_cx_http1_total")->value()); } +TEST_P(ProxyFilterIntegrationTest, UseCacheFileShortTtl) { + upstream_tls_ = false; // avoid cert errors for unknown hostname + use_cache_file_ = true; + dns_cache_ttl_ = 2; + + dns_hostname_ = "not_actually_localhost"; // Set to a name that won't resolve. + initializeWithArgs(); + std::string host = + fmt::format("{}:{}", dns_hostname_, fake_upstreams_[0]->localAddress()->ip()->port()); + codec_client_ = makeHttpConnection(lookupPort("http")); + const Http::TestRequestHeaderMapImpl request_headers{ + {":method", "POST"}, {":path", "/test/long/url"}, {":scheme", "http"}, {":authority", host}}; + + auto response = + sendRequestAndWaitForResponse(request_headers, 1024, default_response_headers_, 1024); + checkSimpleRequestSuccess(1024, 1024, response.get()); + EXPECT_EQ(1, test_server_->counter("dns_cache.foo.cache_load")->value()); + EXPECT_EQ(1, test_server_->counter("cluster.cluster_0.upstream_cx_http1_total")->value()); + + // Wait for the host to be removed due to short TTL + test_server_->waitForCounterGe("dns_cache.foo.host_removed", 1); + + // Send a request and expect an error due to 1) removed host and 2) DNS resolution fail. + response = codec_client_->makeHeaderOnlyRequest(request_headers); + ASSERT_TRUE(response->waitForEndStream()); + EXPECT_EQ("503", response->headers().getStatusValue()); +} + +TEST_P(ProxyFilterIntegrationTest, UseCacheFileShortTtlHostActive) { + upstream_tls_ = false; // avoid cert errors for unknown hostname + use_cache_file_ = true; + dns_cache_ttl_ = 2; + + dns_hostname_ = "not_actually_localhost"; // Set to a name that won't resolve. + initializeWithArgs(); + std::string host = + fmt::format("{}:{}", dns_hostname_, fake_upstreams_[0]->localAddress()->ip()->port()); + codec_client_ = makeHttpConnection(lookupPort("http")); + const Http::TestRequestHeaderMapImpl request_headers{ + {":method", "POST"}, {":path", "/test/long/url"}, {":scheme", "http"}, {":authority", host}}; + + auto response = codec_client_->makeHeaderOnlyRequest(request_headers); + waitForNextUpstreamRequest(); + + // Wait for the host to be removed due to short TTL + test_server_->waitForCounterGe("dns_cache.foo.host_removed", 1); + + // Finish the response. + upstream_request_->encodeHeaders(default_response_headers_, true); + + // The disconnect will trigger failure. + ASSERT_TRUE(response->waitForEndStream()); + EXPECT_EQ("200", response->headers().getStatusValue()); +} + TEST_P(ProxyFilterIntegrationTest, UseCacheFileAndTestHappyEyeballs) { upstream_tls_ = false; // upstream creation doesn't handle autonomous_upstream_ autonomous_upstream_ = true; diff --git a/test/extensions/filters/http/ext_authz/ext_authz_test.cc b/test/extensions/filters/http/ext_authz/ext_authz_test.cc index 96f74729dabef..b7164fa127783 100644 --- a/test/extensions/filters/http/ext_authz/ext_authz_test.cc +++ b/test/extensions/filters/http/ext_authz/ext_authz_test.cc @@ -949,7 +949,7 @@ TEST_F(HttpFilterTest, HeadersToRemoveRemovesHeadersExceptSpecialHeaders) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -1004,7 +1004,7 @@ TEST_F(HttpFilterTest, ClearCache) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -1051,7 +1051,7 @@ TEST_F(HttpFilterTest, ClearCacheRouteHeadersToAppendOnly) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -1095,7 +1095,7 @@ TEST_F(HttpFilterTest, ClearCacheRouteHeadersToAddOnly) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -1139,7 +1139,7 @@ TEST_F(HttpFilterTest, ClearCacheRouteHeadersToRemoveOnly) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -1184,7 +1184,7 @@ TEST_F(HttpFilterTest, NoClearCacheRoute) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -1222,7 +1222,7 @@ TEST_F(HttpFilterTest, NoClearCacheRouteConfig) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -2163,7 +2163,7 @@ TEST_P(HttpFilterTestParam, OkResponse) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); Filters::Common::ExtAuthz::Response response{}; @@ -2525,7 +2525,7 @@ TEST_P(HttpFilterTestParam, DeniedResponseWith401) { const StreamInfo::StreamInfo&) -> void { request_callbacks_ = &callbacks; })); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)); + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)); EXPECT_EQ(Http::FilterHeadersStatus::StopAllIterationAndWatermark, filter_->decodeHeaders(request_headers_, false)); @@ -2570,7 +2570,7 @@ TEST_P(HttpFilterTestParam, DeniedResponseWith401NoClusterResponseCodeStats) { const StreamInfo::StreamInfo&) -> void { request_callbacks_ = &callbacks; })); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)); + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)); EXPECT_EQ(Http::FilterHeadersStatus::StopAllIterationAndWatermark, filter_->decodeHeaders(request_headers_, false)); @@ -2606,7 +2606,7 @@ TEST_P(HttpFilterTestParam, DeniedResponseWith403) { const StreamInfo::StreamInfo&) -> void { request_callbacks_ = &callbacks; })); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)); + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)); EXPECT_EQ(Http::FilterHeadersStatus::StopAllIterationAndWatermark, filter_->decodeHeaders(request_headers_, false)); @@ -2817,7 +2817,7 @@ TEST_F(HttpFilterTest, EmitDynamicMetadata) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(Envoy::StreamInfo::ResponseFlag::UnauthorizedExternalService)) + setResponseFlag(Envoy::StreamInfo::CoreResponseFlag::UnauthorizedExternalService)) .Times(0); request_callbacks_->onComplete(std::make_unique(response)); diff --git a/test/extensions/filters/http/ext_proc/BUILD b/test/extensions/filters/http/ext_proc/BUILD index a99fde2191eec..9d511fbd9d8a9 100644 --- a/test/extensions/filters/http/ext_proc/BUILD +++ b/test/extensions/filters/http/ext_proc/BUILD @@ -19,6 +19,7 @@ envoy_extension_cc_test( size = "small", srcs = ["config_test.cc"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//source/extensions/filters/http/ext_proc:config", "//test/mocks/server:factory_context_mocks", @@ -30,7 +31,14 @@ envoy_extension_cc_test( name = "filter_test", size = "small", srcs = ["filter_test.cc"], + copts = select({ + "//bazel:windows_x86_64": [], + "//conditions:default": [ + "-DUSE_CEL_PARSER", + ], + }), extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ ":mock_server_lib", ":utils_lib", @@ -50,6 +58,7 @@ envoy_extension_cc_test( "//test/mocks/runtime:runtime_mocks", "//test/mocks/server:factory_context_mocks", "//test/mocks/server:overload_manager_mocks", + "//test/proto:helloworld_proto_cc_proto", "//test/test_common:test_runtime_lib", "@envoy_api//envoy/config/core/v3:pkg_cc_proto", "@envoy_api//envoy/service/ext_proc/v3:pkg_cc_proto", @@ -61,6 +70,7 @@ envoy_extension_cc_test( size = "small", srcs = ["state_test.cc"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//source/extensions/filters/http/ext_proc", ], @@ -71,11 +81,13 @@ envoy_extension_cc_test( size = "small", srcs = ["ordering_test.cc"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ ":mock_server_lib", "//source/extensions/filters/http/ext_proc", "//test/common/http:common_lib", "//test/mocks/event:event_mocks", + "//test/mocks/local_info:local_info_mocks", "//test/mocks/server:factory_context_mocks", "//test/test_common:test_runtime_lib", "@envoy_api//envoy/config/core/v3:pkg_cc_proto", @@ -87,6 +99,7 @@ envoy_extension_cc_test( size = "small", srcs = ["client_test.cc"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//source/common/http:header_map_lib", "//source/extensions/filters/http/ext_proc:client_lib", @@ -102,6 +115,7 @@ envoy_extension_cc_test( size = "small", srcs = ["mutation_utils_test.cc"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ ":utils_lib", "//source/extensions/filters/common/mutation_rules:mutation_rules_lib", @@ -117,20 +131,35 @@ envoy_extension_cc_test( name = "ext_proc_integration_test", size = "large", # This test can take a while under tsan. srcs = ["ext_proc_integration_test.cc"], - extension_names = ["envoy.filters.http.ext_proc"], + copts = select({ + "//bazel:windows_x86_64": [], + "//conditions:default": [ + "-DUSE_CEL_PARSER", + ], + }), + extension_names = [ + "envoy.filters.http.ext_proc", + # TODO(jbohanon) use a test filter here instead of production filter + "envoy.filters.http.set_metadata", + ], shard_count = 4, tags = [ "cpu:3", + "skip_on_windows", ], deps = [ ":logging_test_filter_lib", ":utils_lib", "//source/extensions/filters/http/ext_proc:config", + "//source/extensions/filters/http/set_metadata:config", "//test/common/http:common_lib", "//test/integration:http_integration_lib", + "//test/integration/filters:stream_info_to_headers_filter_lib", + "//test/proto:helloworld_proto_cc_proto", "//test/test_common:test_runtime_lib", "//test/test_common:utility_lib", "@envoy_api//envoy/extensions/filters/http/ext_proc/v3:pkg_cc_proto", + "@envoy_api//envoy/extensions/filters/http/set_metadata/v3:pkg_cc_proto", "@envoy_api//envoy/service/ext_proc/v3:pkg_cc_proto", ], ) @@ -139,9 +168,16 @@ envoy_extension_cc_test( name = "streaming_integration_test", size = "large", srcs = ["streaming_integration_test.cc"], + copts = select({ + "//bazel:windows_x86_64": [], + "//conditions:default": [ + "-DUSE_CEL_PARSER", + ], + }), extension_names = ["envoy.filters.http.ext_proc"], tags = [ "cpu:3", + "skip_on_windows", ], deps = [ ":test_processor_lib", @@ -163,6 +199,7 @@ envoy_extension_cc_test_library( srcs = ["test_processor.cc"], hdrs = ["test_processor.h"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//envoy/network:address_interface", "//test/test_common:network_utility_lib", @@ -178,6 +215,7 @@ envoy_extension_cc_test_library( srcs = ["mock_server.cc"], hdrs = ["mock_server.h"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//source/extensions/filters/http/ext_proc:client_interface", ], @@ -188,6 +226,7 @@ envoy_extension_cc_test_library( srcs = ["utils.cc"], hdrs = ["utils.h"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//envoy/http:header_map_interface", "//test/test_common:utility_lib", @@ -201,6 +240,7 @@ envoy_extension_cc_test_library( srcs = ["ext_proc_grpc_fuzz_helper.cc"], hdrs = ["ext_proc_grpc_fuzz_helper.h"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ "//source/common/common:thread_lib", "//source/common/grpc:common_lib", @@ -243,6 +283,7 @@ envoy_cc_fuzz_test( srcs = ["ext_proc_grpc_fuzz.cc"], hdrs = ["ext_proc_grpc_fuzz.h"], corpus = "ext_proc_grpc_corpus", + tags = ["skip_on_windows"], deps = EXT_PROC_GRPC_FUZZ_TEST_DEPS, ) @@ -251,6 +292,7 @@ envoy_cc_fuzz_test( srcs = ["ext_proc_grpc_fuzz_persistent.cc"], hdrs = ["ext_proc_grpc_fuzz.h"], corpus = "ext_proc_grpc_corpus", + tags = ["skip_on_windows"], deps = EXT_PROC_GRPC_FUZZ_TEST_DEPS, ) @@ -258,6 +300,7 @@ envoy_extension_cc_test( name = "ext_proc_benchmark_test", srcs = ["ext_proc_benchmark_test.cc"], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ ":test_processor_lib", "//envoy/http:header_map_interface", @@ -285,6 +328,7 @@ envoy_extension_cc_test_library( "logging_test_filter.cc", ], extension_names = ["envoy.filters.http.ext_proc"], + tags = ["skip_on_windows"], deps = [ ":logging_test_filter_proto_cc_proto", "//envoy/http:filter_interface", diff --git a/test/extensions/filters/http/ext_proc/config_test.cc b/test/extensions/filters/http/ext_proc/config_test.cc index 6cfa1d9196a98..fb982aee9b250 100644 --- a/test/extensions/filters/http/ext_proc/config_test.cc +++ b/test/extensions/filters/http/ext_proc/config_test.cc @@ -21,8 +21,12 @@ TEST(HttpExtProcConfigTest, CorrectConfig) { target_uri: ext_proc_server stat_prefix: google failure_mode_allow: true - request_attributes: 'Foo, Bar, Baz' - response_attributes: More + request_attributes: + - 'Foo' + - 'Bar' + - 'Baz' + response_attributes: + - 'More' processing_mode: request_header_mode: send response_header_mode: skip @@ -32,6 +36,15 @@ TEST(HttpExtProcConfigTest, CorrectConfig) { response_trailer_mode: send filter_metadata: hello: "world" + metadata_options: + forwarding_namespaces: + typed: + - ns1 + untyped: + - ns2 + receiving_namespaces: + untyped: + - ns2 )EOF"; ExternalProcessingFilterConfig factory; @@ -54,8 +67,12 @@ TEST(HttpExtProcConfigTest, CorrectConfigServerContext) { target_uri: ext_proc_server stat_prefix: google failure_mode_allow: true - request_attributes: 'Foo, Bar, Baz' - response_attributes: More + request_attributes: + - 'Foo' + - 'Bar' + - 'Baz' + response_attributes: + - 'More' processing_mode: request_header_mode: send response_header_mode: skip @@ -65,6 +82,15 @@ TEST(HttpExtProcConfigTest, CorrectConfigServerContext) { response_trailer_mode: send filter_metadata: hello: "world" + metadata_options: + forwarding_namespaces: + typed: + - ns1 + untyped: + - ns2 + receiving_namespaces: + untyped: + - ns2 )EOF"; ExternalProcessingFilterConfig factory; diff --git a/test/extensions/filters/http/ext_proc/ext_proc_integration_test.cc b/test/extensions/filters/http/ext_proc/ext_proc_integration_test.cc index b75f2eb4e1420..d0becb1f2bab0 100644 --- a/test/extensions/filters/http/ext_proc/ext_proc_integration_test.cc +++ b/test/extensions/filters/http/ext_proc/ext_proc_integration_test.cc @@ -1,6 +1,8 @@ #include +#include #include "envoy/extensions/filters/http/ext_proc/v3/ext_proc.pb.h" +#include "envoy/extensions/filters/http/set_metadata/v3/set_metadata.pb.h" #include "envoy/network/address.h" #include "envoy/service/ext_proc/v3/external_processor.pb.h" @@ -48,6 +50,7 @@ struct ConfigOptions { bool valid_grpc_server = true; bool add_logging_filter = false; bool http1_codec = false; + bool add_metadata = false; }; // These tests exercise the ext_proc filter through Envoy's integration test @@ -79,7 +82,7 @@ class ExtProcIntegrationTest : public HttpIntegrationTest, scoped_runtime_.mergeValues( {{"envoy.reloadable_features.send_header_raw_value", header_raw_value_}}); scoped_runtime_.mergeValues( - {{"envoy_reloadable_features_immediate_response_use_filter_mutation_rule", + {{"envoy.reloadable_features.immediate_response_use_filter_mutation_rule", filter_mutation_rule_}}); config_helper_.addConfigModifier([this, config_option]( @@ -116,6 +119,38 @@ class ExtProcIntegrationTest : public HttpIntegrationTest, ext_proc_filter.mutable_typed_config()->PackFrom(proto_config_); config_helper_.prependFilter(MessageUtil::getJsonStringFromMessageOrError(ext_proc_filter)); + // Add set_metadata filter to inject dynamic metadata used for testing + if (config_option.add_metadata) { + envoy::config::listener::v3::Filter set_metadata_filter; + std::string set_metadata_filter_name = "envoy.filters.http.set_metadata"; + set_metadata_filter.set_name(set_metadata_filter_name); + + envoy::extensions::filters::http::set_metadata::v3::Config set_metadata_config; + auto* untyped_md = set_metadata_config.add_metadata(); + untyped_md->set_metadata_namespace("forwarding_ns_untyped"); + untyped_md->set_allow_overwrite(true); + ProtobufWkt::Struct test_md_val; + (*test_md_val.mutable_fields())["foo"].set_string_value("value from set_metadata"); + (*untyped_md->mutable_value()) = test_md_val; + + auto* typed_md = set_metadata_config.add_metadata(); + typed_md->set_metadata_namespace("forwarding_ns_typed"); + typed_md->set_allow_overwrite(true); + envoy::extensions::filters::http::set_metadata::v3::Metadata typed_md_to_stuff; + typed_md_to_stuff.set_metadata_namespace("typed_value from set_metadata"); + typed_md->mutable_typed_value()->PackFrom(typed_md_to_stuff); + + set_metadata_filter.mutable_typed_config()->PackFrom(set_metadata_config); + config_helper_.prependFilter( + MessageUtil::getJsonStringFromMessageOrError(set_metadata_filter)); + + // Add filter that dumps streamInfo into headers so we can check our receiving + // namespaces + config_helper_.prependFilter(fmt::format(R"EOF( + name: stream-info-to-headers-filter + )EOF")); + } + // Add logging test filter only in Envoy gRPC mode. // gRPC side stream logging is only supported in Envoy gRPC mode at the moment. if (clientType() == Grpc::ClientType::EnvoyGrpc && config_option.add_logging_filter && @@ -249,6 +284,26 @@ class ExtProcIntegrationTest : public HttpIntegrationTest, ASSERT_TRUE(processor_stream_->waitForGrpcMessage(*dispatcher_, request)); } + void processGenericMessage( + FakeUpstream& grpc_upstream, bool first_message, + absl::optional> cb) { + ProcessingRequest request; + if (first_message) { + ASSERT_TRUE(grpc_upstream.waitForHttpConnection(*dispatcher_, processor_connection_)); + ASSERT_TRUE(processor_connection_->waitForNewStream(*dispatcher_, processor_stream_)); + } + ASSERT_TRUE(processor_stream_->waitForGrpcMessage(*dispatcher_, request)); + ASSERT_TRUE(request.has_request_headers()); + if (first_message) { + processor_stream_->startGrpcStream(); + } + ProcessingResponse response; + const bool sendReply = !cb || (*cb)(request, response); + if (sendReply) { + processor_stream_->sendGrpcMessage(response); + } + } + void processRequestHeadersMessage( FakeUpstream& grpc_upstream, bool first_message, absl::optional> cb) { @@ -1836,6 +1891,28 @@ TEST_P(ExtProcIntegrationTest, GetAndImmediateRespondMutationAllowEnvoy) { EXPECT_THAT(response->headers(), SingleHeaderValueIs("x-envoy-foo", "bar")); } +// Test the filter using an ext_proc server that responds to the request_header message +// by sending back an immediate_response message with x-envoy header mutation. +// The deprecated default checker allows x-envoy headers to be mutated and should +// override config-level checkers if the runtime guard is disabled. +TEST_P(ExtProcIntegrationTest, GetAndRespondImmediatelyWithDefaultHeaderMutationChecker) { + // this is default, but setting explicitly for test clarity + filter_mutation_rule_ = "false"; + proto_config_.mutable_mutation_rules()->mutable_allow_envoy()->set_value(false); + initializeConfig(); + HttpIntegrationTest::initialize(); + auto response = sendDownstreamRequest(absl::nullopt); + processAndRespondImmediately(*grpc_upstreams_[0], true, [](ImmediateResponse& immediate) { + immediate.mutable_status()->set_code(envoy::type::v3::StatusCode::Unauthorized); + auto* hdr = immediate.mutable_headers()->add_set_headers(); + // Adding x-envoy header is allowed since default overrides config. + hdr->mutable_header()->set_key("x-envoy-foo"); + hdr->mutable_header()->set_value("bar"); + }); + verifyDownstreamResponse(*response, 401); + EXPECT_FALSE(response->headers().get(LowerCaseString("x-envoy-foo")).empty()); +} + // Test the filter with request body buffering enabled using // an ext_proc server that responds to the request_body message // by modifying a header that should cause an error. @@ -3285,4 +3362,114 @@ TEST_P(ExtProcIntegrationTest, SendBodyBufferedPartialWithTrailer) { verifyDownstreamResponse(*response, 200); } +TEST_P(ExtProcIntegrationTest, SendAndReceiveDynamicMetadata) { + proto_config_.mutable_processing_mode()->set_request_header_mode(ProcessingMode::SEND); + proto_config_.mutable_processing_mode()->set_response_header_mode(ProcessingMode::SKIP); + + auto* md_opts = proto_config_.mutable_metadata_options(); + md_opts->mutable_forwarding_namespaces()->add_untyped("forwarding_ns_untyped"); + md_opts->mutable_forwarding_namespaces()->add_typed("forwarding_ns_typed"); + md_opts->mutable_receiving_namespaces()->add_untyped("receiving_ns_untyped"); + + ConfigOptions config_option = {}; + config_option.add_metadata = true; + initializeConfig(config_option); + HttpIntegrationTest::initialize(); + + auto response = sendDownstreamRequest(absl::nullopt); + + ProtobufWkt::Struct test_md_struct; + (*test_md_struct.mutable_fields())["foo"].set_string_value("value from ext_proc"); + + ProtobufWkt::Value md_val; + *(md_val.mutable_struct_value()) = test_md_struct; + + processGenericMessage( + *grpc_upstreams_[0], true, [md_val](const ProcessingRequest& req, ProcessingResponse& resp) { + // Verify the processing request contains the untyped metadata we injected. + EXPECT_TRUE(req.metadata_context().filter_metadata().contains("forwarding_ns_untyped")); + const ProtobufWkt::Struct& fwd_metadata = + req.metadata_context().filter_metadata().at("forwarding_ns_untyped"); + EXPECT_EQ(1, fwd_metadata.fields_size()); + EXPECT_TRUE(fwd_metadata.fields().contains("foo")); + EXPECT_EQ("value from set_metadata", fwd_metadata.fields().at("foo").string_value()); + + // Verify the processing request contains the typed metadata we injected. + EXPECT_TRUE(req.metadata_context().typed_filter_metadata().contains("forwarding_ns_typed")); + const ProtobufWkt::Any& fwd_typed_metadata = + req.metadata_context().typed_filter_metadata().at("forwarding_ns_typed"); + EXPECT_EQ("type.googleapis.com/envoy.extensions.filters.http.set_metadata.v3.Metadata", + fwd_typed_metadata.type_url()); + envoy::extensions::filters::http::set_metadata::v3::Metadata typed_md_from_req; + fwd_typed_metadata.UnpackTo(&typed_md_from_req); + EXPECT_EQ("typed_value from set_metadata", typed_md_from_req.metadata_namespace()); + + // Spoof the response to contain receiving metadata. + HeadersResponse headers_resp; + (*resp.mutable_request_headers()) = headers_resp; + auto mut_md_fields = resp.mutable_dynamic_metadata()->mutable_fields(); + (*mut_md_fields).emplace("receiving_ns_untyped", md_val); + + return true; + }); + + handleUpstreamRequest(); + + ASSERT_TRUE(response->waitForEndStream()); + ASSERT_TRUE(response->complete()); + + // Verify the response received contains the headers from dynamic metadata we expect. + ASSERT_FALSE((*response).headers().empty()); + auto md_header_result = + (*response).headers().get(Http::LowerCaseString("receiving_ns_untyped.foo")); + ASSERT_EQ(1, md_header_result.size()); + EXPECT_EQ("value from ext_proc", md_header_result[0]->value().getStringView()); + + verifyDownstreamResponse(*response, 200); +} + +#if defined(USE_CEL_PARSER) +// Test the filter using the default configuration by connecting to +// an ext_proc server that responds to the request_headers message +// by requesting to modify the request headers. +TEST_P(ExtProcIntegrationTest, GetAndSetRequestResponseAttributes) { + proto_config_.mutable_processing_mode()->set_request_header_mode(ProcessingMode::SEND); + proto_config_.mutable_processing_mode()->set_response_header_mode(ProcessingMode::SEND); + proto_config_.mutable_request_attributes()->Add("request.path"); + proto_config_.mutable_request_attributes()->Add("request.method"); + proto_config_.mutable_request_attributes()->Add("request.scheme"); + proto_config_.mutable_request_attributes()->Add("connection.mtls"); + proto_config_.mutable_response_attributes()->Add("response.code"); + proto_config_.mutable_response_attributes()->Add("response.code_details"); + + initializeConfig(); + HttpIntegrationTest::initialize(); + auto response = sendDownstreamRequest(absl::nullopt); + processRequestHeadersMessage( + *grpc_upstreams_[0], true, [](const HttpHeaders& req, HeadersResponse&) { + EXPECT_EQ(req.attributes().size(), 1); + auto proto_struct = req.attributes().at("envoy.filters.http.ext_proc"); + EXPECT_EQ(proto_struct.fields().at("request.path").string_value(), "/"); + EXPECT_EQ(proto_struct.fields().at("request.method").string_value(), "GET"); + EXPECT_EQ(proto_struct.fields().at("request.scheme").string_value(), "http"); + EXPECT_EQ(proto_struct.fields().at("connection.mtls").bool_value(), false); + return true; + }); + + handleUpstreamRequest(); + + processResponseHeadersMessage( + *grpc_upstreams_[0], false, [](const HttpHeaders& req, HeadersResponse&) { + EXPECT_EQ(req.attributes().size(), 1); + auto proto_struct = req.attributes().at("envoy.filters.http.ext_proc"); + EXPECT_EQ(proto_struct.fields().at("response.code").string_value(), "200"); + EXPECT_EQ(proto_struct.fields().at("response.code_details").string_value(), + StreamInfo::ResponseCodeDetails::get().ViaUpstream); + return true; + }); + + verifyDownstreamResponse(*response, 200); +} +#endif + } // namespace Envoy diff --git a/test/extensions/filters/http/ext_proc/filter_test.cc b/test/extensions/filters/http/ext_proc/filter_test.cc index 47865bdbf334f..907f52aef5c6c 100644 --- a/test/extensions/filters/http/ext_proc/filter_test.cc +++ b/test/extensions/filters/http/ext_proc/filter_test.cc @@ -21,6 +21,7 @@ #include "test/mocks/event/mocks.h" #include "test/mocks/http/mocks.h" #include "test/mocks/http/stream_encoder.h" +#include "test/mocks/local_info/mocks.h" #include "test/mocks/network/mocks.h" #include "test/mocks/router/mocks.h" #include "test/mocks/runtime/mocks.h" @@ -97,6 +98,16 @@ class HttpFilterTest : public testing::Test { EXPECT_CALL(decoder_callbacks_, dispatcher()).WillRepeatedly(ReturnRef(dispatcher_)); EXPECT_CALL(decoder_callbacks_, route()).WillRepeatedly(Return(route_)); EXPECT_CALL(decoder_callbacks_, streamInfo()).WillRepeatedly(ReturnRef(stream_info_)); + EXPECT_CALL(encoder_callbacks_, streamInfo()).WillRepeatedly(ReturnRef(stream_info_)); + EXPECT_CALL(stream_info_, dynamicMetadata()).WillRepeatedly(ReturnRef(dynamic_metadata_)); + EXPECT_CALL(stream_info_, setDynamicMetadata(_, _)) + .Times(AnyNumber()) + .WillRepeatedly(Invoke(this, &HttpFilterTest::doSetDynamicMetadata)); + + EXPECT_CALL(decoder_callbacks_, connection()) + .WillRepeatedly(Return(OptRef{connection_})); + EXPECT_CALL(encoder_callbacks_, connection()) + .WillRepeatedly(Return(OptRef{connection_})); // Pointing dispatcher_.time_system_ to a SimulatedTimeSystem object. test_time_ = new Envoy::Event::SimulatedTimeSystem(); @@ -121,8 +132,11 @@ class HttpFilterTest : public testing::Test { if (!yaml.empty()) { TestUtility::loadFromYaml(yaml, proto_config); } - config_ = - std::make_shared(proto_config, 200ms, 10000, *stats_store_.rootScope(), ""); + config_ = std::make_shared( + proto_config, 200ms, 10000, *stats_store_.rootScope(), "", + std::make_shared( + Envoy::Extensions::Filters::Common::Expr::createBuilder(nullptr)), + local_info_); filter_ = std::make_unique(config_, std::move(client_), proto_config.grpc_service()); filter_->setEncoderFilterCallbacks(encoder_callbacks_); EXPECT_CALL(encoder_callbacks_, encoderBufferLimit()).WillRepeatedly(Return(BufferSize)); @@ -169,8 +183,6 @@ class HttpFilterTest : public testing::Test { if (final_expected_grpc_service_.has_value()) { EXPECT_TRUE(TestUtility::protoEqual(final_expected_grpc_service_.value(), config_with_hash_key.config())); - std::cout << final_expected_grpc_service_.value().DebugString(); - std::cout << config_with_hash_key.config().DebugString(); } stream_callbacks_ = &callbacks; @@ -186,6 +198,10 @@ class HttpFilterTest : public testing::Test { return stream; } + void doSetDynamicMetadata(const std::string& ns, const ProtobufWkt::Struct& val) { + (*dynamic_metadata_.mutable_filter_metadata())[ns] = val; + }; + void doSend(ProcessingRequest&& request, Unused) { last_request_ = std::move(request); } bool doSendClose() { return !server_closed_stream_; } @@ -545,7 +561,7 @@ class HttpFilterTest : public testing::Test { ExternalProcessorCallbacks* stream_callbacks_ = nullptr; ProcessingRequest last_request_; bool server_closed_stream_ = false; - NiceMock stats_store_; + testing::NiceMock stats_store_; FilterConfigSharedPtr config_; std::shared_ptr filter_; testing::NiceMock dispatcher_; @@ -561,6 +577,9 @@ class HttpFilterTest : public testing::Test { std::vector timers_; TestScopedRuntime scoped_runtime_; Envoy::Event::SimulatedTimeSystem* test_time_; + envoy::config::core::v3::Metadata dynamic_metadata_; + testing::NiceMock connection_; + testing::NiceMock local_info_; }; // Using the default configuration, test the filter with a processor that @@ -3102,6 +3121,538 @@ TEST_F(HttpFilterTest, ResponseTrailerMutationExceedSizeLimit) { EXPECT_EQ(1, config_->stats().rejected_header_mutations_.value()); } +TEST_F(HttpFilterTest, MetadataOptionsOverride) { + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SKIP" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + forwarding_namespaces: + untyped: + - untyped_ns_1 + typed: + - typed_ns_1 + receiving_namespaces: + untyped: + - untyped_receiving_ns_1 + )EOF"); + ExtProcPerRoute override_cfg; + const std::string override_yaml = R"EOF( + overrides: + metadata_options: + forwarding_namespaces: + untyped: + - untyped_ns_2 + typed: + - typed_ns_2 + receiving_namespaces: + untyped: + - untyped_receiving_ns_2 + )EOF"; + TestUtility::loadFromYaml(override_yaml, override_cfg); + + FilterConfigPerRoute route_config(override_cfg); + + EXPECT_CALL(decoder_callbacks_, traversePerFilterConfig(_)) + .WillOnce( + testing::Invoke([&](std::function cb) { + cb(route_config); + })); + + response_headers_.addCopy(LowerCaseString(":status"), "200"); + response_headers_.addCopy(LowerCaseString("content-type"), "text/plain"); + response_headers_.addCopy(LowerCaseString("content-length"), "3"); + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + processResponseHeaders(false, absl::nullopt); + + ASSERT_EQ(filter_->encodingState().untypedForwardingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->encodingState().untypedForwardingMetadataNamespaces()[0], "untyped_ns_2"); + ASSERT_EQ(filter_->decodingState().untypedForwardingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->decodingState().untypedForwardingMetadataNamespaces()[0], "untyped_ns_2"); + + ASSERT_EQ(filter_->encodingState().typedForwardingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->decodingState().typedForwardingMetadataNamespaces()[0], "typed_ns_2"); + + ASSERT_EQ(filter_->encodingState().untypedReceivingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->encodingState().untypedReceivingMetadataNamespaces()[0], + "untyped_receiving_ns_2"); + ASSERT_EQ(filter_->decodingState().untypedReceivingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->decodingState().untypedReceivingMetadataNamespaces()[0], + "untyped_receiving_ns_2"); + + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + filter_->onDestroy(); +} + +// Validate that when metadata options are not specified as an override, the less-specific +// namespaces lists are used. +TEST_F(HttpFilterTest, MetadataOptionsNoOverride) { + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SKIP" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + forwarding_namespaces: + untyped: + - untyped_ns_1 + typed: + - typed_ns_1 + receiving_namespaces: + untyped: + - untyped_receiving_ns_1 + )EOF"); + ExtProcPerRoute override_cfg; + const std::string override_yaml = R"EOF( + overrides: {} + )EOF"; + TestUtility::loadFromYaml(override_yaml, override_cfg); + + FilterConfigPerRoute route_config(override_cfg); + + EXPECT_CALL(decoder_callbacks_, traversePerFilterConfig(_)) + .WillOnce( + testing::Invoke([&](std::function cb) { + cb(route_config); + })); + + response_headers_.addCopy(LowerCaseString(":status"), "200"); + response_headers_.addCopy(LowerCaseString("content-type"), "text/plain"); + response_headers_.addCopy(LowerCaseString("content-length"), "3"); + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + processResponseHeaders(false, absl::nullopt); + + ASSERT_EQ(filter_->encodingState().untypedForwardingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->encodingState().untypedForwardingMetadataNamespaces()[0], "untyped_ns_1"); + ASSERT_EQ(filter_->decodingState().untypedForwardingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->decodingState().untypedForwardingMetadataNamespaces()[0], "untyped_ns_1"); + + ASSERT_EQ(filter_->encodingState().typedForwardingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->decodingState().typedForwardingMetadataNamespaces()[0], "typed_ns_1"); + + ASSERT_EQ(filter_->encodingState().untypedReceivingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->encodingState().untypedReceivingMetadataNamespaces()[0], + "untyped_receiving_ns_1"); + ASSERT_EQ(filter_->decodingState().untypedReceivingMetadataNamespaces().size(), 1); + EXPECT_EQ(filter_->decodingState().untypedReceivingMetadataNamespaces()[0], + "untyped_receiving_ns_1"); + + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + filter_->onDestroy(); +} + +// Verify that the filter sets the processing request with dynamic metadata +// including when the metadata is on the connection stream info +TEST_F(HttpFilterTest, SendDynamicMetadata) { + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SKIP" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + forwarding_namespaces: + untyped: + - connection.and.request.have.data + - connection.has.data + - request.has.data + - neither.have.data + - untyped.and.typed.connection.data + - typed.connection.data + - untyped.connection.data + typed: + - untyped.and.typed.connection.data + - typed.connection.data + - typed.request.data + - untyped.connection.data + )EOF"); + + const std::string request_yaml = R"EOF( + filter_metadata: + connection.and.request.have.data: + data: request + request.has.data: + data: request + typed_filter_metadata: + typed.request.data: + # We are using ExtProcOverrides just because we know it is built and imported already. + '@type': type.googleapis.com/envoy.extensions.filters.http.ext_proc.v3.ExtProcOverrides + request_attributes: + - request_typed + )EOF"; + + const std::string connection_yaml = R"EOF( + filter_metadata: + connection.and.request.have.data: + data: connection_untyped + connection.has.data: + data: connection_untyped + untyped.and.typed.connection.data: + data: connection_untyped + untyped.connection.data: + data: connection_untyped + not.selected.data: + data: connection_untyped + typed_filter_metadata: + untyped.and.typed.connection.data: + # We are using ExtProcOverrides just because we know it is built and imported already. + '@type': type.googleapis.com/envoy.extensions.filters.http.ext_proc.v3.ExtProcOverrides + request_attributes: + - connection_typed + typed.connection.data: + # We are using ExtProcOverrides just because we know it is built and imported already. + '@type': type.googleapis.com/envoy.extensions.filters.http.ext_proc.v3.ExtProcOverrides + request_attributes: + - connection_typed + not.selected.data: + # We are using ExtProcOverrides just because we know it is built and imported already. + '@type': type.googleapis.com/envoy.extensions.filters.http.ext_proc.v3.ExtProcOverrides + request_attributes: + - connection_typed + )EOF"; + + envoy::config::core::v3::Metadata connection_metadata; + TestUtility::loadFromYaml(request_yaml, dynamic_metadata_); + TestUtility::loadFromYaml(connection_yaml, connection_metadata); + connection_.stream_info_.metadata_ = connection_metadata; + + Buffer::OwnedImpl empty_chunk; + + EXPECT_EQ(FilterHeadersStatus::Continue, filter_->decodeHeaders(request_headers_, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + + // ensure the metadata that is attached to the processing request is identical to + // the metadata we specified above + EXPECT_EQ("request", last_request_.metadata_context() + .filter_metadata() + .at("connection.and.request.have.data") + .fields() + .at("data") + .string_value()); + + EXPECT_EQ("request", last_request_.metadata_context() + .filter_metadata() + .at("request.has.data") + .fields() + .at("data") + .string_value()); + + EXPECT_EQ("connection_untyped", last_request_.metadata_context() + .filter_metadata() + .at("connection.has.data") + .fields() + .at("data") + .string_value()); + + EXPECT_EQ("connection_untyped", last_request_.metadata_context() + .filter_metadata() + .at("untyped.and.typed.connection.data") + .fields() + .at("data") + .string_value()); + + EXPECT_EQ(0, last_request_.metadata_context().filter_metadata().count("neither.have.data")); + + EXPECT_EQ(0, last_request_.metadata_context().filter_metadata().count("not.selected.data")); + + EXPECT_EQ(0, last_request_.metadata_context().filter_metadata().count("typed.connection.data")); + + envoy::extensions::filters::http::ext_proc::v3::ExtProcOverrides typed_any; + last_request_.metadata_context() + .typed_filter_metadata() + .at("typed.connection.data") + .UnpackTo(&typed_any); + ASSERT_EQ(1, typed_any.request_attributes().size()); + EXPECT_EQ("connection_typed", typed_any.request_attributes()[0]); + + last_request_.metadata_context() + .typed_filter_metadata() + .at("untyped.and.typed.connection.data") + .UnpackTo(&typed_any); + ASSERT_EQ(1, typed_any.request_attributes().size()); + EXPECT_EQ("connection_typed", typed_any.request_attributes()[0]); + + EXPECT_EQ( + 0, last_request_.metadata_context().typed_filter_metadata().count("untyped.connection.data")); + + EXPECT_EQ(0, last_request_.metadata_context().typed_filter_metadata().count("not.selected.data")); + + processResponseHeaders(false, absl::nullopt); + + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + filter_->onDestroy(); +} + +// Verify that when returning an response with dynamic_metadata field set, the filter emits +// dynamic metadata. +TEST_F(HttpFilterTest, EmitDynamicMetadata) { + // Configure the filter to only pass response headers to ext server. + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SKIP" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + receiving_namespaces: + untyped: + - envoy.filters.http.ext_proc + )EOF"); + + Buffer::OwnedImpl empty_chunk; + + EXPECT_EQ(FilterHeadersStatus::Continue, filter_->decodeHeaders(request_headers_, false)); + EXPECT_EQ(FilterDataStatus::Continue, filter_->decodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + + processResponseHeaders(false, [](const HttpHeaders&, ProcessingResponse& resp, HeadersResponse&) { + ProtobufWkt::Struct foobar; + (*foobar.mutable_fields())["foo"].set_string_value("bar"); + auto metadata_mut = resp.mutable_dynamic_metadata()->mutable_fields(); + auto mut_struct = (*metadata_mut)["envoy.filters.http.ext_proc"].mutable_struct_value(); + *mut_struct = foobar; + }); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->encodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + EXPECT_EQ("bar", dynamic_metadata_.filter_metadata() + .at("envoy.filters.http.ext_proc") + .fields() + .at("foo") + .string_value()); + + filter_->onDestroy(); +} + +// Verify that when returning an response with dynamic_metadata field set, the filter emits +// dynamic metadata to namespaces other than its own. +TEST_F(HttpFilterTest, EmitDynamicMetadataArbitraryNamespace) { + // Configure the filter to only pass response headers to ext server. + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SKIP" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + receiving_namespaces: + untyped: + - envoy.filters.http.ext_authz + )EOF"); + + Buffer::OwnedImpl empty_chunk; + + EXPECT_EQ(FilterHeadersStatus::Continue, filter_->decodeHeaders(request_headers_, false)); + EXPECT_EQ(FilterDataStatus::Continue, filter_->decodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + + processResponseHeaders(false, [](const HttpHeaders&, ProcessingResponse& resp, HeadersResponse&) { + ProtobufWkt::Struct foobar; + (*foobar.mutable_fields())["foo"].set_string_value("bar"); + auto metadata_mut = resp.mutable_dynamic_metadata()->mutable_fields(); + auto mut_struct = (*metadata_mut)["envoy.filters.http.ext_authz"].mutable_struct_value(); + *mut_struct = foobar; + }); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->encodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + EXPECT_EQ("bar", dynamic_metadata_.filter_metadata() + .at("envoy.filters.http.ext_authz") + .fields() + .at("foo") + .string_value()); + + filter_->onDestroy(); +} + +// Verify that when returning an response with dynamic_metadata field set, the +// filter does not emit metadata when no allowed namespaces are configured. +TEST_F(HttpFilterTest, DisableEmitDynamicMetadata) { + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SEND" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + )EOF"); + + Buffer::OwnedImpl empty_chunk; + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); + processRequestHeaders(false, absl::nullopt); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->decodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + + processResponseHeaders(false, [](const HttpHeaders&, ProcessingResponse& resp, HeadersResponse&) { + ProtobufWkt::Struct foobar; + (*foobar.mutable_fields())["foo"].set_string_value("bar"); + auto metadata_mut = resp.mutable_dynamic_metadata()->mutable_fields(); + auto mut_struct = (*metadata_mut)["envoy.filters.http.ext_proc"].mutable_struct_value(); + *mut_struct = foobar; + }); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->encodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + EXPECT_EQ(0, dynamic_metadata_.filter_metadata().size()); + + filter_->onDestroy(); +} + +// Verify that when returning an response with dynamic_metadata field set, the +// filter does not emit metadata to namespaces which are not allowed. +TEST_F(HttpFilterTest, DisableEmittingDynamicMetadataToDisallowedNamespaces) { + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SEND" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + receiving_namespaces: + untyped: + - envoy.filters.http.ext_proc + )EOF"); + + Buffer::OwnedImpl empty_chunk; + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); + processRequestHeaders(false, absl::nullopt); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->decodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + + processResponseHeaders(false, [](const HttpHeaders&, ProcessingResponse& resp, HeadersResponse&) { + ProtobufWkt::Struct foobar; + (*foobar.mutable_fields())["foo"].set_string_value("bar"); + auto metadata_mut = resp.mutable_dynamic_metadata()->mutable_fields(); + auto mut_struct = (*metadata_mut)["envoy.filters.http.ext_authz"].mutable_struct_value(); + *mut_struct = foobar; + }); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->encodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + EXPECT_EQ(0, dynamic_metadata_.filter_metadata().size()); + + filter_->onDestroy(); +} + +// Verify that when returning an response with dynamic_metadata field set, the filter emits +// dynamic metadata and later emissions overwrite earlier ones. +TEST_F(HttpFilterTest, EmitDynamicMetadataUseLast) { + // Configure the filter to only pass response headers to ext server. + initialize(R"EOF( + grpc_service: + envoy_grpc: + cluster_name: "ext_proc_server" + processing_mode: + request_header_mode: "SEND" + response_header_mode: "SEND" + request_body_mode: "NONE" + response_body_mode: "NONE" + request_trailer_mode: "SKIP" + response_trailer_mode: "SKIP" + metadata_options: + receiving_namespaces: + untyped: + - envoy.filters.http.ext_proc + )EOF"); + + Buffer::OwnedImpl empty_chunk; + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); + processRequestHeaders(false, [](const HttpHeaders&, ProcessingResponse& resp, HeadersResponse&) { + ProtobufWkt::Struct batbaz; + (*batbaz.mutable_fields())["bat"].set_string_value("baz"); + auto metadata_mut = resp.mutable_dynamic_metadata()->mutable_fields(); + auto mut_struct = (*metadata_mut)["envoy.filters.http.ext_proc"].mutable_struct_value(); + *mut_struct = batbaz; + }); + EXPECT_EQ(FilterDataStatus::Continue, filter_->decodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); + + EXPECT_EQ(FilterHeadersStatus::StopIteration, filter_->encodeHeaders(response_headers_, false)); + + processResponseHeaders(false, [](const HttpHeaders&, ProcessingResponse& resp, HeadersResponse&) { + ProtobufWkt::Struct foobar; + (*foobar.mutable_fields())["foo"].set_string_value("bar"); + auto metadata_mut = resp.mutable_dynamic_metadata()->mutable_fields(); + auto mut_struct = (*metadata_mut)["envoy.filters.http.ext_proc"].mutable_struct_value(); + *mut_struct = foobar; + }); + + EXPECT_EQ(FilterDataStatus::Continue, filter_->encodeData(empty_chunk, true)); + EXPECT_EQ(FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); + + EXPECT_FALSE(dynamic_metadata_.filter_metadata() + .at("envoy.filters.http.ext_proc") + .fields() + .contains("bat")); + + EXPECT_EQ("bar", dynamic_metadata_.filter_metadata() + .at("envoy.filters.http.ext_proc") + .fields() + .at("foo") + .string_value()); + + filter_->onDestroy(); +} + class HttpFilter2Test : public HttpFilterTest, public ::Envoy::Http::HttpConnectionManagerImplMixin {}; diff --git a/test/extensions/filters/http/ext_proc/ordering_test.cc b/test/extensions/filters/http/ext_proc/ordering_test.cc index 744692ef22ff5..06d1e89e4aba7 100644 --- a/test/extensions/filters/http/ext_proc/ordering_test.cc +++ b/test/extensions/filters/http/ext_proc/ordering_test.cc @@ -7,6 +7,7 @@ #include "test/extensions/filters/http/ext_proc/mock_server.h" #include "test/mocks/event/mocks.h" #include "test/mocks/http/mocks.h" +#include "test/mocks/local_info/mocks.h" #include "test/mocks/network/mocks.h" #include "test/mocks/router/mocks.h" #include "test/mocks/stream_info/mocks.h" @@ -70,8 +71,11 @@ class OrderingTest : public testing::Test { if (cb) { (*cb)(proto_config); } - config_ = std::make_shared(proto_config, kMessageTimeout, kMaxMessageTimeoutMs, - *stats_store_.rootScope(), ""); + config_ = std::make_shared( + proto_config, kMessageTimeout, kMaxMessageTimeoutMs, *stats_store_.rootScope(), "", + std::make_shared( + Envoy::Extensions::Filters::Common::Expr::createBuilder(nullptr)), + local_info_); filter_ = std::make_unique(config_, std::move(client_), proto_config.grpc_service()); filter_->setEncoderFilterCallbacks(encoder_callbacks_); filter_->setDecoderFilterCallbacks(decoder_callbacks_); @@ -212,6 +216,7 @@ class OrderingTest : public testing::Test { Http::TestResponseHeaderMapImpl response_headers_; Http::TestRequestTrailerMapImpl request_trailers_; Http::TestResponseTrailerMapImpl response_trailers_; + NiceMock local_info_; }; // A base class for tests that will check that gRPC streams fail while being created diff --git a/test/extensions/filters/http/ext_proc/unit_test_fuzz/BUILD b/test/extensions/filters/http/ext_proc/unit_test_fuzz/BUILD index 2a7265e6a63b3..630a47ea12dfb 100644 --- a/test/extensions/filters/http/ext_proc/unit_test_fuzz/BUILD +++ b/test/extensions/filters/http/ext_proc/unit_test_fuzz/BUILD @@ -13,6 +13,7 @@ envoy_package() envoy_cc_mock( name = "ext_proc_mocks", hdrs = ["mocks.h"], + tags = ["skip_on_windows"], deps = [ "//source/extensions/filters/http/ext_proc:client_interface", "@envoy_api//envoy/service/ext_proc/v3:pkg_cc_proto", @@ -33,12 +34,14 @@ envoy_cc_fuzz_test( name = "ext_proc_unit_test_fuzz", srcs = ["ext_proc_unit_test_fuzz.cc"], corpus = "ext_proc_corpus", + tags = ["skip_on_windows"], deps = [ ":ext_proc_mocks", ":ext_proc_unit_test_fuzz_proto_cc_proto", "//source/extensions/filters/http/ext_proc:config", "//test/extensions/filters/http/common/fuzz:http_filter_fuzzer_lib", "//test/mocks/http:http_mocks", + "//test/mocks/local_info:local_info_mocks", "//test/mocks/network:network_mocks", ], ) diff --git a/test/extensions/filters/http/ext_proc/unit_test_fuzz/ext_proc_unit_test_fuzz.cc b/test/extensions/filters/http/ext_proc/unit_test_fuzz/ext_proc_unit_test_fuzz.cc index 984b828e0e02b..184c4be323655 100644 --- a/test/extensions/filters/http/ext_proc/unit_test_fuzz/ext_proc_unit_test_fuzz.cc +++ b/test/extensions/filters/http/ext_proc/unit_test_fuzz/ext_proc_unit_test_fuzz.cc @@ -5,6 +5,7 @@ #include "test/extensions/filters/http/ext_proc/unit_test_fuzz/mocks.h" #include "test/fuzz/fuzz_runner.h" #include "test/mocks/http/mocks.h" +#include "test/mocks/local_info/mocks.h" #include "test/mocks/network/mocks.h" using testing::Return; @@ -45,7 +46,8 @@ class FuzzerMocks { NiceMock request_trailers_; NiceMock response_trailers_; NiceMock buffer_; - testing::NiceMock async_client_stream_info_; + NiceMock async_client_stream_info_; + NiceMock local_info_; }; DEFINE_PROTO_FUZZER( @@ -56,6 +58,17 @@ DEFINE_PROTO_FUZZER( ENVOY_LOG_MISC(debug, "EnvoyException during validation: {}", e.what()); return; } + + // ASAN fuzz testing is producing an error on CEL parsing that is believed to be a false positive. + // It is determined that the error is unrelated to the implementation of request and response + // attributes as demonstrated here + // https://github.com/envoyproxy/envoy/compare/main...jbohanon:envoy:bug/cel-parser-antlr-exception-use-after-free. + // Discussion on this is located at https://github.com/envoyproxy/envoy/pull/31017 + if (!input.config().request_attributes().empty() || + !input.config().response_attributes().empty()) { + return; + } + static FuzzerMocks mocks; NiceMock stats_store; @@ -71,8 +84,10 @@ DEFINE_PROTO_FUZZER( try { config = std::make_shared( - proto_config, std::chrono::milliseconds(200), 200, *stats_store.rootScope(), - "ext_proc_prefix"); + proto_config, std::chrono::milliseconds(200), 200, *stats_store.rootScope(), "", + std::make_shared( + Envoy::Extensions::Filters::Common::Expr::createBuilder(nullptr)), + mocks.local_info_); } catch (const EnvoyException& e) { ENVOY_LOG_MISC(debug, "EnvoyException during ext_proc filter config validation: {}", e.what()); return; diff --git a/test/extensions/filters/http/fault/fault_filter_test.cc b/test/extensions/filters/http/fault/fault_filter_test.cc index 2a8cac10b8081..c831196a69cb8 100644 --- a/test/extensions/filters/http/fault/fault_filter_test.cc +++ b/test/extensions/filters/http/fault/fault_filter_test.cc @@ -246,7 +246,7 @@ TEST_F(FaultFilterTest, AbortWithHttpStatus) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) .Times(0); // Abort related calls @@ -266,7 +266,7 @@ TEST_F(FaultFilterTest, AbortWithHttpStatus) { EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -300,7 +300,7 @@ TEST_F(FaultFilterTest, HeaderAbortWithHttpStatus) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) .Times(0); // Abort related calls @@ -322,7 +322,7 @@ TEST_F(FaultFilterTest, HeaderAbortWithHttpStatus) { EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -356,7 +356,7 @@ TEST_F(FaultFilterTest, AbortWithGrpcStatus) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) .Times(0); // Abort related calls @@ -377,7 +377,7 @@ TEST_F(FaultFilterTest, AbortWithGrpcStatus) { encodeHeaders_(HeaderMapEqualRef(&response_headers), true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -406,7 +406,7 @@ TEST_F(FaultFilterTest, HeaderAbortWithGrpcStatus) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) .Times(0); // Abort related calls @@ -428,7 +428,7 @@ TEST_F(FaultFilterTest, HeaderAbortWithGrpcStatus) { encodeHeaders_(HeaderMapEqualRef(&response_headers), true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -457,7 +457,7 @@ TEST_F(FaultFilterTest, HeaderAbortWithHttpAndGrpcStatus) { EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) .Times(0); // Abort related calls @@ -479,7 +479,7 @@ TEST_F(FaultFilterTest, HeaderAbortWithHttpAndGrpcStatus) { EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -585,7 +585,7 @@ TEST_F(FaultFilterTest, FixedDelayDeprecatedPercentAndNonZeroDuration) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -593,7 +593,7 @@ TEST_F(FaultFilterTest, FixedDelayDeprecatedPercentAndNonZeroDuration) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_EQ(Http::FilterDataStatus::StopIterationAndWatermark, filter_->decodeData(data_, false)); EXPECT_EQ(1UL, config_->stats().active_faults_.value()); @@ -639,7 +639,7 @@ TEST_F(FaultFilterTest, ConsecutiveDelayFaults) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)) .Times(2); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, dynamicMetadata()) .WillOnce(ReturnRef(dynamic_metadata)) @@ -654,7 +654,7 @@ TEST_F(FaultFilterTest, ConsecutiveDelayFaults) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_EQ(Http::FilterDataStatus::StopIterationAndWatermark, filter_->decodeData(data_, false)); EXPECT_EQ(1UL, config_->stats().active_faults_.value()); @@ -720,7 +720,7 @@ TEST_F(FaultFilterTest, DelayForDownstreamCluster) { .WillOnce(Return(500UL)); expectDelayTimer(500UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -730,7 +730,7 @@ TEST_F(FaultFilterTest, DelayForDownstreamCluster) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_EQ(Http::FilterDataStatus::StopIterationAndWatermark, filter_->decodeData(data_, false)); @@ -769,7 +769,7 @@ TEST_F(FaultFilterTest, DelayForDownstreamClusterDisableTracing) { .WillOnce(Return(500UL)); expectDelayTimer(500UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -779,7 +779,7 @@ TEST_F(FaultFilterTest, DelayForDownstreamClusterDisableTracing) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); EXPECT_EQ(Http::FilterDataStatus::StopIterationAndWatermark, filter_->decodeData(data_, false)); @@ -828,7 +828,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbortDownstream) { expectDelayTimer(500UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -854,7 +854,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbortDownstream) { EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); timer_->invokeCallback(); @@ -893,7 +893,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbort) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -915,7 +915,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbort) { EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); @@ -947,7 +947,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbortDownstreamNodes) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); request_headers_.addCopy("x-envoy-downstream-service-node", "canary"); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, @@ -969,7 +969,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbortDownstreamNodes) { EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); @@ -1011,7 +1011,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbortHeaderMatchSuccess) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -1032,7 +1032,7 @@ TEST_F(FaultFilterTest, FixedDelayAndAbortHeaderMatchSuccess) { encodeHeaders_(HeaderMapEqualRef(&response_headers), false)); EXPECT_CALL(decoder_filter_callbacks_, encodeData(_, true)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); @@ -1095,7 +1095,7 @@ TEST_F(FaultFilterTest, TimerResetAfterStreamReset) { EXPECT_CALL(*timer_, enableTimer(std::chrono::milliseconds(5000UL), _)); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(0UL, config_->stats().delays_injected_.value()); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, @@ -1114,7 +1114,7 @@ TEST_F(FaultFilterTest, TimerResetAfterStreamReset) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()).Times(0); EXPECT_EQ(0UL, config_->stats().aborts_injected_.value()); @@ -1149,7 +1149,7 @@ TEST_F(FaultFilterTest, FaultWithTargetClusterMatchSuccess) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -1157,7 +1157,7 @@ TEST_F(FaultFilterTest, FaultWithTargetClusterMatchSuccess) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_CALL(decoder_filter_callbacks_, continueDecoding()); timer_->invokeCallback(); @@ -1254,7 +1254,7 @@ TEST_F(FaultFilterTest, RouteFaultOverridesListenerFault) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -1355,7 +1355,7 @@ TEST_F(FaultFilterRateLimitTest, DelayWithResponseRateLimitEnabled) { expectDelayTimer(5000UL); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::DelayInjected)); + setResponseFlag(StreamInfo::CoreResponseFlag::DelayInjected)); // Rate limiter related calls. ON_CALL(encoder_filter_callbacks_, encoderBufferLimit()).WillByDefault(Return(1100)); @@ -1369,7 +1369,7 @@ TEST_F(FaultFilterRateLimitTest, DelayWithResponseRateLimitEnabled) { EXPECT_CALL(runtime_.snapshot_, getInteger("fault.http.abort.http_status", _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_, encodeHeaders_(_, _)).Times(0); EXPECT_CALL(decoder_filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FaultInjected)) + setResponseFlag(StreamInfo::CoreResponseFlag::FaultInjected)) .Times(0); EXPECT_EQ(Http::FilterDataStatus::StopIterationAndWatermark, filter_->decodeData(data_, false)); EXPECT_EQ(1UL, config_->stats().active_faults_.value()); diff --git a/test/extensions/filters/http/file_system_buffer/filter_integration_test.cc b/test/extensions/filters/http/file_system_buffer/filter_integration_test.cc index 46fdd93a94ba2..0982e77ad4a5d 100644 --- a/test/extensions/filters/http/file_system_buffer/filter_integration_test.cc +++ b/test/extensions/filters/http/file_system_buffer/filter_integration_test.cc @@ -75,7 +75,7 @@ TEST_P(FileSystemBufferIntegrationTest, RequestAndResponseWithGiantBodyBuffer) { // Not quite as giant as the memory buffer's integration test uses - with // disk operations involved that size risks timing out the test. testRouterRequestAndResponseWithBody(1024 * 1024, 1024 * 1024, false, false, nullptr, - std::chrono::milliseconds(25000) * TSAN_TIMEOUT_FACTOR); + std::chrono::milliseconds(25000) * TIMEOUT_FACTOR); } TEST_P(FileSystemBufferIntegrationTest, HeaderOnlyRequestAndResponseBuffer) { diff --git a/test/extensions/filters/http/grpc_http1_reverse_bridge/reverse_bridge_test.cc b/test/extensions/filters/http/grpc_http1_reverse_bridge/reverse_bridge_test.cc index b8bbd517e458b..8c6609dbf17f1 100644 --- a/test/extensions/filters/http/grpc_http1_reverse_bridge/reverse_bridge_test.cc +++ b/test/extensions/filters/http/grpc_http1_reverse_bridge/reverse_bridge_test.cc @@ -481,6 +481,7 @@ TEST_F(ReverseBridgeTest, GrpcRequestInternalError) { {{":status", "400"}, {"content-type", "application/x-protobuf"}}); EXPECT_EQ(Http::FilterHeadersStatus::Continue, filter_->encodeHeaders(headers, false)); EXPECT_THAT(headers, HeaderValueOf(Http::Headers::get().ContentType, "application/grpc")); + EXPECT_THAT(headers, HeaderValueOf(Http::Headers::get().Status, "200")); { // First few calls should drain the buffer diff --git a/test/extensions/filters/http/health_check/health_check_test.cc b/test/extensions/filters/http/health_check/health_check_test.cc index 0513d731b6580..09920659d24e5 100644 --- a/test/extensions/filters/http/health_check/health_check_test.cc +++ b/test/extensions/filters/http/health_check/health_check_test.cc @@ -241,7 +241,7 @@ TEST_F(HealthCheckFilterNoPassThroughTest, HealthCheckFailedCallbackCalled) { })); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck)); + setResponseFlag(StreamInfo::CoreResponseFlag::FailedLocalHealthCheck)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -311,7 +311,7 @@ TEST_F(HealthCheckFilterCachingTest, CachedServiceUnavailableCallbackCalled) { })); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck)); + setResponseFlag(StreamInfo::CoreResponseFlag::FailedLocalHealthCheck)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, true)); @@ -351,7 +351,7 @@ TEST_F(HealthCheckFilterCachingTest, All) { // Verify that the next request uses the cached value without setting the degraded header. prepareFilter(true); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck)); + setResponseFlag(StreamInfo::CoreResponseFlag::FailedLocalHealthCheck)); EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&health_check_response), true)) .Times(1) .WillRepeatedly(Invoke([&](Http::ResponseHeaderMap& headers, bool end_stream) { @@ -385,7 +385,7 @@ TEST_F(HealthCheckFilterCachingTest, DegradedHeader) { // Verify that the next request uses the cached value and that the x-envoy-degraded header is set. prepareFilter(true); EXPECT_CALL(callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::FailedLocalHealthCheck)); + setResponseFlag(StreamInfo::CoreResponseFlag::FailedLocalHealthCheck)); EXPECT_CALL(callbacks_, encodeHeaders_(HeaderMapEqualRef(&health_check_response), true)) .Times(1) .WillRepeatedly(Invoke([&](Http::ResponseHeaderMap& headers, bool end_stream) { diff --git a/test/extensions/filters/http/ratelimit/ratelimit_test.cc b/test/extensions/filters/http/ratelimit/ratelimit_test.cc index 93da09c9f600a..db63d1b5be2c9 100644 --- a/test/extensions/filters/http/ratelimit/ratelimit_test.cc +++ b/test/extensions/filters/http/ratelimit/ratelimit_test.cc @@ -249,7 +249,7 @@ TEST_F(HttpRateLimitFilterTest, OkResponse) { EXPECT_CALL(filter_callbacks_, continueDecoding()); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); request_callbacks_->complete(Filters::Common::RateLimit::LimitStatus::OK, nullptr, nullptr, nullptr, "", nullptr); @@ -291,7 +291,7 @@ TEST_F(HttpRateLimitFilterTest, OkResponseWithHeaders) { EXPECT_CALL(filter_callbacks_, continueDecoding()); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); Http::HeaderMapPtr request_headers_to_add{ @@ -347,7 +347,7 @@ TEST_F(HttpRateLimitFilterTest, OkResponseWithFilterHeaders) { EXPECT_CALL(filter_callbacks_, continueDecoding()); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); auto descriptor_statuses = { @@ -458,7 +458,7 @@ TEST_F(HttpRateLimitFilterTest, ErrorResponse) { EXPECT_EQ(Http::FilterDataStatus::Continue, filter_->decodeData(data_, false)); EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->decodeTrailers(request_trailers_)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); EXPECT_EQ( @@ -486,7 +486,7 @@ TEST_F(HttpRateLimitFilterTest, ErrorResponseWithFailureModeAllowOff) { filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimitServiceError)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimitServiceError)); EXPECT_CALL(filter_callbacks_, encodeHeaders_(_, true)) .WillOnce(Invoke([&](const Http::ResponseHeaderMap& headers, bool) -> void { @@ -523,7 +523,7 @@ TEST_F(HttpRateLimitFilterTest, ErrorResponseWithFailureModeAllowOffAndCustomSta filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimitServiceError)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimitServiceError)); EXPECT_CALL(filter_callbacks_, encodeHeaders_(_, true)) .WillOnce(Invoke([&](const Http::ResponseHeaderMap& headers, bool) -> void { @@ -560,7 +560,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponse) { filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl()}; Http::TestResponseHeaderMapImpl response_headers{ @@ -613,7 +613,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithDynamicMetadata) { })); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl()}; Http::TestResponseHeaderMapImpl response_headers{ @@ -658,7 +658,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithHeaders) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::HeaderMapPtr rl_headers{new Http::TestResponseHeaderMapImpl{ {"x-ratelimit-limit", "1000"}, {"x-ratelimit-remaining", "0"}, {"retry-after", "33"}}}; @@ -710,7 +710,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithBody) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); const std::string response_body = "this is a custom over limit response body."; const std::string content_length = std::to_string(response_body.length()); @@ -773,7 +773,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithBodyAndContentType) { EXPECT_EQ(Http::FilterTrailersStatus::Continue, filter_->encodeTrailers(response_trailers_)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); const std::string response_body = R"EOF( { "message": "this is a custom over limit response body as json.", "retry-after": "33" } @@ -835,7 +835,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithFilterHeaders) { }))); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); EXPECT_EQ(Http::FilterHeadersStatus::StopIteration, filter_->decodeHeaders(request_headers_, false)); @@ -890,7 +890,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithoutEnvoyRateLimitedHeader) { filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl()}; Http::TestResponseHeaderMapImpl response_headers{{":status", "429"}}; @@ -970,7 +970,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithRateLimitedStatus) { filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl()}; Http::TestResponseHeaderMapImpl response_headers{ @@ -1011,7 +1011,7 @@ TEST_F(HttpRateLimitFilterTest, LimitResponseWithInvalidRateLimitedStatus) { filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl()}; Http::TestResponseHeaderMapImpl response_headers{ @@ -1642,7 +1642,7 @@ TEST_F(HttpRateLimitFilterTest, StatsWithPrefix) { filter_->decodeHeaders(request_headers_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl()}; Http::TestResponseHeaderMapImpl response_headers{ diff --git a/test/extensions/filters/http/rbac/rbac_filter_integration_test.cc b/test/extensions/filters/http/rbac/rbac_filter_integration_test.cc index a4b69f6493e58..f78248117d592 100644 --- a/test/extensions/filters/http/rbac/rbac_filter_integration_test.cc +++ b/test/extensions/filters/http/rbac/rbac_filter_integration_test.cc @@ -100,6 +100,24 @@ name: rbac - any: true )EOF"; +const std::string RBAC_CONFIG_PERMISSION_WITH_URI_PATH_TEMPLATE_MATCH = R"EOF( +name: rbac +typed_config: + "@type": type.googleapis.com/envoy.extensions.filters.http.rbac.v3.RBAC + rules: + action: DENY + policies: + foo: + permissions: + - uri_template: + name: envoy.path.match.uri_template.uri_template_matcher + typed_config: + "@type": type.googleapis.com/envoy.extensions.path.match.uri_template.v3.UriTemplateMatchConfig + path_template: "/test/deny/path" + principals: + - any: true +)EOF"; + const std::string RBAC_CONFIG_WITH_LOG_ACTION = R"EOF( name: rbac typed_config: @@ -771,6 +789,27 @@ TEST_P(RBACIntegrationTest, PathIgnoreCase) { } } +TEST_P(RBACIntegrationTest, PermissionUriPathTemplateMatch) { + config_helper_.prependFilter(RBAC_CONFIG_PERMISSION_WITH_URI_PATH_TEMPLATE_MATCH); + initialize(); + + codec_client_ = makeHttpConnection(lookupPort("http")); + + auto response = codec_client_->makeRequestWithBody( + Http::TestRequestHeaderMapImpl{ + {":method", "POST"}, + {":path", "/test/deny/path"}, + {":scheme", "http"}, + {":authority", "sni.lyft.com"}, + {"x-forwarded-for", "10.0.0.1"}, + }, + 1024); + + ASSERT_TRUE(response->waitForEndStream()); + ASSERT_TRUE(response->complete()); + EXPECT_EQ("403", response->headers().getStatusValue()); +} + TEST_P(RBACIntegrationTest, LogConnectionAllow) { config_helper_.prependFilter(RBAC_CONFIG_WITH_LOG_ACTION); initialize(); diff --git a/test/extensions/filters/http/wasm/test_data/metadata_rust.rs b/test/extensions/filters/http/wasm/test_data/metadata_rust.rs index da95f60555c86..901ca7dfa8705 100644 --- a/test/extensions/filters/http/wasm/test_data/metadata_rust.rs +++ b/test/extensions/filters/http/wasm/test_data/metadata_rust.rs @@ -15,7 +15,7 @@ impl Context for TestRoot {} impl RootContext for TestRoot { fn on_tick(&mut self) { - if let Some(value) = self.get_property(vec!["node", "metadata", "wasm_node_get_key"]) { + if let Some(value) = self.get_property(vec!["xds", "node", "metadata", "wasm_node_get_key"]) { debug!("onTick {}", String::from_utf8(value).unwrap()); } else { debug!("missing node metadata"); diff --git a/test/extensions/filters/http/wasm/test_data/test_cpp.cc b/test/extensions/filters/http/wasm/test_data/test_cpp.cc index e5952c8896f81..d2907b308e380 100644 --- a/test/extensions/filters/http/wasm/test_data/test_cpp.cc +++ b/test/extensions/filters/http/wasm/test_data/test_cpp.cc @@ -81,6 +81,7 @@ bool TestRootContext::onConfigure(size_t size) { {{"plugin_vm_id"}, "vm_id"}, {{"listener_direction"}, std::string("\x1\0\0\0\0\0\0\0\0", 8)}, // INBOUND {{"listener_metadata"}, ""}, + {{"xds", "node", "metadata", "istio.io/metadata"}, "sample_data"}, }; for (const auto& property : properties) { std::string value; diff --git a/test/extensions/filters/http/wasm/wasm_filter_test.cc b/test/extensions/filters/http/wasm/wasm_filter_test.cc index 1cffc3a67b8c6..cf3d2fd590be1 100644 --- a/test/extensions/filters/http/wasm/wasm_filter_test.cc +++ b/test/extensions/filters/http/wasm/wasm_filter_test.cc @@ -1775,14 +1775,13 @@ TEST_P(WasmHttpFilterTest, Property) { // TODO(PiotrSikora): test not yet implemented using Rust SDK. return; } - setupTest("", "property"); - setupFilter(); envoy::config::core::v3::Node node_data; ProtobufWkt::Value node_val; node_val.set_string_value("sample_data"); (*node_data.mutable_metadata()->mutable_fields())["istio.io/metadata"] = node_val; EXPECT_CALL(local_info_, node()).WillRepeatedly(ReturnRef(node_data)); - + setupTest("", "property"); + setupFilter(); request_stream_info_.metadata_.mutable_filter_metadata()->insert( Protobuf::MapPair( "envoy.filters.http.wasm", diff --git a/test/extensions/filters/network/dubbo_proxy/conn_manager_test.cc b/test/extensions/filters/network/dubbo_proxy/conn_manager_test.cc index 60650be44870c..917a0e404bde2 100644 --- a/test/extensions/filters/network/dubbo_proxy/conn_manager_test.cc +++ b/test/extensions/filters/network/dubbo_proxy/conn_manager_test.cc @@ -871,7 +871,7 @@ TEST_F(ConnectionManagerTest, OnDataWithFilterSendsLocalReply) { // First filter sends local reply. EXPECT_CALL(*first_filter, onMessageDecoded(_, _)) .WillOnce(Invoke([&](MessageMetadataSharedPtr, ContextSharedPtr) -> FilterStatus { - callbacks->streamInfo().setResponseFlag(StreamInfo::ResponseFlag::NoRouteFound); + callbacks->streamInfo().setResponseFlag(StreamInfo::CoreResponseFlag::NoRouteFound); callbacks->sendLocalReply(direct_response, false); return FilterStatus::AbortIteration; })); diff --git a/test/extensions/filters/network/ext_authz/ext_authz_test.cc b/test/extensions/filters/network/ext_authz/ext_authz_test.cc index 29e9f6e388c46..2091cf1332d70 100644 --- a/test/extensions/filters/network/ext_authz/ext_authz_test.cc +++ b/test/extensions/filters/network/ext_authz/ext_authz_test.cc @@ -216,7 +216,7 @@ TEST_F(ExtAuthzFilterTest, DeniedWithOnData) { EXPECT_CALL(filter_callbacks_.connection_, close(Network::ConnectionCloseType::NoFlush, _)); EXPECT_CALL(filter_callbacks_.connection_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UnauthorizedExternalService)); + setResponseFlag(StreamInfo::CoreResponseFlag::UnauthorizedExternalService)); EXPECT_CALL( filter_callbacks_.connection_.stream_info_, setResponseCodeDetails(Filters::Common::ExtAuthz::ResponseCodeDetails::get().AuthzDenied)); @@ -291,7 +291,7 @@ TEST_F(ExtAuthzFilterTest, FailClose) { EXPECT_CALL(filter_callbacks_.connection_, close(_, _)); EXPECT_CALL(filter_callbacks_, continueReading()).Times(0); EXPECT_CALL(filter_callbacks_.connection_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UnauthorizedExternalService)); + setResponseFlag(StreamInfo::CoreResponseFlag::UnauthorizedExternalService)); EXPECT_CALL( filter_callbacks_.connection_.stream_info_, setResponseCodeDetails(Filters::Common::ExtAuthz::ResponseCodeDetails::get().AuthzError)); @@ -463,7 +463,7 @@ TEST_F(ExtAuthzFilterTest, ImmediateNOK) { EXPECT_TRUE(TestUtility::protoEqual(returned_dynamic_metadata, dynamic_metadata)); })); EXPECT_CALL(filter_callbacks_.connection_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UnauthorizedExternalService)); + setResponseFlag(StreamInfo::CoreResponseFlag::UnauthorizedExternalService)); EXPECT_CALL( filter_callbacks_.connection_.stream_info_, setResponseCodeDetails(Filters::Common::ExtAuthz::ResponseCodeDetails::get().AuthzDenied)); diff --git a/test/extensions/filters/network/http_connection_manager/config_filter_chain_test.cc b/test/extensions/filters/network/http_connection_manager/config_filter_chain_test.cc index 1c42d6a1f420f..372a971e0a187 100644 --- a/test/extensions/filters/network/http_connection_manager/config_filter_chain_test.cc +++ b/test/extensions/filters/network/http_connection_manager/config_filter_chain_test.cc @@ -172,7 +172,7 @@ stat_prefix: router Http::TestRequestHeaderMapImpl headers; missing_config_filter->setDecoderFilterCallbacks(decoder_callbacks); missing_config_filter->decodeHeaders(headers, false); - EXPECT_TRUE(stream_info.hasResponseFlag(StreamInfo::ResponseFlag::NoFilterConfigFound)); + EXPECT_TRUE(stream_info.hasResponseFlag(StreamInfo::CoreResponseFlag::NoFilterConfigFound)); } // Tests where upgrades are configured on via the HCM. diff --git a/test/extensions/filters/network/local_ratelimit/local_ratelimit_test.cc b/test/extensions/filters/network/local_ratelimit/local_ratelimit_test.cc index 18f731804d71e..b4e43d706511b 100644 --- a/test/extensions/filters/network/local_ratelimit/local_ratelimit_test.cc +++ b/test/extensions/filters/network/local_ratelimit/local_ratelimit_test.cc @@ -93,7 +93,7 @@ stat_prefix: local_rate_limit_stats // Second connection should be rate limited. ActiveFilter active_filter2(config_); EXPECT_CALL(active_filter2.read_filter_callbacks_.connection_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::UpstreamRetryLimitExceeded)); + setResponseFlag(StreamInfo::CoreResponseFlag::UpstreamRetryLimitExceeded)); EXPECT_CALL(active_filter2.read_filter_callbacks_.connection_, close(Network::ConnectionCloseType::NoFlush, "local_ratelimit_close_over_limit")); EXPECT_EQ(Network::FilterStatus::StopIteration, active_filter2.filter_.onNewConnection()); diff --git a/test/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit_test.cc b/test/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit_test.cc index acfca8c4bcc31..81c567dacf0d8 100644 --- a/test/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit_test.cc +++ b/test/extensions/filters/network/thrift_proxy/filters/ratelimit/ratelimit_test.cc @@ -224,7 +224,7 @@ TEST_F(ThriftRateLimitFilterTest, OkResponse) { EXPECT_CALL(filter_callbacks_, continueDecoding()); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); request_callbacks_->complete(Filters::Common::RateLimit::LimitStatus::OK, nullptr, nullptr, nullptr, "", nullptr); @@ -305,7 +305,7 @@ TEST_F(ThriftRateLimitFilterTest, ErrorResponse) { EXPECT_EQ(ThriftProxy::FilterStatus::Continue, filter_->messageEnd()); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); EXPECT_EQ( @@ -348,7 +348,7 @@ TEST_F(ThriftRateLimitFilterTest, ErrorResponseWithDynamicMetadata) { EXPECT_EQ(ThriftProxy::FilterStatus::Continue, filter_->messageEnd()); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)) + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)) .Times(0); EXPECT_EQ( @@ -380,7 +380,7 @@ TEST_F(ThriftRateLimitFilterTest, ErrorResponseWithFailureModeAllowOff) { EXPECT_EQ(ThriftProxy::AppExceptionType::InternalError, app_ex.type_); })); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimitServiceError)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimitServiceError)); request_callbacks_->complete(Filters::Common::RateLimit::LimitStatus::Error, nullptr, nullptr, nullptr, "", nullptr); @@ -414,7 +414,7 @@ TEST_F(ThriftRateLimitFilterTest, LimitResponse) { })); EXPECT_CALL(filter_callbacks_, continueDecoding()).Times(0); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); request_callbacks_->complete(Filters::Common::RateLimit::LimitStatus::OverLimit, nullptr, nullptr, nullptr, "", nullptr); @@ -445,7 +445,7 @@ TEST_F(ThriftRateLimitFilterTest, LimitResponseWithHeaders) { // TODO(zuercher): Headers are currently ignored, but sendLocalReply is the place to pass them. EXPECT_CALL(filter_callbacks_, sendLocalReply(_, false)); EXPECT_CALL(filter_callbacks_.stream_info_, - setResponseFlag(StreamInfo::ResponseFlag::RateLimited)); + setResponseFlag(StreamInfo::CoreResponseFlag::RateLimited)); Http::ResponseHeaderMapPtr h{new Http::TestResponseHeaderMapImpl(*rl_headers)}; request_callbacks_->complete(Filters::Common::RateLimit::LimitStatus::OverLimit, nullptr, diff --git a/test/extensions/filters/network/thrift_proxy/router_test.cc b/test/extensions/filters/network/thrift_proxy/router_test.cc index 3d6957de5adb0..cd1de06c40da9 100644 --- a/test/extensions/filters/network/thrift_proxy/router_test.cc +++ b/test/extensions/filters/network/thrift_proxy/router_test.cc @@ -763,6 +763,11 @@ TEST_P(ThriftRouterRainidayTest, PoolRemoteConnectionFailure) { context_.server_factory_context_.cluster_manager_.thread_local_cluster_.tcp_conn_pool_ .poolFailure(ConnectionPool::PoolFailureReason::RemoteConnectionFailure); + EXPECT_EQ(1UL, + context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ + ->statsScope() + .counterFromString("thrift.upstream_resp_exception_local.remote_connection_failure") + .value()); EXPECT_EQ(1UL, context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ ->statsScope() @@ -793,6 +798,21 @@ TEST_P(ThriftRouterRainidayTest, PoolLocalConnectionFailure) { context_.server_factory_context_.cluster_manager_.thread_local_cluster_.tcp_conn_pool_ .poolFailure(ConnectionPool::PoolFailureReason::LocalConnectionFailure); + EXPECT_EQ(1UL, + context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ + ->statsScope() + .counterFromString("thrift.upstream_resp_exception_local.local_connection_failure") + .value()); + EXPECT_EQ(1UL, + context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ + ->statsScope() + .counterFromString("thrift.upstream_resp_exception_local") + .value()); + EXPECT_EQ(1UL, + context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ + ->statsScope() + .counterFromString("thrift.upstream_resp_exception") + .value()); EXPECT_EQ(0UL, context_.server_factory_context_.cluster_manager_.thread_local_cluster_ .tcp_conn_pool_.host_->stats_.rq_error_.value()); } @@ -822,6 +842,11 @@ TEST_P(ThriftRouterRainidayTest, PoolTimeout) { context_.server_factory_context_.cluster_manager_.thread_local_cluster_.tcp_conn_pool_ .poolFailure(ConnectionPool::PoolFailureReason::Timeout); + EXPECT_EQ(1UL, + context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ + ->statsScope() + .counterFromString("thrift.upstream_resp_exception_local.timeout") + .value()); EXPECT_EQ(1UL, context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ ->statsScope() @@ -857,6 +882,11 @@ TEST_P(ThriftRouterRainidayTest, PoolOverflowFailure) { context_.server_factory_context_.cluster_manager_.thread_local_cluster_.tcp_conn_pool_ .poolFailure(ConnectionPool::PoolFailureReason::Overflow, true); + EXPECT_EQ(1UL, + context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ + ->statsScope() + .counterFromString("thrift.upstream_resp_exception_local.overflow") + .value()); EXPECT_EQ(1UL, context_.server_factory_context_.cluster_manager_.thread_local_cluster_.cluster_.info_ ->statsScope() @@ -1423,6 +1453,7 @@ TEST_F(ThriftRouterTest, PoolTimeoutUpstreamTimeMeasurement) { dispatcher_.globalTimeSystem().advanceTimeWait(std::chrono::milliseconds(500)); EXPECT_CALL(cluster_store, counter("thrift.upstream_resp_exception")); EXPECT_CALL(cluster_store, counter("thrift.upstream_resp_exception_local")); + EXPECT_CALL(cluster_store, counter("thrift.upstream_resp_exception_local.timeout")); EXPECT_CALL(cluster_store, histogram("thrift.upstream_rq_time", Stats::Histogram::Unit::Milliseconds)) .Times(0); diff --git a/test/extensions/load_balancing_policies/common/benchmark_base_tester.cc b/test/extensions/load_balancing_policies/common/benchmark_base_tester.cc index 3cc30ae2eb693..32a1521c73e45 100644 --- a/test/extensions/load_balancing_policies/common/benchmark_base_tester.cc +++ b/test/extensions/load_balancing_policies/common/benchmark_base_tester.cc @@ -32,10 +32,10 @@ BaseTester::BaseTester(uint64_t num_hosts, uint32_t weighted_subset_percent, uin Upstream::makeHostsPerLocality({hosts}); priority_set_.updateHosts( 0, Upstream::HostSetImpl::partitionHosts(updated_hosts, hosts_per_locality), {}, hosts, {}, - absl::nullopt); + random_.random(), absl::nullopt); local_priority_set_.updateHosts( 0, Upstream::HostSetImpl::partitionHosts(updated_hosts, hosts_per_locality), {}, hosts, {}, - absl::nullopt); + random_.random(), absl::nullopt); } } // namespace Common diff --git a/test/extensions/load_balancing_policies/ring_hash/config_test.cc b/test/extensions/load_balancing_policies/ring_hash/config_test.cc index 19eca2c14a569..2d69ff02226e7 100644 --- a/test/extensions/load_balancing_policies/ring_hash/config_test.cc +++ b/test/extensions/load_balancing_policies/ring_hash/config_test.cc @@ -1,5 +1,6 @@ #include "envoy/config/core/v3/extension.pb.h" #include "envoy/extensions/load_balancing_policies/ring_hash/v3/ring_hash.pb.h" +#include "envoy/extensions/load_balancing_policies/ring_hash/v3/ring_hash.pb.validate.h" #include "source/extensions/load_balancing_policies/ring_hash/config.h" @@ -70,6 +71,20 @@ TEST(RingHashConfigTest, Validate) { context.api_.random_, context.time_system_), EnvoyException, "ring hash: minimum_ring_size (4) > maximum_ring_size (2)"); } + + { + envoy::config::core::v3::TypedExtensionConfig config; + config.set_name("envoy.load_balancing_policies.ring_hash"); + envoy::extensions::load_balancing_policies::ring_hash::v3::RingHash config_msg; + config_msg.mutable_minimum_ring_size()->set_value(0); + + config.mutable_typed_config()->PackFrom(config_msg); + + std::string err; + EXPECT_EQ(Validate(config_msg, &err), false); + EXPECT_EQ(err, "RingHashValidationError.MinimumRingSize: value must be " + "inside range [1, 8388608]"); + } } } // namespace diff --git a/test/extensions/load_balancing_policies/subset/subset_benchmark.cc b/test/extensions/load_balancing_policies/subset/subset_benchmark.cc index d775c8851e335..e09337efca9cc 100644 --- a/test/extensions/load_balancing_policies/subset/subset_benchmark.cc +++ b/test/extensions/load_balancing_policies/subset/subset_benchmark.cc @@ -58,10 +58,10 @@ class SubsetLbTester : public LoadBalancingPolices::Common::BaseTester { void update() { priority_set_.updateHosts( 0, Upstream::HostSetImpl::partitionHosts(smaller_hosts_, smaller_locality_hosts_), nullptr, - {}, host_moved_, absl::nullopt); + {}, host_moved_, random_.random(), absl::nullopt); priority_set_.updateHosts( 0, Upstream::HostSetImpl::partitionHosts(orig_hosts_, orig_locality_hosts_), nullptr, - host_moved_, {}, absl::nullopt); + host_moved_, {}, random_.random(), absl::nullopt); } std::unique_ptr subset_info_; @@ -71,6 +71,7 @@ class SubsetLbTester : public LoadBalancingPolices::Common::BaseTester { Upstream::HostsPerLocalitySharedPtr orig_locality_hosts_; Upstream::HostsPerLocalitySharedPtr smaller_locality_hosts_; Upstream::HostVector host_moved_; + Random::RandomGeneratorImpl random_; }; void benchmarkSubsetLoadBalancerCreate(::benchmark::State& state) { diff --git a/test/extensions/load_balancing_policies/subset/subset_test.cc b/test/extensions/load_balancing_policies/subset/subset_test.cc index 032fc45b56622..d9c241a30f3b7 100644 --- a/test/extensions/load_balancing_policies/subset/subset_test.cc +++ b/test/extensions/load_balancing_policies/subset/subset_test.cc @@ -346,7 +346,7 @@ class SubsetLoadBalancerTest : public Event::TestUsingSimulatedTime, std::make_shared(*local_hosts_), local_hosts_per_locality_, std::make_shared(), HostsPerLocalityImpl::empty(), std::make_shared(), HostsPerLocalityImpl::empty()), - {}, {}, {}, absl::nullopt); + {}, {}, {}, 0, absl::nullopt); auto child_lb_creator = std::make_unique( lb_type_, ring_hash_lb_config_, maglev_lb_config_, round_robin_lb_config_, @@ -501,7 +501,7 @@ class SubsetLoadBalancerTest : public Event::TestUsingSimulatedTime, updateHostsParams(local_hosts_, local_hosts_per_locality_, std::make_shared(*local_hosts_), local_hosts_per_locality_), - {}, {}, remove, absl::nullopt); + {}, {}, remove, 0, absl::nullopt); } for (const auto& host : add) { @@ -518,7 +518,7 @@ class SubsetLoadBalancerTest : public Event::TestUsingSimulatedTime, updateHostsParams(local_hosts_, local_hosts_per_locality_, std::make_shared(*local_hosts_), local_hosts_per_locality_), - {}, add, {}, absl::nullopt); + {}, add, {}, 0, absl::nullopt); } } else if (!add.empty() || !remove.empty()) { local_priority_set_.updateHosts( @@ -526,7 +526,7 @@ class SubsetLoadBalancerTest : public Event::TestUsingSimulatedTime, updateHostsParams(local_hosts_, local_hosts_per_locality_, std::make_shared(*local_hosts_), local_hosts_per_locality_), - {}, add, remove, absl::nullopt); + {}, add, remove, 0, absl::nullopt); } } @@ -1706,6 +1706,7 @@ TEST_P(SubsetLoadBalancerTest, ZoneAwareFallbackAfterUpdate) { envoy::config::core::v3::Locality local_locality; local_locality.set_zone("0"); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(0)); modifyHosts({makeHost("tcp://127.0.0.1:8000", {{"version", "1.0"}}, local_locality)}, {host_set_.hosts_[0]}, absl::optional(0)); @@ -1836,6 +1837,7 @@ TEST_P(SubsetLoadBalancerTest, ZoneAwareFallbackDefaultSubsetAfterUpdate) { envoy::config::core::v3::Locality local_locality; local_locality.set_zone("0"); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(0)); modifyHosts({makeHost("tcp://127.0.0.1:8001", {{"version", "default"}}, local_locality)}, {host_set_.hosts_[1]}, absl::optional(0)); @@ -1962,6 +1964,7 @@ TEST_P(SubsetLoadBalancerTest, ZoneAwareBalancesSubsetsAfterUpdate) { envoy::config::core::v3::Locality local_locality; local_locality.set_zone("0"); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(0)); modifyHosts({makeHost("tcp://127.0.0.1:8001", {{"version", "1.1"}}, local_locality)}, {host_set_.hosts_[1]}, absl::optional(0)); @@ -2116,6 +2119,7 @@ TEST_P(SubsetLoadBalancerTest, ZoneAwareComplicatedBalancesSubsetsAfterUpdate) { envoy::config::core::v3::Locality locality_2; locality_2.set_zone("2"); + EXPECT_CALL(random_, random()).WillRepeatedly(Return(0)); modifyHosts({makeHost("tcp://127.0.0.1:8001", {{"version", "1.1"}}, local_locality)}, {}, absl::optional(0)); diff --git a/test/extensions/resource_monitors/fixed_heap/BUILD b/test/extensions/resource_monitors/fixed_heap/BUILD index 65697704e0602..47d8d0c324fc8 100644 --- a/test/extensions/resource_monitors/fixed_heap/BUILD +++ b/test/extensions/resource_monitors/fixed_heap/BUILD @@ -18,7 +18,6 @@ envoy_extension_cc_test( external_deps = ["abseil_optional"], deps = [ "//source/extensions/resource_monitors/fixed_heap:fixed_heap_monitor", - "//test/test_common:test_runtime_lib", "@envoy_api//envoy/extensions/resource_monitors/fixed_heap/v3:pkg_cc_proto", ], ) diff --git a/test/extensions/resource_monitors/fixed_heap/fixed_heap_monitor_test.cc b/test/extensions/resource_monitors/fixed_heap/fixed_heap_monitor_test.cc index 5c5e558993c21..3dae2b026e50e 100644 --- a/test/extensions/resource_monitors/fixed_heap/fixed_heap_monitor_test.cc +++ b/test/extensions/resource_monitors/fixed_heap/fixed_heap_monitor_test.cc @@ -2,8 +2,6 @@ #include "source/extensions/resource_monitors/fixed_heap/fixed_heap_monitor.h" -#include "test/test_common/test_runtime.h" - #include "absl/types/optional.h" #include "gmock/gmock.h" #include "gtest/gtest.h" @@ -76,48 +74,6 @@ TEST(FixedHeapMonitorTest, ComputeUsageWithRealMemoryStats) { monitor->updateResourceUsage(resource); EXPECT_NEAR(resource.pressure(), expected_usage, 0.0005); } - -//// TODO(Diazalan): Remove two legacy tests after flag is deprecated -TEST(FixedHeapMonitorTest, LegacyComputesCorrectUsage) { - - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues( - {{"envoy.reloadable_features.count_unused_mapped_pages_as_free", "false"}}); - - envoy::extensions::resource_monitors::fixed_heap::v3::FixedHeapConfig config; - config.set_max_heap_size_bytes(1000); - auto stats_reader = std::make_unique(); - EXPECT_CALL(*stats_reader, reservedHeapBytes()).WillOnce(Return(800)); - EXPECT_CALL(*stats_reader, unmappedHeapBytes()).WillOnce(Return(100)); - auto monitor = std::make_unique(config, std::move(stats_reader)); - - ResourcePressure resource; - monitor->updateResourceUsage(resource); - EXPECT_TRUE(resource.hasPressure()); - EXPECT_FALSE(resource.hasError()); - EXPECT_EQ(resource.pressure(), 0.7); -} - -TEST(FixedHeapMonitorTest, LegacyComputeUsageWithRealMemoryStats) { - - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues( - {{"envoy.reloadable_features.count_unused_mapped_pages_as_free", "false"}}); - - envoy::extensions::resource_monitors::fixed_heap::v3::FixedHeapConfig config; - const uint64_t max_heap = 1024 * 1024 * 1024; - config.set_max_heap_size_bytes(max_heap); - auto stats_reader = std::make_unique(); - const double expected_usage = - (stats_reader->reservedHeapBytes() - stats_reader->unmappedHeapBytes()) / - static_cast(max_heap); - auto monitor = std::make_unique(config, std::move(stats_reader)); - - ResourcePressure resource; - monitor->updateResourceUsage(resource); - EXPECT_NEAR(resource.pressure(), expected_usage, 0.0005); -} - } // namespace } // namespace FixedHeapMonitor } // namespace ResourceMonitors diff --git a/test/extensions/tracers/opentelemetry/grpc_trace_exporter_test.cc b/test/extensions/tracers/opentelemetry/grpc_trace_exporter_test.cc index e4da244ae3c69..84db740d5ebfd 100644 --- a/test/extensions/tracers/opentelemetry/grpc_trace_exporter_test.cc +++ b/test/extensions/tracers/opentelemetry/grpc_trace_exporter_test.cc @@ -24,24 +24,24 @@ class OpenTelemetryGrpcTraceExporterTest : public testing::Test { opentelemetry::proto::collector::trace::v1::ExportTraceServiceResponse>; OpenTelemetryGrpcTraceExporterTest() : async_client_(new Grpc::MockAsyncClient) { - expectStreamStart(); + expectTraceExportStart(); } - void expectStreamStart() { + void expectTraceExportStart() { EXPECT_CALL(*async_client_, startRaw(_, _, _, _)) .WillOnce( Invoke([this](absl::string_view, absl::string_view, Grpc::RawAsyncStreamCallbacks& cbs, const Http::AsyncClient::StreamOptions&) { this->callbacks_ = dynamic_cast(&cbs); - return &this->stream_; + return &this->conn_; })); } - void expectStreamMessage(const std::string& expected_message_yaml) { + void expectTraceExportMessage(const std::string& expected_message_yaml) { opentelemetry::proto::collector::trace::v1::ExportTraceServiceRequest expected_message; TestUtility::loadFromYaml(expected_message_yaml, expected_message); - EXPECT_CALL(stream_, isAboveWriteBufferHighWatermark()).WillOnce(Return(false)); - EXPECT_CALL(stream_, sendMessageRaw_(_, false)) + EXPECT_CALL(conn_, isAboveWriteBufferHighWatermark()).WillOnce(Return(false)); + EXPECT_CALL(conn_, sendMessageRaw_(_, true)) .WillOnce(Invoke([expected_message](Buffer::InstancePtr& request, bool) { opentelemetry::proto::collector::trace::v1::ExportTraceServiceRequest message; Buffer::ZeroCopyInputStreamImpl request_stream(std::move(request)); @@ -52,14 +52,14 @@ class OpenTelemetryGrpcTraceExporterTest : public testing::Test { protected: Grpc::MockAsyncClient* async_client_; - Grpc::MockAsyncStream stream_; + Grpc::MockAsyncStream conn_; TraceCallbacks* callbacks_; }; TEST_F(OpenTelemetryGrpcTraceExporterTest, CreateExporterAndExportSpan) { OpenTelemetryGrpcTraceExporter exporter(Grpc::RawAsyncClientPtr{async_client_}); - expectStreamMessage(R"EOF( + expectTraceExportMessage(R"EOF( resource_spans: scope_spans: - spans: @@ -75,8 +75,8 @@ TEST_F(OpenTelemetryGrpcTraceExporterTest, CreateExporterAndExportSpan) { TEST_F(OpenTelemetryGrpcTraceExporterTest, NoExportWithHighWatermark) { OpenTelemetryGrpcTraceExporter exporter(Grpc::RawAsyncClientPtr{async_client_}); - EXPECT_CALL(stream_, isAboveWriteBufferHighWatermark()).WillOnce(Return(true)); - EXPECT_CALL(stream_, sendMessageRaw_(_, false)).Times(0); + EXPECT_CALL(conn_, isAboveWriteBufferHighWatermark()).WillOnce(Return(true)); + EXPECT_CALL(conn_, sendMessageRaw_(_, false)).Times(0); opentelemetry::proto::collector::trace::v1::ExportTraceServiceRequest request; opentelemetry::proto::trace::v1::Span span; span.set_name("tests"); @@ -93,25 +93,25 @@ TEST_F(OpenTelemetryGrpcTraceExporterTest, ExportWithRemoteClose) { - name: "test" )EOF"; - expectStreamMessage(request_yaml); + expectTraceExportMessage(request_yaml); opentelemetry::proto::collector::trace::v1::ExportTraceServiceRequest request; opentelemetry::proto::trace::v1::Span span; span.set_name("test"); *request.add_resource_spans()->add_scope_spans()->add_spans() = span; EXPECT_TRUE(exporter.log(request)); - // Close the stream, now that we've created it. + // Terminate the request, now that we've created it. callbacks_->onRemoteClose(Grpc::Status::Internal, "bad"); - // Second call should make a new stream. - expectStreamStart(); - expectStreamMessage(request_yaml); + // Second call should make a new request. + expectTraceExportStart(); + expectTraceExportMessage(request_yaml); EXPECT_TRUE(exporter.log(request)); } TEST_F(OpenTelemetryGrpcTraceExporterTest, ExportWithNoopCallbacks) { OpenTelemetryGrpcTraceExporter exporter(Grpc::RawAsyncClientPtr{async_client_}); - expectStreamMessage(R"EOF( + expectTraceExportMessage(R"EOF( resource_spans: scope_spans: - spans: diff --git a/test/extensions/upstreams/http/config_test.cc b/test/extensions/upstreams/http/config_test.cc index 8a85979c8d014..c851fa63db32a 100644 --- a/test/extensions/upstreams/http/config_test.cc +++ b/test/extensions/upstreams/http/config_test.cc @@ -32,24 +32,27 @@ class ConfigTest : public ::testing::Test { }; TEST_F(ConfigTest, Basic) { - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_FALSE(config.use_downstream_protocol_); - EXPECT_FALSE(config.use_http2_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_FALSE(config->use_downstream_protocol_); + EXPECT_FALSE(config->use_http2_); } TEST_F(ConfigTest, Downstream) { options_.mutable_use_downstream_protocol_config(); { - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_TRUE(config.use_downstream_protocol_); - EXPECT_FALSE(config.use_http2_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_TRUE(config->use_downstream_protocol_); + EXPECT_FALSE(config->use_http2_); } options_.mutable_use_downstream_protocol_config()->mutable_http2_protocol_options(); { - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_TRUE(config.use_downstream_protocol_); - EXPECT_TRUE(config.use_http2_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_TRUE(config->use_downstream_protocol_); + EXPECT_TRUE(config->use_http2_); } } @@ -60,28 +63,32 @@ TEST(FactoryTest, EmptyProto) { TEST_F(ConfigTest, Auto) { options_.mutable_auto_config(); - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_FALSE(config.use_downstream_protocol_); - EXPECT_TRUE(config.use_http2_); - EXPECT_FALSE(config.use_http3_); - EXPECT_TRUE(config.use_alpn_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_FALSE(config->use_downstream_protocol_); + EXPECT_TRUE(config->use_http2_); + EXPECT_FALSE(config->use_http3_); + EXPECT_TRUE(config->use_alpn_); } TEST_F(ConfigTest, AutoHttp3) { options_.mutable_auto_config(); options_.mutable_auto_config()->mutable_http3_protocol_options(); options_.mutable_auto_config()->mutable_alternate_protocols_cache_options(); - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_TRUE(config.use_http2_); - EXPECT_TRUE(config.use_http3_); - EXPECT_TRUE(config.use_alpn_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_TRUE(config->use_http2_); + EXPECT_TRUE(config->use_http3_); + EXPECT_TRUE(config->use_alpn_); } TEST_F(ConfigTest, AutoHttp3NoCache) { options_.mutable_auto_config(); options_.mutable_auto_config()->mutable_http3_protocol_options(); EXPECT_THROW_WITH_MESSAGE( - ProtocolOptionsConfigImpl config(options_, server_context_), EnvoyException, + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(), + EnvoyException, "alternate protocols cache must be configured when HTTP/3 is enabled with auto_config"); } @@ -93,7 +100,9 @@ TEST_F(ConfigTest, KvStoreConcurrencyFail) { ->mutable_key_value_store_config(); server_context_.options_.concurrency_ = 2; EXPECT_THROW_WITH_MESSAGE( - ProtocolOptionsConfigImpl config(options_, server_context_), EnvoyException, + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(), + EnvoyException, "options has key value store but Envoy has concurrency = 2 : key_value_store_config {\n}\n"); } @@ -180,13 +189,20 @@ TEST_F(ConfigTest, HeaderValidatorConfig) { Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); TestUtility::loadFromYamlAndValidate(yaml_string, options_); #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; - EXPECT_NE(nullptr, config.header_validator_factory_->createClientHeaderValidator( + EXPECT_NE(nullptr, config->header_validator_factory_->createClientHeaderValidator( ::Envoy::Http::Protocol::Http2, stats)); #else // If UHV is disabled, providing config should result in rejection - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } @@ -204,13 +220,20 @@ TEST_F(ConfigTest, HeaderValidatorConfigWithRuntimeDisabled) { Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); TestUtility::loadFromYamlAndValidate(yaml_string, options_); #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; // Without envoy.reloadable_features.enable_universal_header_validator set UHV is always disabled - EXPECT_EQ(nullptr, config.header_validator_factory_); + EXPECT_EQ(nullptr, config->header_validator_factory_); #else // If UHV is disabled, providing config should result in rejection - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } @@ -225,14 +248,21 @@ TEST_F(ConfigTest, DefaultHeaderValidatorConfigWithRuntimeEnabled) { Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_NE(nullptr, config.header_validator_factory_->createClientHeaderValidator( + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_NE(nullptr, config->header_validator_factory_->createClientHeaderValidator( ::Envoy::Http::Protocol::Http2, stats)); EXPECT_FALSE(proto_config.http1_protocol_options().allow_chunked_length()); #else // If UHV is disabled but envoy.reloadable_features.enable_universal_header_validator is set, the // config is rejected - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } @@ -242,10 +272,11 @@ TEST_F(ConfigTest, DefaultHeaderValidatorConfigWithoutOverride) { DefaultHeaderValidatorFactoryConfigOverride factory(proto_config); Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; - ProtocolOptionsConfigImpl config(options_, server_context_); + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); // By default envoy.reloadable_features.enable_universal_header_validator is false preventing UHV // use - EXPECT_EQ(nullptr, config.header_validator_factory_); + EXPECT_EQ(nullptr, config->header_validator_factory_); } TEST_F(ConfigTest, TranslateDownstreamLegacyConfigToDefaultHeaderValidatorConfig) { @@ -266,14 +297,21 @@ TEST_F(ConfigTest, TranslateDownstreamLegacyConfigToDefaultHeaderValidatorConfig Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_NE(nullptr, config.header_validator_factory_->createClientHeaderValidator( + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_NE(nullptr, config->header_validator_factory_->createClientHeaderValidator( ::Envoy::Http::Protocol::Http2, stats)); EXPECT_TRUE(proto_config.http1_protocol_options().allow_chunked_length()); #else // If UHV is disabled but envoy.reloadable_features.enable_universal_header_validator is set, the // config is rejected - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } @@ -295,14 +333,21 @@ TEST_F(ConfigTest, TranslateAutoLegacyConfigToDefaultHeaderValidatorConfig) { Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_NE(nullptr, config.header_validator_factory_->createClientHeaderValidator( + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_NE(nullptr, config->header_validator_factory_->createClientHeaderValidator( ::Envoy::Http::Protocol::Http2, stats)); EXPECT_TRUE(proto_config.http1_protocol_options().allow_chunked_length()); #else // If UHV is disabled but envoy.reloadable_features.enable_universal_header_validator is set, the // config is rejected - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } @@ -324,14 +369,21 @@ TEST_F(ConfigTest, TranslateExplicitLegacyConfigToDefaultHeaderValidatorConfig) Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_NE(nullptr, config.header_validator_factory_->createClientHeaderValidator( + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_NE(nullptr, config->header_validator_factory_->createClientHeaderValidator( ::Envoy::Http::Protocol::Http2, stats)); EXPECT_TRUE(proto_config.http1_protocol_options().allow_chunked_length()); #else // If UHV is disabled but envoy.reloadable_features.enable_universal_header_validator is set, the // config is rejected - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } @@ -353,14 +405,21 @@ TEST_F(ConfigTest, TranslateExplicitH2LegacyConfigToDefaultHeaderValidatorConfig Registry::InjectFactory<::Envoy::Http::HeaderValidatorFactoryConfig> registration(factory); NiceMock<::Envoy::Http::MockHeaderValidatorStats> stats; #ifdef ENVOY_ENABLE_UHV - ProtocolOptionsConfigImpl config(options_, server_context_); - EXPECT_NE(nullptr, config.header_validator_factory_->createClientHeaderValidator( + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_).value(); + EXPECT_NE(nullptr, config->header_validator_factory_->createClientHeaderValidator( ::Envoy::Http::Protocol::Http2, stats)); EXPECT_FALSE(proto_config.http1_protocol_options().allow_chunked_length()); #else // If UHV is disabled but envoy.reloadable_features.enable_universal_header_validator is set, the // config is rejected - EXPECT_THROW({ ProtocolOptionsConfigImpl config(options_, server_context_); }, EnvoyException); + EXPECT_THROW( + { + std::shared_ptr config = + ProtocolOptionsConfigImpl::createProtocolOptionsConfig(options_, server_context_) + .value(); + }, + EnvoyException); #endif } diff --git a/test/integration/BUILD b/test/integration/BUILD index 51937089c341d..4649014f41aff 100644 --- a/test/integration/BUILD +++ b/test/integration/BUILD @@ -1,4 +1,3 @@ -load("@base_pip3//:requirements.bzl", "requirement") load("@rules_python//python:defs.bzl", "py_binary") load( "//bazel:envoy_build_system.bzl", @@ -8,7 +7,6 @@ load( "envoy_cc_test_library", "envoy_package", "envoy_proto_library", - "envoy_py_test", "envoy_select_admin_functionality", "envoy_select_enable_http3", "envoy_select_enable_yaml", @@ -374,41 +372,6 @@ envoy_cc_test_binary( ], ) -envoy_py_test( - name = "hotrestart_handoff_test", - size = "medium", - srcs = select({ - "//bazel:disable_hot_restart_or_admin": ["null_test.py"], - "//conditions:default": ["hotrestart_handoff_test.py"], - }), - args = [ - "--envoy-binary=$(location :hotrestart_main)", - "--h3-request=$(location //tools/h3_request)", - "--ca-certs=$(location //test/config/integration/certs:cacert.pem)", - "--ca-key=$(location //test/config/integration/certs:cakey.pem)", - ], - data = [ - ":hotrestart_main", - "//test/config/integration/certs:cacert.pem", - "//test/config/integration/certs:cakey.pem", - "//tools/h3_request", - ], - main = select({ - "//bazel:disable_hot_restart_or_admin": "null_test.py", - "//conditions:default": "hotrestart_handoff_test.py", - }), - # Hot restart does not apply on Windows. - # py_test doesn't do coverage. - tags = [ - "nocoverage", - "skip_on_windows", - ], - deps = [ - requirement("aiohttp"), - requirement("cryptography"), - ], -) - envoy_sh_test( name = "hotrestart_test", size = "large", diff --git a/test/integration/base_integration_test.cc b/test/integration/base_integration_test.cc index 9813d24d2923a..bfae7ee7bbe9e 100644 --- a/test/integration/base_integration_test.cc +++ b/test/integration/base_integration_test.cc @@ -537,7 +537,7 @@ std::string BaseIntegrationTest::waitForAccessLog(const std::string& filename, u // Wait a max of 1s for logs to flush to disk. std::string contents; - const int num_iterations = TSAN_TIMEOUT_FACTOR * 1000; + const int num_iterations = TIMEOUT_FACTOR * 1000; for (int i = 0; i < num_iterations; ++i) { contents = TestEnvironment::readFileToStringForTest(filename); std::vector entries = absl::StrSplit(contents, '\n', absl::SkipEmpty()); diff --git a/test/integration/base_integration_test.h b/test/integration/base_integration_test.h index 7b16822a4c7fe..c6cf68fdcb117 100644 --- a/test/integration/base_integration_test.h +++ b/test/integration/base_integration_test.h @@ -570,7 +570,7 @@ class BaseIntegrationTest : protected Logger::Loggable { bool use_real_stats_{}; // If true, skip checking stats for missing tag-extraction rules. - bool skip_tag_extraction_rule_check_{}; + bool skip_tag_extraction_rule_check_{true}; // By default, node metadata (node name, cluster name, locality) for the test server gets set to // hard-coded values in the OptionsImpl ("node_name", "cluster_name", etc.). Set to true if your diff --git a/test/integration/clusters/custom_static_cluster.cc b/test/integration/clusters/custom_static_cluster.cc index 709ea07c9b7a1..8472157247991 100644 --- a/test/integration/clusters/custom_static_cluster.cc +++ b/test/integration/clusters/custom_static_cluster.cc @@ -16,7 +16,7 @@ void CustomStaticCluster::startPreInit() { priority_set_.updateHosts( priority_, Upstream::HostSetImpl::partitionHosts(hosts_ptr, Upstream::HostsPerLocalityImpl::empty()), {}, - hosts, {}, absl::nullopt); + hosts, {}, 123, absl::nullopt); onPreInitComplete(); } diff --git a/test/integration/eds_integration_test.cc b/test/integration/eds_integration_test.cc index 010969397424a..e95465c2565cb 100644 --- a/test/integration/eds_integration_test.cc +++ b/test/integration/eds_integration_test.cc @@ -477,137 +477,6 @@ TEST_P(EdsIntegrationTest, LocalityUpdateActiveHealthStatusReuse) { EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_healthy")->value()); } -// Validates that updating a locality of an actively checked endpoint, does -// not reuse the previously determined health status. -// The test should be removed once -// envoy.reloadable_features.keep_endpoint_active_hc_status_on_locality_update -// is deprecated. -TEST_P(EdsIntegrationTest, LocalityUpdateActiveHealthStatusNoReuse) { - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues( - {{"envoy.reloadable_features.keep_endpoint_active_hc_status_on_locality_update", "false"}}); - // setup with active-HC. - initializeTest(true, [](envoy::config::cluster::v3::Cluster& cluster) { - // Disable the healthy panic threshold, preventing using a non-healthy host. - cluster.mutable_common_lb_config()->mutable_healthy_panic_threshold(); - cluster.mutable_health_checks(0)->mutable_interval()->CopyFrom( - Protobuf::util::TimeUtil::MillisecondsToDuration(10000)); - cluster.mutable_health_checks(0)->mutable_no_traffic_interval()->CopyFrom( - Protobuf::util::TimeUtil::MillisecondsToDuration(10000)); - cluster.set_ignore_health_on_host_removal(true); - }); - envoy::config::endpoint::v3::ClusterLoadAssignment cluster_load_assignment; - - // Create an EDS message with a duplicated endpoint in 2 localities. - TestUtility::loadFromYaml(R"EOF( - cluster_name: "cluster_0" - endpoints: - - lb_endpoints: - - endpoint: - priority: 0 - locality: - sub_zone: xx -)EOF", - cluster_load_assignment); - auto* endpoint_A = cluster_load_assignment.mutable_endpoints(0)->mutable_lb_endpoints(0); - setUpstreamAddress(0, *endpoint_A); - - // Send the first EDS response. - sendPlainEds(cluster_load_assignment); - - // Wait for the first HC to arrive to the upstream. - waitForNextUpstreamRequest(); - upstream_request_->encodeHeaders(Http::TestResponseHeaderMapImpl{{":status", "200"}}, true); - test_server_->waitForCounterEq("cluster.cluster_0.health_check.attempt", 1); - test_server_->waitForCounterGe("cluster.cluster_0.health_check.success", 1); - cleanupUpstreamAndDownstream(); - - // After the first hc there should be no upstream healthy host, and any - // downstream request will fail, until the update-merge-window ends. - EXPECT_EQ(0, test_server_->counter("cluster.cluster_0.upstream_cx_none_healthy")->value()); - BufferingStreamDecoderPtr response = IntegrationUtil::makeSingleRequest( - lookupPort("http"), "GET", "/cluster_0", "", downstream_protocol_, version_, "foo.com"); - ASSERT_TRUE(response->complete()); - EXPECT_EQ("503", response->headers().getStatusValue()); - EXPECT_EQ(1, test_server_->counter("cluster.cluster_0.upstream_cx_none_healthy")->value()); - cleanupUpstreamAndDownstream(); - response.reset(); - - // Wait for scheduled updates (update-merge-window). - test_server_->waitForCounterEq("cluster_manager.cluster_updated_via_merge", 1); - - // Now the upstream should be healthy. - // There should only be 1 endpoint, and it should be healthy (according to EDS). - EXPECT_EQ(0, test_server_->counter("cluster.cluster_0.health_check.failure")->value()); - EXPECT_EQ(1, test_server_->counter("cluster.cluster_0.membership_change")->value()); - EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_total")->value()); - EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_healthy")->value()); - - // Now a downstream request can be passed to the upstream. - registerTestServerPorts({"http"}); - testRouterHeaderOnlyRequestAndResponse(); - cleanupUpstreamAndDownstream(); - - // 2nd change: Connection is open, send an EDS response changing the order of the - // priorities in the message, but doesn't impact localities. This should have no - // impact on the host's health status, and cluster availability. - cluster_load_assignment.mutable_endpoints(0)->set_priority(1); - sendPlainEds(cluster_load_assignment, true); - - // No locality update, so the previous pool can be used, and a request will be - // served. - testRouterHeaderOnlyRequestAndResponse(); - cleanupUpstreamAndDownstream(); - - // There should be 3 membership changes (+2 compared to the previous, as the - // memberships of priority 0 and 1 have changed). - test_server_->waitForCounterEq("cluster.cluster_0.membership_change", 3); - // There should still be be 1 endpoint, and it should stay healthy. - EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_total")->value()); - EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_healthy")->value()); - - // 3rd change: Connection is open, send an EDS response changing the localities in the - // message. This will cause recreation of the LB, resending the HC to the "new" - // endpoint. This will impact cluster availability. - cluster_load_assignment.mutable_endpoints(0)->mutable_locality()->set_sub_zone("xx2"); - sendPlainEds(cluster_load_assignment, true); - - // Wait for first HC for the tcp proxy after EDS update with localities. - waitForNextUpstreamRequest(); - upstream_request_->encodeHeaders(Http::TestResponseHeaderMapImpl{{":status", "200"}}, true); - cleanupUpstreamAndDownstream(); - - // After the first hc there should be no upstream healthy host, and any - // downstream request will fail, until the update-merge-window ends. - // - // when reusing health-status, Envoy will be able to connect to the upstream - // even before receiving the HC response, because the endpoint was already - // set to healthy. - { - EXPECT_EQ(1, test_server_->counter("cluster.cluster_0.upstream_cx_none_healthy")->value()); - response = IntegrationUtil::makeSingleRequest(lookupPort("http"), "GET", "/cluster_0", "", - downstream_protocol_, version_, "foo.com"); - ASSERT_TRUE(response->complete()); - EXPECT_EQ("503", response->headers().getStatusValue()); - cleanupUpstreamAndDownstream(); - response.reset(); - EXPECT_EQ(2, test_server_->counter("cluster.cluster_0.upstream_cx_none_healthy")->value()); - - // Wait for scheduled updates (update-merge-window). - test_server_->waitForCounterEq("cluster_manager.cluster_updated_via_merge", 3); - } - - // Now the upstream should be healthy, and a request will be served. - testRouterHeaderOnlyRequestAndResponse(); - cleanupUpstreamAndDownstream(); - // There should be 3 membership changes (+1 compared to the previous, as the - // membership of the first locality has changed). - test_server_->waitForCounterEq("cluster.cluster_0.membership_change", 4); - // There should still be be 1 endpoint, and it should stay healthy. - EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_total")->value()); - EXPECT_EQ(1, test_server_->gauge("cluster.cluster_0.membership_healthy")->value()); -} - // Verifies that cluster warming proceeds even if a host is deleted before health checks complete. // This is a regression test for https://github.com/envoyproxy/envoy/issues/17836. TEST_P(EdsIntegrationTest, FinishWarmingIgnoreHealthCheck) { diff --git a/test/integration/fake_upstream.cc b/test/integration/fake_upstream.cc index d7addab05920e..67822c700302f 100644 --- a/test/integration/fake_upstream.cc +++ b/test/integration/fake_upstream.cc @@ -248,7 +248,7 @@ bool waitForWithDispatcherRun(Event::TestTimeSystem& time_system, absl::Mutex& l Event::TestTimeSystem::RealTimeBound bound(timeout); while (bound.withinBound()) { // Wake up periodically to run the client dispatcher. - if (time_system.waitFor(lock, absl::Condition(&condition), 5ms * TSAN_TIMEOUT_FACTOR)) { + if (time_system.waitFor(lock, absl::Condition(&condition), 5ms * TIMEOUT_FACTOR)) { return true; } diff --git a/test/integration/fake_upstream.h b/test/integration/fake_upstream.h index e721c999ec6d4..399418dbfedeb 100644 --- a/test/integration/fake_upstream.h +++ b/test/integration/fake_upstream.h @@ -639,7 +639,7 @@ struct FakeUpstreamConfig { }; FakeUpstreamConfig(Event::TestTimeSystem& time_system) : time_system_(time_system) { - http2_options_ = ::Envoy::Http2::Utility::initializeAndValidateOptions(http2_options_); + http2_options_ = ::Envoy::Http2::Utility::initializeAndValidateOptions(http2_options_).value(); // Legacy options which are always set. http2_options_.set_allow_connect(true); http2_options_.set_allow_metadata(true); diff --git a/test/integration/filters/BUILD b/test/integration/filters/BUILD index 867bca9cef3eb..a81d62141edd4 100644 --- a/test/integration/filters/BUILD +++ b/test/integration/filters/BUILD @@ -913,6 +913,7 @@ envoy_cc_test_library( "//envoy/http:filter_interface", "//envoy/registry", "//envoy/server:filter_config_interface", + "//source/common/protobuf", "//source/extensions/filters/http/common:pass_through_filter_lib", "//test/extensions/filters/http/common:empty_http_filter_config_lib", ], diff --git a/test/integration/filters/stream_info_to_headers_filter.cc b/test/integration/filters/stream_info_to_headers_filter.cc index 41077688ff15e..489e4d5614409 100644 --- a/test/integration/filters/stream_info_to_headers_filter.cc +++ b/test/integration/filters/stream_info_to_headers_filter.cc @@ -1,6 +1,7 @@ #include "envoy/registry/registry.h" #include "envoy/server/filter_config.h" +#include "source/common/protobuf/protobuf.h" #include "source/extensions/filters/http/common/pass_through_filter.h" #include "test/extensions/filters/http/common/empty_http_filter_config.h" @@ -15,6 +16,38 @@ std::string toUsec(MonotonicTime time) { return absl::StrCat(time.time_since_epo } // namespace +void addValueHeaders(Http::ResponseHeaderMap& headers, std::string key_prefix, + const ProtobufWkt::Value& val) { + switch (val.kind_case()) { + case ProtobufWkt::Value::kNullValue: + headers.addCopy(Http::LowerCaseString(key_prefix), "null"); + break; + case ProtobufWkt::Value::kNumberValue: + headers.addCopy(Http::LowerCaseString(key_prefix), std::to_string(val.number_value())); + break; + case ProtobufWkt::Value::kStringValue: + headers.addCopy(Http::LowerCaseString(key_prefix), val.string_value()); + break; + case ProtobufWkt::Value::kBoolValue: + headers.addCopy(Http::LowerCaseString(key_prefix), val.bool_value() ? "true" : "false"); + break; + case ProtobufWkt::Value::kListValue: { + const auto& vals = val.list_value().values(); + for (auto i = 0; i < vals.size(); ++i) { + addValueHeaders(headers, key_prefix + "." + std::to_string(i), vals[i]); + } + break; + } + case ProtobufWkt::Value::kStructValue: + for (const auto& field : val.struct_value().fields()) { + addValueHeaders(headers, key_prefix + "." + field.first, field.second); + } + break; + default: + break; + } +} + // A filter that sticks stream info into headers for integration testing. class StreamInfoToHeadersFilter : public Http::PassThroughFilter { public: @@ -97,6 +130,17 @@ class StreamInfoToHeadersFilter : public Http::PassThroughFilter { upstream_timing.connectionPoolCallbackLatency().value().count()); } } + + if (decoder_callbacks_->streamInfo().dynamicMetadata().filter_metadata_size() > 0) { + const auto& md = decoder_callbacks_->streamInfo().dynamicMetadata().filter_metadata(); + for (const auto& md_entry : md) { + std::string key_prefix = md_entry.first; + for (const auto& field : md_entry.second.fields()) { + addValueHeaders(headers, key_prefix + "." + field.first, field.second); + } + } + } + return Http::FilterHeadersStatus::Continue; } }; diff --git a/test/integration/http2_flood_integration_test.cc b/test/integration/http2_flood_integration_test.cc index 09839ea0ddb68..9e069eb9d32e3 100644 --- a/test/integration/http2_flood_integration_test.cc +++ b/test/integration/http2_flood_integration_test.cc @@ -968,8 +968,8 @@ TEST_P(Http2FloodMitigationTest, KeepAliveTimerTriggersFloodProtection) { [](envoy::extensions::filters::network::http_connection_manager::v3::HttpConnectionManager& hcm) { auto* keep_alive = hcm.mutable_http2_protocol_options()->mutable_connection_keepalive(); - keep_alive->mutable_interval()->set_seconds(1 * TSAN_TIMEOUT_FACTOR); - keep_alive->mutable_timeout()->set_seconds(2 * TSAN_TIMEOUT_FACTOR); + keep_alive->mutable_interval()->set_seconds(1 * TIMEOUT_FACTOR); + keep_alive->mutable_timeout()->set_seconds(2 * TIMEOUT_FACTOR); }); prefillOutboundDownstreamQueue(AllFrameFloodLimit - 1); diff --git a/test/integration/http_integration.cc b/test/integration/http_integration.cc index 7e5d8b735af7b..32cd019ca2b57 100644 --- a/test/integration/http_integration.cc +++ b/test/integration/http_integration.cc @@ -272,7 +272,8 @@ IntegrationCodecClientPtr HttpIntegrationTest::makeRawHttpConnection( cluster->max_response_headers_count_ = 200; if (!http2_options.has_value()) { http2_options = Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions()); + envoy::config::core::v3::Http2ProtocolOptions()) + .value(); http2_options.value().set_allow_connect(true); http2_options.value().set_allow_metadata(true); #ifdef ENVOY_ENABLE_QUIC @@ -388,8 +389,7 @@ void HttpIntegrationTest::initialize() { quic_connection_persistent_info->quic_config_.SetInitialStreamFlowControlWindowToSend( Http3::Utility::OptionsLimits::DEFAULT_INITIAL_STREAM_WINDOW_SIZE); // Adjust timeouts. - quic::QuicTime::Delta connect_timeout = - quic::QuicTime::Delta::FromSeconds(5 * TSAN_TIMEOUT_FACTOR); + quic::QuicTime::Delta connect_timeout = quic::QuicTime::Delta::FromSeconds(5 * TIMEOUT_FACTOR); quic_connection_persistent_info->quic_config_.set_max_time_before_crypto_handshake( connect_timeout); quic_connection_persistent_info->quic_config_.set_max_idle_time_before_crypto_handshake( diff --git a/test/integration/http_integration.h b/test/integration/http_integration.h index d8a6959f8dad6..866dc05757efc 100644 --- a/test/integration/http_integration.h +++ b/test/integration/http_integration.h @@ -305,9 +305,10 @@ class HttpIntegrationTest : public BaseIntegrationTest { void testAdminDrain(Http::CodecClient::Type admin_request_type); // Test sending and receiving large request and response bodies with autonomous upstream. - void testGiantRequestAndResponse( - uint64_t request_size, uint64_t response_size, bool set_content_length_header, - std::chrono::milliseconds timeout = 2 * TestUtility::DefaultTimeout * TSAN_TIMEOUT_FACTOR); + void testGiantRequestAndResponse(uint64_t request_size, uint64_t response_size, + bool set_content_length_header, + std::chrono::milliseconds timeout = 2 * + TestUtility::DefaultTimeout); struct BytesCountExpectation { BytesCountExpectation(int wire_bytes_sent, int wire_bytes_received, int header_bytes_sent, diff --git a/test/integration/idle_timeout_integration_test.cc b/test/integration/idle_timeout_integration_test.cc index 3bd8c03712820..68acfa4771002 100644 --- a/test/integration/idle_timeout_integration_test.cc +++ b/test/integration/idle_timeout_integration_test.cc @@ -116,9 +116,7 @@ class IdleTimeoutIntegrationTest : public HttpProtocolIntegrationTest { } } - // TODO(htuch): This might require scaling for TSAN/ASAN/Valgrind/etc. Bump if - // this is the cause of flakes. - static constexpr uint64_t IdleTimeoutMs = 300 * TSAN_TIMEOUT_FACTOR; + static constexpr uint64_t IdleTimeoutMs = 300 * TIMEOUT_FACTOR; static constexpr uint64_t RequestTimeoutMs = 200; bool enable_global_idle_timeout_{false}; bool enable_per_stream_idle_timeout_{false}; diff --git a/test/integration/integration_test.cc b/test/integration/integration_test.cc index 702c6bf6d9ed8..c25269f59eda8 100644 --- a/test/integration/integration_test.cc +++ b/test/integration/integration_test.cc @@ -1558,23 +1558,6 @@ TEST_P(IntegrationTest, AbsolutePathWithMixedScheme) { EXPECT_THAT(response, StartsWith("HTTP/1.1 301")); } -TEST_P(IntegrationTest, AbsolutePathWithMixedSchemeLegacy) { - config_helper_.addRuntimeOverride( - "envoy.reloadable_features.allow_absolute_url_with_mixed_scheme", "false"); - config_helper_.addRuntimeOverride("envoy.reloadable_features.handle_uppercase_scheme", "false"); - - // Mixed scheme requests will be rejected - auto host = config_helper_.createVirtualHost("www.namewithport.com:1234", "/"); - host.set_require_tls(envoy::config::route::v3::VirtualHost::ALL); - config_helper_.addVirtualHost(host); - initialize(); - std::string response; - sendRawHttpAndWaitForResponse( - lookupPort("http"), "GET hTtp://www.namewithport.com:1234 HTTP/1.1\r\nHost: host\r\n\r\n", - &response, true); - EXPECT_THAT(response, StartsWith("HTTP/1.1 400")); -} - TEST_P(IntegrationTest, AbsolutePathWithoutPort) { // Add a restrictive default match, to avoid the request hitting the * / catchall. config_helper_.setDefaultHostAndRoute("foo.com", "/found"); diff --git a/test/integration/multiplexed_integration_test.cc b/test/integration/multiplexed_integration_test.cc index 71573f90a5e77..9d2e36ac426d6 100644 --- a/test/integration/multiplexed_integration_test.cc +++ b/test/integration/multiplexed_integration_test.cc @@ -219,7 +219,8 @@ TEST_P(MultiplexedIntegrationTest, CodecStreamIdleTimeout) { downstream_protocol_ == Http::CodecType::HTTP3 ? 32 * 1024 : 65535; envoy::config::core::v3::Http2ProtocolOptions http2_options = ::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions()); + envoy::config::core::v3::Http2ProtocolOptions()) + .value(); http2_options.mutable_initial_stream_window_size()->set_value(stream_flow_control_window); #ifdef ENVOY_ENABLE_QUIC if (downstream_protocol_ == Http::CodecType::HTTP3) { diff --git a/test/integration/overload_integration_test.cc b/test/integration/overload_integration_test.cc index 1232968546dcc..d9060673cd3fd 100644 --- a/test/integration/overload_integration_test.cc +++ b/test/integration/overload_integration_test.cc @@ -585,16 +585,12 @@ TEST_P(LoadShedPointIntegrationTest, Http1ServerDispatchAbortShedsLoadWhenNewReq // Test using 100-continue to start the response before doing triggering Overload. // Even though Envoy has encoded the 1xx headers, 1xx headers are not the actual response // so Envoy should still send the local reply when shedding load. -TEST_P( - LoadShedPointIntegrationTest, - Http1ServerDispatchAbortShedsLoadWithLocalReplyWhen1xxResponseStartedWithFlagAllowCodecErrorResponseAfter1xxHeadersEnabled) { +TEST_P(LoadShedPointIntegrationTest, + Http1ServerDispatchAbortShedsLoadWithLocalReplyWhen1xxResponseStarted) { // Test only applies to HTTP1. if (downstreamProtocol() != Http::CodecClient::Type::HTTP1) { return; } - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues( - {{"envoy.reloadable_features.http1_allow_codec_error_response_after_1xx_headers", "true"}}); initializeOverloadManager( TestUtility::parseYaml(R"EOF( @@ -635,61 +631,6 @@ TEST_P( test_server_->waitForCounterEq("http.config_test.downstream_rq_overload_close", 1); } -// TODO(kbaichoo): remove this test when the runtime flag is removed. -TEST_P( - LoadShedPointIntegrationTest, - Http1ServerDispatchAbortShedsLoadWithLocalReplyWhen1xxResponseStartedWithFlagAllowCodecErrorResponseAfter1xxHeadersDisabled) { - // Test only applies to HTTP1. - if (downstreamProtocol() != Http::CodecClient::Type::HTTP1) { - return; - } - TestScopedRuntime scoped_runtime; - scoped_runtime.mergeValues( - {{"envoy.reloadable_features.http1_allow_codec_error_response_after_1xx_headers", "false"}}); - - initializeOverloadManager( - TestUtility::parseYaml(R"EOF( - name: "envoy.load_shed_points.http1_server_abort_dispatch" - triggers: - - name: "envoy.resource_monitors.testonly.fake_resource_monitor" - threshold: - value: 0.90 - )EOF")); - test_server_->waitForCounterEq("http.config_test.downstream_rq_overload_close", 0); - - // Start the 100-continue request - codec_client_ = makeHttpConnection(makeClientConnection((lookupPort("http")))); - auto encoder_decoder = - codec_client_->startRequest(Http::TestRequestHeaderMapImpl{{":method", "POST"}, - {":path", "/dynamo/url"}, - {":scheme", "http"}, - {":authority", "sni.lyft.com"}, - {"expect", "100-contINUE"}}); - - // Wait for 100-continue - request_encoder_ = &encoder_decoder.first; - auto response = std::move(encoder_decoder.second); - ASSERT_TRUE(fake_upstreams_[0]->waitForHttpConnection(*dispatcher_, fake_upstream_connection_)); - // The continue headers should arrive immediately. - response->waitFor1xxHeaders(); - ASSERT_TRUE(fake_upstream_connection_->waitForNewStream(*dispatcher_, upstream_request_)); - - // Put envoy in overloaded state and check that it rejects the continuing - // dispatch. - updateResource(0.95); - test_server_->waitForGaugeEq( - "overload.envoy.load_shed_points.http1_server_abort_dispatch.scale_percent", 100); - codec_client_->sendData(*request_encoder_, 10, true); - - // Since the runtime flag `http1_allow_codec_error_response_after_1xx_headers` - // is disabled the downstream client ends up just getting a closed connection. - // Envoy's downstream codec does not provide a local reply as we've started - // the response. - ASSERT_TRUE(codec_client_->waitForDisconnect()); - EXPECT_FALSE(response->complete()); - test_server_->waitForCounterEq("http.config_test.downstream_rq_overload_close", 1); -} - TEST_P(LoadShedPointIntegrationTest, Http1ServerDispatchShouldNotAbortEncodingUpstreamResponse) { // Test only applies to HTTP1. if (downstreamProtocol() != Http::CodecClient::Type::HTTP1) { diff --git a/test/integration/protocol_integration_test.cc b/test/integration/protocol_integration_test.cc index 271c020b15acf..03bc51ff801db 100644 --- a/test/integration/protocol_integration_test.cc +++ b/test/integration/protocol_integration_test.cc @@ -3621,7 +3621,8 @@ TEST_P( constexpr uint32_t window_size = 65535; envoy::config::core::v3::Http2ProtocolOptions http2_options = ::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions()); + envoy::config::core::v3::Http2ProtocolOptions()) + .value(); http2_options.mutable_initial_stream_window_size()->set_value(window_size); http2_options.mutable_initial_connection_window_size()->set_value(window_size); @@ -3704,7 +3705,8 @@ TEST_P(ProtocolIntegrationTest, ResetLargeResponseUponReceivingHeaders) { envoy::config::core::v3::Http2ProtocolOptions http2_options = ::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions()); + envoy::config::core::v3::Http2ProtocolOptions()) + .value(); http2_options.mutable_initial_stream_window_size()->set_value(65535); http2_options.mutable_initial_connection_window_size()->set_value(65535); codec_client_ = makeRawHttpConnection(makeClientConnection(lookupPort("http")), http2_options); diff --git a/test/integration/python/BUILD b/test/integration/python/BUILD new file mode 100644 index 0000000000000..8d824bbdad997 --- /dev/null +++ b/test/integration/python/BUILD @@ -0,0 +1,41 @@ +load("@base_pip3//:requirements.bzl", "requirement") +load("//bazel:envoy_build_system.bzl", "envoy_package", "envoy_py_test") + +licenses(["notice"]) # Apache 2 + +envoy_package() + +envoy_py_test( + name = "hotrestart_handoff_test", + size = "medium", + srcs = select({ + "//bazel:disable_hot_restart_or_admin": ["null_test.py"], + "//conditions:default": ["hotrestart_handoff_test.py"], + }), + args = [ + "--envoy-binary=$(location //test/integration:hotrestart_main)", + "--h3-request=$(location //tools/h3_request)", + "--ca-certs=$(location //test/config/integration/certs:cacert.pem)", + "--ca-key=$(location //test/config/integration/certs:cakey.pem)", + ], + data = [ + "//test/config/integration/certs:cacert.pem", + "//test/config/integration/certs:cakey.pem", + "//test/integration:hotrestart_main", + "//tools/h3_request", + ], + main = select({ + "//bazel:disable_hot_restart_or_admin": "null_test.py", + "//conditions:default": "hotrestart_handoff_test.py", + }), + # Hot restart does not apply on Windows. + # py_test doesn't do coverage. + tags = [ + "nocoverage", + "skip_on_windows", + ], + deps = [ + requirement("aiohttp"), + requirement("cryptography"), + ], +) diff --git a/test/integration/hotrestart_handoff_test.py b/test/integration/python/hotrestart_handoff_test.py similarity index 100% rename from test/integration/hotrestart_handoff_test.py rename to test/integration/python/hotrestart_handoff_test.py diff --git a/test/integration/null_test.py b/test/integration/python/null_test.py similarity index 100% rename from test/integration/null_test.py rename to test/integration/python/null_test.py diff --git a/test/integration/quic_http_integration_test.cc b/test/integration/quic_http_integration_test.cc index 580dc2d73727f..2ce46d476f087 100644 --- a/test/integration/quic_http_integration_test.cc +++ b/test/integration/quic_http_integration_test.cc @@ -1496,7 +1496,7 @@ TEST_P(QuicHttpIntegrationTest, DeferredLoggingWithRetransmission) { socket_swap.write_matcher_->setDestinationPort(lookupPort("http")); socket_swap.write_matcher_->setWriteOverride(std::move(ebadf)); upstream_request_->encodeHeaders(Http::TestResponseHeaderMapImpl{{":status", "200"}}, true); - timeSystem().advanceTimeWait(std::chrono::seconds(TSAN_TIMEOUT_FACTOR)); + timeSystem().advanceTimeWait(std::chrono::seconds(TIMEOUT_FACTOR)); } ASSERT_TRUE(response->waitForEndStream()); @@ -1990,5 +1990,71 @@ TEST_P(QuicHttpIntegrationTest, PreferredAddressDroppedByIncompatibleListenerFil EXPECT_THAT(log, testing::HasSubstr("200 \"foo\"")); } +// Validate that the correct transport parameter is sent when `send_disable_active_migration` is +// enabled. +TEST_P(QuicHttpIntegrationTest, SendDisableActiveMigration) { + autonomous_upstream_ = true; + config_helper_.addConfigModifier([=](envoy::config::bootstrap::v3::Bootstrap& bootstrap) -> void { + bootstrap.mutable_static_resources() + ->mutable_listeners(0) + ->mutable_udp_listener_config() + ->mutable_quic_options() + ->mutable_send_disable_active_migration() + ->set_value(true); + }); + + initialize(); + codec_client_ = makeHttpConnection(makeClientConnection(lookupPort("http"))); + EnvoyQuicClientSession* quic_session = + static_cast(codec_client_->connection()); + EXPECT_EQ(Network::Test::getLoopbackAddressString(version_), + quic_connection_->peer_address().host().ToString()); + ASSERT_TRUE(quic_connection_->waitForHandshakeDone()); + + // Validate the setting was transmitted. + EXPECT_TRUE(quic_session->config()->DisableConnectionMigration()); + + Http::TestRequestHeaderMapImpl request_headers{ + {":method", "GET"}, + {":path", "/test/long/url"}, + {":authority", "sni.lyft.com"}, + {":scheme", "http"}, + {AutonomousStream::RESPONSE_SIZE_BYTES, std::to_string(1024 * 1024)}}; + IntegrationStreamDecoderPtr response = + codec_client_->makeHeaderOnlyRequest(default_request_headers_); + EXPECT_TRUE(response->waitForEndStream()); + ASSERT_TRUE(response->complete()); +} + +// Validate that the transport parameter is not sent when `send_disable_active_migration` is +// unset. +TEST_P(QuicHttpIntegrationTest, UnsetSendDisableActiveMigration) { + autonomous_upstream_ = true; + + // No config modifier to enable the setting. + + initialize(); + codec_client_ = makeHttpConnection(makeClientConnection(lookupPort("http"))); + EnvoyQuicClientSession* quic_session = + static_cast(codec_client_->connection()); + EXPECT_EQ(Network::Test::getLoopbackAddressString(version_), + quic_connection_->peer_address().host().ToString()); + ASSERT_TRUE(quic_connection_->waitForHandshakeDone()); + + // Validate the setting was not transmitted. + EXPECT_FALSE(quic_session->config()->DisableConnectionMigration()); + + Http::TestRequestHeaderMapImpl request_headers{ + {":method", "GET"}, + {":path", "/test/long/url"}, + {":authority", "sni.lyft.com"}, + {":scheme", "http"}, + {AutonomousStream::RESPONSE_SIZE_BYTES, std::to_string(1024 * 1024)}}; + IntegrationStreamDecoderPtr response = + codec_client_->makeHeaderOnlyRequest(default_request_headers_); + EXPECT_TRUE(response->waitForEndStream()); + ASSERT_TRUE(response->complete()); +} + } // namespace Quic } // namespace Envoy diff --git a/test/integration/tcp_async_client_integration_test.cc b/test/integration/tcp_async_client_integration_test.cc index 8550b9b601f08..cd31af091dd92 100644 --- a/test/integration/tcp_async_client_integration_test.cc +++ b/test/integration/tcp_async_client_integration_test.cc @@ -111,6 +111,7 @@ TEST_P(TcpAsyncClientIntegrationTest, MultipleResponseFrames) { tcp_client->close(); } +#if ENVOY_PLATFORM_ENABLE_SEND_RST // Test if RST close can be detected from downstream and upstream is closed by RST. TEST_P(TcpAsyncClientIntegrationTest, TestClientCloseRST) { enableHalfClose(true); @@ -175,7 +176,6 @@ TEST_P(TcpAsyncClientIntegrationTest, TestUpstreamCloseRST) { tcp_client->waitForDisconnect(); } -#if !defined(WIN32) // Test the behaviour when the connection is half closed and then the connection is reset by // the client. The behavior is different for windows, since RST support is literally supported for // unix like system, disabled the test for windows. diff --git a/test/integration/tcp_tunneling_integration_test.cc b/test/integration/tcp_tunneling_integration_test.cc index 568dab2ad112e..5e0a5a37d664a 100644 --- a/test/integration/tcp_tunneling_integration_test.cc +++ b/test/integration/tcp_tunneling_integration_test.cc @@ -1196,6 +1196,66 @@ TEST_P(TcpTunnelingIntegrationTest, CopyInvalidResponseHeaders) { EXPECT_THAT(waitForAccessLog(access_log_filename), testing::HasSubstr(header_value)); } +TEST_P(TcpTunnelingIntegrationTest, CopyInvalidResponseHeadersWithRetry) { + const std::string access_log_filename = + TestEnvironment::temporaryPath(TestUtility::uniqueFilename()); + config_helper_.addConfigModifier([&](envoy::config::bootstrap::v3::Bootstrap& bootstrap) -> void { + envoy::extensions::filters::network::tcp_proxy::v3::TcpProxy proxy_config; + proxy_config.set_stat_prefix("tcp_stats"); + proxy_config.set_cluster("cluster_0"); + proxy_config.mutable_tunneling_config()->set_hostname("foo.lyft.com:80"); + proxy_config.mutable_tunneling_config()->set_propagate_response_headers(true); + proxy_config.mutable_max_connect_attempts()->set_value(2); + + envoy::extensions::access_loggers::file::v3::FileAccessLog access_log_config; + access_log_config.mutable_log_format()->mutable_text_format_source()->set_inline_string( + "%FILTER_STATE(envoy.tcp_proxy.propagate_response_headers:TYPED)%\n"); + access_log_config.set_path(access_log_filename); + proxy_config.add_access_log()->mutable_typed_config()->PackFrom(access_log_config); + + auto* listeners = bootstrap.mutable_static_resources()->mutable_listeners(); + for (auto& listener : *listeners) { + if (listener.name() != "tcp_proxy") { + continue; + } + auto* filter_chain = listener.mutable_filter_chains(0); + auto* filter = filter_chain->mutable_filters(0); + filter->mutable_typed_config()->PackFrom(proxy_config); + break; + } + }); + initialize(); + + // Start a connection, and verify the upgrade headers are received upstream. + tcp_client_ = makeTcpConnection(lookupPort("tcp_proxy")); + ASSERT_TRUE(fake_upstreams_[0]->waitForHttpConnection(*dispatcher_, fake_upstream_connection_)); + ASSERT_TRUE(fake_upstream_connection_->waitForNewStream(*dispatcher_, upstream_request_)); + ASSERT_TRUE(upstream_request_->waitForHeadersComplete()); + + // Send invalid response headers. + default_response_headers_.setStatus(enumToInt(Http::Code::ServiceUnavailable)); + const std::string header_value = "secret-value"; + default_response_headers_.addCopy("test-header-name", header_value); + upstream_request_->encodeHeaders(default_response_headers_, true); + + // The TCP proxy will create another request since the first failed and a retry is configured. + if (upstreamProtocol() == Http::CodecType::HTTP1) { + ASSERT_TRUE(fake_upstreams_[0]->waitForHttpConnection(*dispatcher_, fake_upstream_connection_)); + } + + ASSERT_TRUE(fake_upstream_connection_->waitForNewStream(*dispatcher_, upstream_request_)); + ASSERT_TRUE(upstream_request_->waitForHeadersComplete()); + upstream_request_->encodeHeaders(default_response_headers_, true); + + // The connection should be fully closed, but the client has no way of knowing + // that. Ensure the FIN is read and clean up state. + tcp_client_->waitForHalfClose(); + tcp_client_->close(); + + // Verify response header value is in the access log. + EXPECT_THAT(waitForAccessLog(access_log_filename), testing::HasSubstr(header_value)); +} + TEST_P(TcpTunnelingIntegrationTest, CopyResponseTrailers) { if (upstreamProtocol() == Http::CodecType::HTTP1) { return; diff --git a/test/integration/udp_tunneling_integration_test.cc b/test/integration/udp_tunneling_integration_test.cc index 1809d117a52f3..10aa40480d631 100644 --- a/test/integration/udp_tunneling_integration_test.cc +++ b/test/integration/udp_tunneling_integration_test.cc @@ -893,6 +893,63 @@ TEST_P(UdpTunnelingIntegrationTest, PropagateInvalidResponseHeaders) { EXPECT_THAT(waitForAccessLog(access_log_filename), testing::HasSubstr("404")); } +TEST_P(UdpTunnelingIntegrationTest, PropagateInvalidResponseHeadersWithRetry) { + const std::string access_log_filename = + TestEnvironment::temporaryPath(TestUtility::uniqueFilename()); + + const std::string session_access_log_config = fmt::format(R"EOF( + access_log: + - name: envoy.access_loggers.file + typed_config: + '@type': type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog + path: {} + log_format: + text_format_source: + inline_string: "%FILTER_STATE(envoy.udp_proxy.propagate_response_headers:TYPED)%\n" +)EOF", + access_log_filename); + + const TestConfig config{"host.com", + "target.com", + 2, + 30, + false, + "", + BufferOptions{1, 30}, + absl::nullopt, + session_access_log_config, + "", + true, + false}; + setup(config); + + client_->write("hello", *listener_address_); + ASSERT_TRUE(fake_upstreams_[0]->waitForHttpConnection(*dispatcher_, fake_upstream_connection_)); + ASSERT_TRUE(fake_upstream_connection_->waitForNewStream(*dispatcher_, upstream_request_)); + ASSERT_TRUE(upstream_request_->waitForHeadersComplete()); + expectRequestHeaders(upstream_request_->headers()); + + Http::TestResponseHeaderMapImpl response_headers{{":status", "404"}}; + upstream_request_->encodeHeaders(response_headers, true); + + test_server_->waitForCounterEq("cluster.cluster_0.upstream_rq_retry", 1); + test_server_->waitForGaugeEq("udp.foo.downstream_sess_active", 1); + + // Since retry is enabled, a new request is expected to be sent by the UDP proxy. + ASSERT_TRUE(fake_upstream_connection_->waitForNewStream(*dispatcher_, upstream_request_)); + ASSERT_TRUE(upstream_request_->waitForHeadersComplete()); + expectRequestHeaders(upstream_request_->headers()); + + upstream_request_->encodeHeaders(response_headers, true); + + test_server_->waitForCounterEq("cluster.cluster_0.udp.sess_tunnel_failure", 1); + test_server_->waitForCounterEq("cluster.cluster_0.udp.sess_tunnel_success", 0); + test_server_->waitForGaugeEq("udp.foo.downstream_sess_active", 0); + + // Verify response header value is in the access log. + EXPECT_THAT(waitForAccessLog(access_log_filename), testing::HasSubstr("404")); +} + TEST_P(UdpTunnelingIntegrationTest, PropagateResponseTrailers) { const std::string access_log_filename = TestEnvironment::temporaryPath(TestUtility::uniqueFilename()); diff --git a/test/integration/xds_integration_test.cc b/test/integration/xds_integration_test.cc index c244d1313694c..5435bb17d55e9 100644 --- a/test/integration/xds_integration_test.cc +++ b/test/integration/xds_integration_test.cc @@ -28,6 +28,7 @@ class XdsIntegrationTest : public testing::TestWithParam, congestionWindowInBytes, (), (const)); \ - MOCK_METHOD(void, dumpState, (std::ostream&, int), (const)); + MOCK_METHOD(void, dumpState, (std::ostream&, int), (const)); \ + MOCK_METHOD(ExecutionContext*, executionContext, (), (const)); class MockConnection : public Connection, public MockConnectionBase { public: diff --git a/test/mocks/network/mocks.h b/test/mocks/network/mocks.h index 09417750b16bd..3c16e1d0e58e5 100644 --- a/test/mocks/network/mocks.h +++ b/test/mocks/network/mocks.h @@ -409,6 +409,7 @@ class MockConnectionSocket : public ConnectionSocket { MOCK_METHOD(absl::optional, lastRoundTripTime, ()); MOCK_METHOD(absl::optional, congestionWindowInBytes, (), (const)); MOCK_METHOD(void, dumpState, (std::ostream&, int), (const)); + MOCK_METHOD(ExecutionContext*, executionContext, (), (const)); IoHandlePtr io_handle_; std::shared_ptr connection_info_provider_; diff --git a/test/mocks/stream_info/mocks.cc b/test/mocks/stream_info/mocks.cc index 5b92c27f06f29..2db8ffc736318 100644 --- a/test/mocks/stream_info/mocks.cc +++ b/test/mocks/stream_info/mocks.cc @@ -86,7 +86,10 @@ MockStreamInfo::MockStreamInfo() downstream_direct_remote_address); ON_CALL(*this, setResponseFlag(_)).WillByDefault(Invoke([this](ResponseFlag response_flag) { - response_flags_ |= response_flag; + auto iter = std::find(response_flags_.begin(), response_flags_.end(), response_flag); + if (iter == response_flags_.end()) { + response_flags_.push_back(response_flag); + } })); ON_CALL(*this, setResponseCode(_)).WillByDefault(Invoke([this](uint32_t code) { response_code_ = code; @@ -138,17 +141,26 @@ MockStreamInfo::MockStreamInfo() })); ON_CALL(*this, bytesSent()).WillByDefault(ReturnPointee(&bytes_sent_)); ON_CALL(*this, hasResponseFlag(_)).WillByDefault(Invoke([this](ResponseFlag flag) { - return response_flags_ & flag; - })); - ON_CALL(*this, intersectResponseFlags(_)).WillByDefault(Invoke([this](uint64_t response_flags) { - return (response_flags_ & response_flags) != 0; + auto iter = std::find(response_flags_.begin(), response_flags_.end(), flag); + return iter != response_flags_.end(); })); ON_CALL(*this, hasAnyResponseFlag()).WillByDefault(Invoke([this]() { - return response_flags_ != 0; + return !response_flags_.empty(); })); - ON_CALL(*this, responseFlags()).WillByDefault(Invoke([this]() -> uint64_t { + ON_CALL(*this, responseFlags()).WillByDefault(Invoke([this]() -> absl::Span { return response_flags_; })); + ON_CALL(*this, legacyResponseFlags()).WillByDefault(Invoke([this]() -> uint64_t { + uint64_t legacy_flags = 0; + for (ResponseFlag flag : response_flags_) { + if (flag.value() <= static_cast(CoreResponseFlag::LastFlag)) { + ASSERT(flag.value() < 64, "Legacy response flag out of range"); + legacy_flags |= (1UL << flag.value()); + } + } + return legacy_flags; + })); + ON_CALL(*this, dynamicMetadata()).WillByDefault(ReturnRef(metadata_)); ON_CALL(Const(*this), dynamicMetadata()).WillByDefault(ReturnRef(metadata_)); ON_CALL(*this, filterState()).WillByDefault(ReturnRef(filter_state_)); diff --git a/test/mocks/stream_info/mocks.h b/test/mocks/stream_info/mocks.h index b83a40d7e69cb..0b166849e32ac 100644 --- a/test/mocks/stream_info/mocks.h +++ b/test/mocks/stream_info/mocks.h @@ -13,6 +13,29 @@ #include "gmock/gmock.h" +namespace testing { + +template <> +class Matcher + : public internal::MatcherBase { +public: + explicit Matcher() = default; + Matcher(Envoy::StreamInfo::ResponseFlag value) { *this = Eq(value); } + Matcher(Envoy::StreamInfo::CoreResponseFlag value) { + *this = Eq(Envoy::StreamInfo::ResponseFlag(value)); + } + + explicit Matcher(const MatcherInterface* impl) + : internal::MatcherBase(impl) {} + + template + explicit Matcher(const MatcherInterface* impl, + typename std::enable_if::value>::type* = nullptr) + : internal::MatcherBase(impl) {} +}; + +} // namespace testing + namespace Envoy { namespace StreamInfo { @@ -71,7 +94,6 @@ class MockStreamInfo : public StreamInfo { MOCK_METHOD(void, setResponseCode, (uint32_t)); MOCK_METHOD(void, setResponseCodeDetails, (absl::string_view)); MOCK_METHOD(void, setConnectionTerminationDetails, (absl::string_view)); - MOCK_METHOD(bool, intersectResponseFlags, (uint64_t), (const)); MOCK_METHOD(void, onUpstreamHostSelected, (Upstream::HostDescriptionConstSharedPtr host)); MOCK_METHOD(SystemTime, startTime, (), (const)); MOCK_METHOD(MonotonicTime, startTimeMonotonic, (), (const)); @@ -107,7 +129,8 @@ class MockStreamInfo : public StreamInfo { MOCK_METHOD(uint64_t, wireBytesSent, (), (const)); MOCK_METHOD(bool, hasResponseFlag, (ResponseFlag), (const)); MOCK_METHOD(bool, hasAnyResponseFlag, (), (const)); - MOCK_METHOD(uint64_t, responseFlags, (), (const)); + MOCK_METHOD(absl::Span, responseFlags, (), (const)); + MOCK_METHOD(uint64_t, legacyResponseFlags, (), (const)); MOCK_METHOD(bool, healthCheck, (), (const)); MOCK_METHOD(void, healthCheck, (bool is_health_check)); MOCK_METHOD(const Network::ConnectionInfoProvider&, downstreamAddressProvider, (), (const)); @@ -153,7 +176,7 @@ class MockStreamInfo : public StreamInfo { absl::optional connection_termination_details_; absl::optional upstream_cluster_info_; std::shared_ptr upstream_info_; - uint64_t response_flags_{}; + absl::InlinedVector response_flags_{}; envoy::config::core::v3::Metadata metadata_; FilterStateSharedPtr filter_state_; uint64_t bytes_received_{}; diff --git a/test/mocks/upstream/cluster_info.cc b/test/mocks/upstream/cluster_info.cc index 9bce3ae3dec2d..dd84cad3aa8db 100644 --- a/test/mocks/upstream/cluster_info.cc +++ b/test/mocks/upstream/cluster_info.cc @@ -53,7 +53,8 @@ MockUpstreamLocalAddressSelector::MockUpstreamLocalAddressSelector( MockClusterInfo::MockClusterInfo() : http2_options_(::Envoy::Http2::Utility::initializeAndValidateOptions( - envoy::config::core::v3::Http2ProtocolOptions())), + envoy::config::core::v3::Http2ProtocolOptions()) + .value()), traffic_stat_names_(stats_store_.symbolTable()), config_update_stats_names_(stats_store_.symbolTable()), lb_stat_names_(stats_store_.symbolTable()), endpoint_stat_names_(stats_store_.symbolTable()), diff --git a/test/mocks/upstream/cluster_info.h b/test/mocks/upstream/cluster_info.h index 4ca2bd73d1ff4..145f2cb0f72ae 100644 --- a/test/mocks/upstream/cluster_info.h +++ b/test/mocks/upstream/cluster_info.h @@ -203,7 +203,9 @@ class MockClusterInfo : public ClusterInfo { Http::FilterChainManager& manager), (const)); MOCK_METHOD(Http::ClientHeaderValidatorPtr, makeHeaderValidator, (Http::Protocol), (const)); - + MOCK_METHOD(const absl::optional< + envoy::config::cluster::v3::UpstreamConnectionOptions::HappyEyeballsConfig>, + happyEyeballsConfig, (), (const)); ::Envoy::Http::HeaderValidatorStats& codecStats(Http::Protocol protocol) const; Http::Http1::CodecStats& http1CodecStats() const override; Http::Http2::CodecStats& http2CodecStats() const override; @@ -270,6 +272,8 @@ class MockClusterInfo : public ClusterInfo { mutable Http::Http2::CodecStats::AtomicPtr http2_codec_stats_; mutable Http::Http3::CodecStats::AtomicPtr http3_codec_stats_; Http::HeaderValidatorFactoryPtr header_validator_factory_; + absl::optional + happy_eyeballs_config_; }; class MockIdleTimeEnabledClusterInfo : public MockClusterInfo { diff --git a/test/mocks/upstream/priority_set.h b/test/mocks/upstream/priority_set.h index a19e208d12580..b7ba1d2019706 100644 --- a/test/mocks/upstream/priority_set.h +++ b/test/mocks/upstream/priority_set.h @@ -25,7 +25,8 @@ class MockPrioritySet : public PrioritySet { MOCK_METHOD(void, updateHosts, (uint32_t priority, UpdateHostsParams&& update_hosts_params, LocalityWeightsConstSharedPtr locality_weights, const HostVector& hosts_added, - const HostVector& hosts_removed, absl::optional weighted_priority_health, + const HostVector& hosts_removed, uint64_t seed, + absl::optional weighted_priority_health, absl::optional overprovisioning_factor, HostMapConstSharedPtr cross_priority_host_map)); MOCK_METHOD(void, batchHostUpdate, (BatchUpdateCb&)); diff --git a/test/per_file_coverage.sh b/test/per_file_coverage.sh index 7edf9ee544c52..ef17130138832 100755 --- a/test/per_file_coverage.sh +++ b/test/per_file_coverage.sh @@ -3,7 +3,7 @@ # directory:coverage_percent # for existing directories with low coverage. declare -a KNOWN_LOW_COVERAGE=( -"source/common:96.2" +"source/common:95.9" # TODO(#32149): increase this once io_uring is tested. "source/common/api:84.5" # flaky due to posix: be careful adjusting "source/common/api/posix:83.8" # flaky (accept failover non-deterministic): be careful adjusting "source/common/config:95.4" @@ -11,6 +11,7 @@ declare -a KNOWN_LOW_COVERAGE=( "source/common/event:95.0" # Emulated edge events guards don't report LCOV "source/common/filesystem/posix:96.2" # FileReadToEndNotReadable fails in some env; createPath can't test all failure branches. "source/common/http/http2:95.2" +"source/common/io:57.9" # TODO(#32149): CI has stopped executing this code. "source/common/json:94.6" "source/common/matcher:94.6" "source/common/network:94.4" # Flaky, `activateFileEvents`, `startSecureTransport` and `ioctl`, listener_socket do not always report LCOV diff --git a/test/server/admin/clusters_handler_test.cc b/test/server/admin/clusters_handler_test.cc index ac88226f454e8..389e713d1e19d 100644 --- a/test/server/admin/clusters_handler_test.cc +++ b/test/server/admin/clusters_handler_test.cc @@ -80,6 +80,8 @@ TEST_P(AdminInstanceTest, ClustersJsonAndText) { .WillByDefault(Return(true)); ON_CALL(*host, healthFlagGet(Upstream::Host::HealthFlag::FAILED_EDS_HEALTH)) .WillByDefault(Return(false)); + ON_CALL(*host, healthFlagGet(Upstream::Host::HealthFlag::EDS_STATUS_DRAINING)) + .WillByDefault(Return(true)); ON_CALL(*host, healthFlagGet(Upstream::Host::HealthFlag::DEGRADED_ACTIVE_HC)) .WillByDefault(Return(true)); ON_CALL(*host, healthFlagGet(Upstream::Host::HealthFlag::DEGRADED_EDS_HEALTH)) @@ -171,7 +173,7 @@ TEST_P(AdminInstanceTest, ClustersJsonAndText) { } ], "health_status": { - "eds_health_status": "DEGRADED", + "eds_health_status": "DRAINING", "failed_active_health_check": true, "failed_outlier_check": true, "failed_active_degraded_check": true, @@ -228,7 +230,7 @@ fake_cluster::1.2.3.4:80::rest_counter::10 fake_cluster::1.2.3.4:80::test_counter::10 fake_cluster::1.2.3.4:80::test_gauge::11 fake_cluster::1.2.3.4:80::hostname::foo.com -fake_cluster::1.2.3.4:80::health_flags::/failed_active_hc/failed_outlier_check/degraded_active_hc/degraded_eds_health/pending_dynamic_removal +fake_cluster::1.2.3.4:80::health_flags::/failed_active_hc/failed_outlier_check/degraded_active_hc/degraded_eds_health/pending_dynamic_removal/eds_status_draining fake_cluster::1.2.3.4:80::weight::5 fake_cluster::1.2.3.4:80::region::test_region fake_cluster::1.2.3.4:80::zone::test_zone diff --git a/test/server/admin/stats_handler_speed_test.cc b/test/server/admin/stats_handler_speed_test.cc index ebd8a57ad117c..15fdea7ba0789 100644 --- a/test/server/admin/stats_handler_speed_test.cc +++ b/test/server/admin/stats_handler_speed_test.cc @@ -149,6 +149,11 @@ class StatsHandlerTest : public Stats::ThreadLocalRealThreadsMixin { } } store_->mergeHistograms([]() {}); + } + + void initClusterInfo() { + ENVOY_LOG_MISC(error, "Initializing cluster info; slow to construct and destruct..."); + endpoint_stats_initialized_ = true; cm_.store_.fixed_tags_ = Stats::TagVector{{"fixed-tag", "fixed-value"}}; for (uint32_t i = 0; i < NumClusters; i++) { @@ -169,7 +174,12 @@ class StatsHandlerTest : public Stats::ThreadLocalRealThreadsMixin { } } - void setPerEndpointStats(bool enabled) { cm_.per_endpoint_enabled_ = enabled; } + void setPerEndpointStats(bool enabled) { + if (enabled && !endpoint_stats_initialized_) { + initClusterInfo(); + } + cm_.per_endpoint_enabled_ = enabled; + } /** * Issues an admin request against the stats saved in store_. @@ -196,6 +206,7 @@ class StatsHandlerTest : public Stats::ThreadLocalRealThreadsMixin { std::vector scopes_; Envoy::Stats::CustomStatNamespacesImpl custom_namespaces_; FastMockClusterManager cm_; + bool endpoint_stats_initialized_{false}; }; } // namespace Server @@ -408,8 +419,8 @@ BENCHMARK_CAPTURE(BM_FilteredCountersPrometheus, per_endpoint_stats_enabled, tru ->Unit(benchmark::kMillisecond); // NOLINTNEXTLINE(readability-identifier-naming) -static void BM_HistogramsJson(benchmark::State& state) { - Envoy::Server::StatsHandlerTest& test_context = testContext(false); +static void BM_HistogramsJson(benchmark::State& state, bool per_endpoint_stats) { + Envoy::Server::StatsHandlerTest& test_context = testContext(per_endpoint_stats); Envoy::Server::StatsParams params; Envoy::Buffer::OwnedImpl response; params.parse("?format=json&type=Histograms&histogram_buckets=detailed", response); @@ -424,4 +435,7 @@ static void BM_HistogramsJson(benchmark::State& state) { auto label = absl::StrCat("output per iteration: ", count); state.SetLabel(label); } -BENCHMARK(BM_HistogramsJson)->Unit(benchmark::kMillisecond); +BENCHMARK_CAPTURE(BM_HistogramsJson, per_endpoint_stats_disabled, false) + ->Unit(benchmark::kMillisecond); +BENCHMARK_CAPTURE(BM_HistogramsJson, per_endpoint_stats_enabled, true) + ->Unit(benchmark::kMillisecond); diff --git a/test/server/configuration_impl_test.cc b/test/server/configuration_impl_test.cc index 44c6837b99d4a..19a8933044700 100644 --- a/test/server/configuration_impl_test.cc +++ b/test/server/configuration_impl_test.cc @@ -89,7 +89,7 @@ TEST_F(ConfigurationImplTest, DefaultStatsFlushInterval) { envoy::config::bootstrap::v3::Bootstrap bootstrap; MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_EQ(std::chrono::milliseconds(5000), config.statsConfig().flushInterval()); EXPECT_FALSE(config.statsConfig().flushOnAdmin()); @@ -122,7 +122,7 @@ TEST_F(ConfigurationImplTest, CustomStatsFlushInterval) { auto bootstrap = Upstream::parseBootstrapFromV3Json(json); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_EQ(std::chrono::milliseconds(500), config.statsConfig().flushInterval()); EXPECT_FALSE(config.statsConfig().flushOnAdmin()); @@ -156,7 +156,7 @@ TEST_F(ConfigurationImplTest, StatsOnAdmin) { auto bootstrap = Upstream::parseBootstrapFromV3Json(json); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_TRUE(config.statsConfig().flushOnAdmin()); } @@ -219,9 +219,8 @@ TEST_F(ConfigurationImplTest, IntervalAndAdminFlush) { auto bootstrap = Upstream::parseBootstrapFromV3Json(json); MainImpl config; - EXPECT_THROW_WITH_MESSAGE( - config.initialize(bootstrap, server_, cluster_manager_factory_), EnvoyException, - "Only one of stats_flush_interval or stats_flush_on_admin should be set!"); + EXPECT_EQ(config.initialize(bootstrap, server_, cluster_manager_factory_).message(), + "Only one of stats_flush_interval or stats_flush_on_admin should be set!"); } TEST_F(ConfigurationImplTest, SetUpstreamClusterPerConnectionBufferLimit) { @@ -280,7 +279,7 @@ TEST_F(ConfigurationImplTest, SetUpstreamClusterPerConnectionBufferLimit) { auto bootstrap = Upstream::parseBootstrapFromV3Json(json); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); ASSERT_EQ(1U, config.clusterManager()->clusters().active_clusters_.count("test_cluster")); EXPECT_EQ(8192U, config.clusterManager() @@ -333,7 +332,7 @@ TEST_F(ConfigurationImplTest, NullTracerSetWhenTracingConfigurationAbsent) { server_.local_info_.node_.set_cluster(""); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_THAT(envoy::config::trace::v3::Tracing{}, ProtoEq(server_.httpContext().defaultTracingConfig())); @@ -381,7 +380,7 @@ TEST_F(ConfigurationImplTest, NullTracerSetWhenHttpKeyAbsentFromTracerConfigurat server_.local_info_.node_.set_cluster(""); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_THAT(envoy::config::trace::v3::Tracing{}, ProtoEq(server_.httpContext().defaultTracingConfig())); @@ -439,10 +438,11 @@ TEST_F(ConfigurationImplTest, ConfigurationFailsWhenInvalidTracerSpecified) { auto bootstrap = Upstream::parseBootstrapFromV3Json(json); MainImpl config; - EXPECT_THROW_WITH_MESSAGE(config.initialize(bootstrap, server_, cluster_manager_factory_), - EnvoyException, - "Didn't find a registered implementation for 'invalid' with type URL: " - "'envoy.config.trace.v2.BlackHoleConfig'"); + EXPECT_THROW_WITH_MESSAGE( + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()), + EnvoyException, + "Didn't find a registered implementation for 'invalid' with type URL: " + "'envoy.config.trace.v2.BlackHoleConfig'"); } TEST_F(ConfigurationImplTest, ProtoSpecifiedStatsSink) { @@ -480,7 +480,7 @@ TEST_F(ConfigurationImplTest, ProtoSpecifiedStatsSink) { server_.server_factory_context_->cluster_manager_.initializeClusters({"fake_cluster"}, {}); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_EQ(1, config.statsConfig().sinks().size()); } @@ -519,7 +519,8 @@ TEST_F(ConfigurationImplTest, StatsSinkWithInvalidName) { MainImpl config; EXPECT_THROW_WITH_MESSAGE( - config.initialize(bootstrap, server_, cluster_manager_factory_), EnvoyException, + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()), + EnvoyException, "Didn't find a registered implementation for 'envoy.invalid' with type URL: ''"); } @@ -555,9 +556,9 @@ TEST_F(ConfigurationImplTest, StatsSinkWithNoName) { bootstrap.mutable_stats_sinks()->Add(); MainImpl config; - EXPECT_THROW_WITH_MESSAGE(config.initialize(bootstrap, server_, cluster_manager_factory_), - EnvoyException, - "Didn't find a registered implementation for '' with type URL: ''"); + EXPECT_THROW_WITH_MESSAGE( + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()), + EnvoyException, "Didn't find a registered implementation for '' with type URL: ''"); } TEST_F(ConfigurationImplTest, StatsSinkWithNoType) { @@ -596,9 +597,9 @@ TEST_F(ConfigurationImplTest, StatsSinkWithNoType) { sink.mutable_typed_config()->PackFrom(typed_struct); MainImpl config; - EXPECT_THROW_WITH_MESSAGE(config.initialize(bootstrap, server_, cluster_manager_factory_), - EnvoyException, - "Didn't find a registered implementation for '' with type URL: ''"); + EXPECT_THROW_WITH_MESSAGE( + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()), + EnvoyException, "Didn't find a registered implementation for '' with type URL: ''"); } // An explicit non-empty LayeredRuntime is available to the server with no @@ -620,7 +621,9 @@ TEST(InitialImplTest, LayeredRuntime) { )EOF"; const auto bootstrap = TestUtility::parseYaml(yaml); NiceMock server; - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); EXPECT_THAT(config.runtime(), ProtoEq(bootstrap.layered_runtime())); } @@ -632,7 +635,9 @@ TEST(InitialImplTest, EmptyLayeredRuntime) { const auto bootstrap = TestUtility::parseYaml(bootstrap_yaml); NiceMock server; - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); const std::string expected_yaml = R"EOF( layers: @@ -681,7 +686,9 @@ TEST_F(ConfigurationImplTest, AdminSocketOptions) { )EOF"; auto bootstrap = Upstream::parseBootstrapFromV3Json(json); - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); Network::MockListenSocket socket_mock; @@ -720,7 +727,9 @@ TEST_F(ConfigurationImplTest, FileAccessLogOutput) { )EOF"; auto bootstrap = Upstream::parseBootstrapFromV3Json(json); - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); Network::MockListenSocket socket_mock; @@ -810,8 +819,8 @@ TEST_F(ConfigurationImplTest, ExceedLoadBalancerHostWeightsLimit) { MainImpl config; EXPECT_THROW_WITH_MESSAGE( - config.initialize(bootstrap, server_, cluster_manager_factory_), EnvoyException, - "The sum of weights of all upstream hosts in a locality exceeds 4294967295"); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()), + EnvoyException, "The sum of weights of all upstream hosts in a locality exceeds 4294967295"); } TEST_F(ConfigurationImplTest, ExceedLoadBalancerLocalityWeightsLimit) { @@ -924,7 +933,8 @@ TEST_F(ConfigurationImplTest, ExceedLoadBalancerLocalityWeightsLimit) { MainImpl config; EXPECT_THROW_WITH_MESSAGE( - config.initialize(bootstrap, server_, cluster_manager_factory_), EnvoyException, + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()), + EnvoyException, "The sum of weights of all localities at the same priority exceeds 4294967295"); } @@ -940,7 +950,7 @@ TEST_F(ConfigurationImplTest, KillTimeoutWithoutSkew) { TestUtility::loadFromJson(json, bootstrap); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_EQ(config.workerWatchdogConfig().killTimeout(), std::chrono::milliseconds(1000)); EXPECT_EQ(config.mainThreadWatchdogConfig().killTimeout(), std::chrono::milliseconds(1000)); @@ -959,7 +969,7 @@ TEST_F(ConfigurationImplTest, CanSkewsKillTimeout) { TestUtility::loadFromJson(json, bootstrap); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_LT(std::chrono::milliseconds(1000), config.mainThreadWatchdogConfig().killTimeout()); EXPECT_LT(std::chrono::milliseconds(1000), config.workerWatchdogConfig().killTimeout()); @@ -979,7 +989,7 @@ TEST_F(ConfigurationImplTest, DoesNotSkewIfKillTimeoutDisabled) { TestUtility::loadFromJson(json, bootstrap); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_EQ(config.mainThreadWatchdogConfig().killTimeout(), std::chrono::milliseconds(0)); EXPECT_EQ(config.workerWatchdogConfig().killTimeout(), std::chrono::milliseconds(0)); @@ -993,8 +1003,8 @@ TEST_F(ConfigurationImplTest, ShouldErrorIfBothWatchdogsAndWatchdogSet) { MainImpl config; - EXPECT_THROW_WITH_MESSAGE(config.initialize(bootstrap, server_, cluster_manager_factory_), - EnvoyException, "Only one of watchdog or watchdogs should be set!"); + EXPECT_EQ(config.initialize(bootstrap, server_, cluster_manager_factory_).message(), + "Only one of watchdog or watchdogs should be set!"); } TEST_F(ConfigurationImplTest, CanSetMultiWatchdogConfigs) { @@ -1011,7 +1021,7 @@ TEST_F(ConfigurationImplTest, CanSetMultiWatchdogConfigs) { TestUtility::loadFromJson(json, bootstrap); MainImpl config; - config.initialize(bootstrap, server_, cluster_manager_factory_); + EXPECT_TRUE(config.initialize(bootstrap, server_, cluster_manager_factory_).ok()); EXPECT_EQ(config.mainThreadWatchdogConfig().missTimeout(), std::chrono::milliseconds(2000)); EXPECT_EQ(config.workerWatchdogConfig().missTimeout(), std::chrono::milliseconds(500)); @@ -1042,7 +1052,9 @@ TEST_F(ConfigurationImplTest, DEPRECATED_FEATURE_TEST(DeprecatedAccessLogPathWit )EOF"; auto bootstrap = Upstream::parseBootstrapFromV3Json(json); - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); Network::MockListenSocket socket_mock; @@ -1077,7 +1089,9 @@ TEST_F(ConfigurationImplTest, AccessLogWithFilter) { )EOF"; auto bootstrap = Upstream::parseBootstrapFromV3Json(json); - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); ASSERT_EQ(config.admin().accessLogs().size(), 1); @@ -1112,7 +1126,9 @@ TEST_F(ConfigurationImplTest, DEPRECATED_FEATURE_TEST(DeprecatedAccessLogPathWit )EOF"; auto bootstrap = Upstream::parseBootstrapFromV3Json(json); - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); ASSERT_EQ(config.admin().accessLogs().size(), 2); @@ -1126,7 +1142,9 @@ TEST_F(ConfigurationImplTest, EmptyAdmin) { )EOF"; auto bootstrap = Upstream::parseBootstrapFromV3Json(json); - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); ASSERT_EQ(config.admin().accessLogs().size(), 0); @@ -1149,7 +1167,9 @@ TEST_F(ConfigurationImplTest, DEPRECATED_FEATURE_TEST(DeprecatedAccessLogPath)) auto bootstrap = Upstream::parseBootstrapFromV3Json(json); NiceMock server; - InitialImpl config(bootstrap); + absl::Status status; + InitialImpl config(bootstrap, status); + ASSERT_TRUE(status.ok()); config.initAdminAccessLog(bootstrap, factory_context_); Network::MockListenSocket socket_mock; diff --git a/test/server/overload_manager_impl_test.cc b/test/server/overload_manager_impl_test.cc index c09eb4e12fc0d..2ede9fd94c3bc 100644 --- a/test/server/overload_manager_impl_test.cc +++ b/test/server/overload_manager_impl_test.cc @@ -772,23 +772,6 @@ TEST_F(OverloadManagerImplTest, UnknownActionShouldError) { "Unknown Overload Manager Action .*"); } -TEST_F(OverloadManagerImplTest, LegacyUnknownActionShouldSilentlyFail) { - scoped_runtime_.mergeValues( - {{"envoy.reloadable_features.overload_manager_error_unknown_action", "false"}}); - const std::string config = R"EOF( - resource_monitors: - - name: "envoy.resource_monitors.fake_resource1" - actions: - - name: "envoy.overload_actions.not_a_valid_action" - triggers: - - name: "envoy.resource_monitors.fake_resource1" - threshold: - value: 0.9 - )EOF"; - - auto overload_manager = createOverloadManager(config); -} - TEST_F(OverloadManagerImplTest, UnknownTrigger) { const std::string config = R"EOF( actions: diff --git a/test/test_common/utility.h b/test/test_common/utility.h index ac0545a5a7cd9..c365450e83a46 100644 --- a/test/test_common/utility.h +++ b/test/test_common/utility.h @@ -47,12 +47,14 @@ using testing::Invoke; // NOLINT(misc-unused-using-decls) namespace Envoy { -#if defined(__has_feature) && __has_feature(thread_sanitizer) -#define TSAN_TIMEOUT_FACTOR 3 +#if defined(__has_feature) && \ + (__has_feature(thread_sanitizer) || __has_feature(memory_sanitizer) || \ + __has_feature(address_sanitizer)) +#define TIMEOUT_FACTOR 3 #elif defined(ENVOY_CONFIG_COVERAGE) -#define TSAN_TIMEOUT_FACTOR 3 +#define TIMEOUT_FACTOR 3 #else -#define TSAN_TIMEOUT_FACTOR 1 +#define TIMEOUT_FACTOR 1 #endif /* @@ -587,7 +589,7 @@ class TestUtility { const std::string& output_format); static constexpr std::chrono::milliseconds DefaultTimeout = - std::chrono::milliseconds(10000) * TSAN_TIMEOUT_FACTOR; + std::chrono::milliseconds(10000) * TIMEOUT_FACTOR; /** * Return a prefix string matcher. diff --git a/tools/base/requirements.in b/tools/base/requirements.in index 0b345c045b9f6..dda44ea97a8c7 100644 --- a/tools/base/requirements.in +++ b/tools/base/requirements.in @@ -38,7 +38,12 @@ pyyaml setuptools slack_sdk sphinx>=7,<7.2 +sphinxcontrib-applehelp>=1.0.8 +sphinxcontrib-devhelp>=1.0.6 sphinxcontrib.googleanalytics +sphinxcontrib-htmlhelp>=2.0.5 +sphinxcontrib-qthelp>=1.0.7 +sphinxcontrib-serializinghtml>=1.1.10 thrift verboselogs yapf diff --git a/tools/base/requirements.txt b/tools/base/requirements.txt index 693e3f55c4b6d..cfda8b641e015 100644 --- a/tools/base/requirements.txt +++ b/tools/base/requirements.txt @@ -86,83 +86,83 @@ aiofiles==23.2.1 \ --hash=sha256:19297512c647d4b27a2cf7c34caa7e405c0d60b5560618a29a9fe027b18b0107 \ --hash=sha256:84ec2218d8419404abcb9f0c02df3f34c6e0a68ed41072acfb1cef5cbc29051a # via envoy-github-release -aiohttp==3.9.1 \ - --hash=sha256:02ab6006ec3c3463b528374c4cdce86434e7b89ad355e7bf29e2f16b46c7dd6f \ - --hash=sha256:04fa38875e53eb7e354ece1607b1d2fdee2d175ea4e4d745f6ec9f751fe20c7c \ - --hash=sha256:0b0a6a36ed7e164c6df1e18ee47afbd1990ce47cb428739d6c99aaabfaf1b3af \ - --hash=sha256:0d406b01a9f5a7e232d1b0d161b40c05275ffbcbd772dc18c1d5a570961a1ca4 \ - --hash=sha256:0e49b08eafa4f5707ecfb321ab9592717a319e37938e301d462f79b4e860c32a \ - --hash=sha256:0e7ba7ff228c0d9a2cd66194e90f2bca6e0abca810b786901a569c0de082f489 \ - --hash=sha256:11cb254e397a82efb1805d12561e80124928e04e9c4483587ce7390b3866d213 \ - --hash=sha256:11ff168d752cb41e8492817e10fb4f85828f6a0142b9726a30c27c35a1835f01 \ - --hash=sha256:176df045597e674fa950bf5ae536be85699e04cea68fa3a616cf75e413737eb5 \ - --hash=sha256:219a16763dc0294842188ac8a12262b5671817042b35d45e44fd0a697d8c8361 \ - --hash=sha256:22698f01ff5653fe66d16ffb7658f582a0ac084d7da1323e39fd9eab326a1f26 \ - --hash=sha256:237533179d9747080bcaad4d02083ce295c0d2eab3e9e8ce103411a4312991a0 \ - --hash=sha256:289ba9ae8e88d0ba16062ecf02dd730b34186ea3b1e7489046fc338bdc3361c4 \ - --hash=sha256:2c59e0076ea31c08553e868cec02d22191c086f00b44610f8ab7363a11a5d9d8 \ - --hash=sha256:2c9376e2b09895c8ca8b95362283365eb5c03bdc8428ade80a864160605715f1 \ - --hash=sha256:3135713c5562731ee18f58d3ad1bf41e1d8883eb68b363f2ffde5b2ea4b84cc7 \ - --hash=sha256:3b9c7426923bb7bd66d409da46c41e3fb40f5caf679da624439b9eba92043fa6 \ - --hash=sha256:3c0266cd6f005e99f3f51e583012de2778e65af6b73860038b968a0a8888487a \ - --hash=sha256:41473de252e1797c2d2293804e389a6d6986ef37cbb4a25208de537ae32141dd \ - --hash=sha256:4831df72b053b1eed31eb00a2e1aff6896fb4485301d4ccb208cac264b648db4 \ - --hash=sha256:49f0c1b3c2842556e5de35f122fc0f0b721334ceb6e78c3719693364d4af8499 \ - --hash=sha256:4b4c452d0190c5a820d3f5c0f3cd8a28ace48c54053e24da9d6041bf81113183 \ - --hash=sha256:4ee8caa925aebc1e64e98432d78ea8de67b2272252b0a931d2ac3bd876ad5544 \ - --hash=sha256:500f1c59906cd142d452074f3811614be04819a38ae2b3239a48b82649c08821 \ - --hash=sha256:5216b6082c624b55cfe79af5d538e499cd5f5b976820eac31951fb4325974501 \ - --hash=sha256:54311eb54f3a0c45efb9ed0d0a8f43d1bc6060d773f6973efd90037a51cd0a3f \ - --hash=sha256:54631fb69a6e44b2ba522f7c22a6fb2667a02fd97d636048478db2fd8c4e98fe \ - --hash=sha256:565760d6812b8d78d416c3c7cfdf5362fbe0d0d25b82fed75d0d29e18d7fc30f \ - --hash=sha256:598db66eaf2e04aa0c8900a63b0101fdc5e6b8a7ddd805c56d86efb54eb66672 \ - --hash=sha256:5c4fa235d534b3547184831c624c0b7c1e262cd1de847d95085ec94c16fddcd5 \ - --hash=sha256:69985d50a2b6f709412d944ffb2e97d0be154ea90600b7a921f95a87d6f108a2 \ - --hash=sha256:69da0f3ed3496808e8cbc5123a866c41c12c15baaaead96d256477edf168eb57 \ - --hash=sha256:6c93b7c2e52061f0925c3382d5cb8980e40f91c989563d3d32ca280069fd6a87 \ - --hash=sha256:70907533db712f7aa791effb38efa96f044ce3d4e850e2d7691abd759f4f0ae0 \ - --hash=sha256:81b77f868814346662c96ab36b875d7814ebf82340d3284a31681085c051320f \ - --hash=sha256:82eefaf1a996060602f3cc1112d93ba8b201dbf5d8fd9611227de2003dddb3b7 \ - --hash=sha256:85c3e3c9cb1d480e0b9a64c658cd66b3cfb8e721636ab8b0e746e2d79a7a9eed \ - --hash=sha256:8a22a34bc594d9d24621091d1b91511001a7eea91d6652ea495ce06e27381f70 \ - --hash=sha256:8cef8710fb849d97c533f259103f09bac167a008d7131d7b2b0e3a33269185c0 \ - --hash=sha256:8d44e7bf06b0c0a70a20f9100af9fcfd7f6d9d3913e37754c12d424179b4e48f \ - --hash=sha256:8d7f98fde213f74561be1d6d3fa353656197f75d4edfbb3d94c9eb9b0fc47f5d \ - --hash=sha256:8d8e4450e7fe24d86e86b23cc209e0023177b6d59502e33807b732d2deb6975f \ - --hash=sha256:8fc49a87ac269d4529da45871e2ffb6874e87779c3d0e2ccd813c0899221239d \ - --hash=sha256:90ec72d231169b4b8d6085be13023ece8fa9b1bb495e4398d847e25218e0f431 \ - --hash=sha256:91c742ca59045dce7ba76cab6e223e41d2c70d79e82c284a96411f8645e2afff \ - --hash=sha256:9b05d33ff8e6b269e30a7957bd3244ffbce2a7a35a81b81c382629b80af1a8bf \ - --hash=sha256:9b05d5cbe9dafcdc733262c3a99ccf63d2f7ce02543620d2bd8db4d4f7a22f83 \ - --hash=sha256:9c5857612c9813796960c00767645cb5da815af16dafb32d70c72a8390bbf690 \ - --hash=sha256:a34086c5cc285be878622e0a6ab897a986a6e8bf5b67ecb377015f06ed316587 \ - --hash=sha256:ab221850108a4a063c5b8a70f00dd7a1975e5a1713f87f4ab26a46e5feac5a0e \ - --hash=sha256:b796b44111f0cab6bbf66214186e44734b5baab949cb5fb56154142a92989aeb \ - --hash=sha256:b8c3a67eb87394386847d188996920f33b01b32155f0a94f36ca0e0c635bf3e3 \ - --hash=sha256:bcb6532b9814ea7c5a6a3299747c49de30e84472fa72821b07f5a9818bce0f66 \ - --hash=sha256:bcc0ea8d5b74a41b621ad4a13d96c36079c81628ccc0b30cfb1603e3dfa3a014 \ - --hash=sha256:bea94403a21eb94c93386d559bce297381609153e418a3ffc7d6bf772f59cc35 \ - --hash=sha256:bff7e2811814fa2271be95ab6e84c9436d027a0e59665de60edf44e529a42c1f \ - --hash=sha256:c72444d17777865734aa1a4d167794c34b63e5883abb90356a0364a28904e6c0 \ - --hash=sha256:c7b5d5d64e2a14e35a9240b33b89389e0035e6de8dbb7ffa50d10d8b65c57449 \ - --hash=sha256:c7e939f1ae428a86e4abbb9a7c4732bf4706048818dfd979e5e2839ce0159f23 \ - --hash=sha256:c88a15f272a0ad3d7773cf3a37cc7b7d077cbfc8e331675cf1346e849d97a4e5 \ - --hash=sha256:c9110c06eaaac7e1f5562caf481f18ccf8f6fdf4c3323feab28a93d34cc646bd \ - --hash=sha256:ca7ca5abfbfe8d39e653870fbe8d7710be7a857f8a8386fc9de1aae2e02ce7e4 \ - --hash=sha256:cae4c0c2ca800c793cae07ef3d40794625471040a87e1ba392039639ad61ab5b \ - --hash=sha256:cdefe289681507187e375a5064c7599f52c40343a8701761c802c1853a504558 \ - --hash=sha256:cf2a0ac0615842b849f40c4d7f304986a242f1e68286dbf3bd7a835e4f83acfd \ - --hash=sha256:cfeadf42840c1e870dc2042a232a8748e75a36b52d78968cda6736de55582766 \ - --hash=sha256:d737e69d193dac7296365a6dcb73bbbf53bb760ab25a3727716bbd42022e8d7a \ - --hash=sha256:d7481f581251bb5558ba9f635db70908819caa221fc79ee52a7f58392778c636 \ - --hash=sha256:df9cf74b9bc03d586fc53ba470828d7b77ce51b0582d1d0b5b2fb673c0baa32d \ - --hash=sha256:e1f80197f8b0b846a8d5cf7b7ec6084493950d0882cc5537fb7b96a69e3c8590 \ - --hash=sha256:ecca113f19d5e74048c001934045a2b9368d77b0b17691d905af18bd1c21275e \ - --hash=sha256:ee2527134f95e106cc1653e9ac78846f3a2ec1004cf20ef4e02038035a74544d \ - --hash=sha256:f27fdaadce22f2ef950fc10dcdf8048407c3b42b73779e48a4e76b3c35bca26c \ - --hash=sha256:f694dc8a6a3112059258a725a4ebe9acac5fe62f11c77ac4dcf896edfa78ca28 \ - --hash=sha256:f800164276eec54e0af5c99feb9494c295118fc10a11b997bbb1348ba1a52065 \ - --hash=sha256:ffcd828e37dc219a72c9012ec44ad2e7e3066bec6ff3aaa19e7d435dbf4032ca +aiohttp==3.9.3 \ + --hash=sha256:017a21b0df49039c8f46ca0971b3a7fdc1f56741ab1240cb90ca408049766168 \ + --hash=sha256:039df344b45ae0b34ac885ab5b53940b174530d4dd8a14ed8b0e2155b9dddccb \ + --hash=sha256:055ce4f74b82551678291473f66dc9fb9048a50d8324278751926ff0ae7715e5 \ + --hash=sha256:06a9b2c8837d9a94fae16c6223acc14b4dfdff216ab9b7202e07a9a09541168f \ + --hash=sha256:07b837ef0d2f252f96009e9b8435ec1fef68ef8b1461933253d318748ec1acdc \ + --hash=sha256:0ed621426d961df79aa3b963ac7af0d40392956ffa9be022024cd16297b30c8c \ + --hash=sha256:0fa43c32d1643f518491d9d3a730f85f5bbaedcbd7fbcae27435bb8b7a061b29 \ + --hash=sha256:1f5a71d25cd8106eab05f8704cd9167b6e5187bcdf8f090a66c6d88b634802b4 \ + --hash=sha256:1f5cd333fcf7590a18334c90f8c9147c837a6ec8a178e88d90a9b96ea03194cc \ + --hash=sha256:27468897f628c627230dba07ec65dc8d0db566923c48f29e084ce382119802bc \ + --hash=sha256:298abd678033b8571995650ccee753d9458dfa0377be4dba91e4491da3f2be63 \ + --hash=sha256:2c895a656dd7e061b2fd6bb77d971cc38f2afc277229ce7dd3552de8313a483e \ + --hash=sha256:361a1026c9dd4aba0109e4040e2aecf9884f5cfe1b1b1bd3d09419c205e2e53d \ + --hash=sha256:363afe77cfcbe3a36353d8ea133e904b108feea505aa4792dad6585a8192c55a \ + --hash=sha256:38a19bc3b686ad55804ae931012f78f7a534cce165d089a2059f658f6c91fa60 \ + --hash=sha256:38f307b41e0bea3294a9a2a87833191e4bcf89bb0365e83a8be3a58b31fb7f38 \ + --hash=sha256:3e59c23c52765951b69ec45ddbbc9403a8761ee6f57253250c6e1536cacc758b \ + --hash=sha256:4b4af9f25b49a7be47c0972139e59ec0e8285c371049df1a63b6ca81fdd216a2 \ + --hash=sha256:504b6981675ace64c28bf4a05a508af5cde526e36492c98916127f5a02354d53 \ + --hash=sha256:50fca156d718f8ced687a373f9e140c1bb765ca16e3d6f4fe116e3df7c05b2c5 \ + --hash=sha256:522a11c934ea660ff8953eda090dcd2154d367dec1ae3c540aff9f8a5c109ab4 \ + --hash=sha256:52df73f14ed99cee84865b95a3d9e044f226320a87af208f068ecc33e0c35b96 \ + --hash=sha256:595f105710293e76b9dc09f52e0dd896bd064a79346234b521f6b968ffdd8e58 \ + --hash=sha256:59c26c95975f26e662ca78fdf543d4eeaef70e533a672b4113dd888bd2423caa \ + --hash=sha256:5bce0dc147ca85caa5d33debc4f4d65e8e8b5c97c7f9f660f215fa74fc49a321 \ + --hash=sha256:5eafe2c065df5401ba06821b9a054d9cb2848867f3c59801b5d07a0be3a380ae \ + --hash=sha256:5ed3e046ea7b14938112ccd53d91c1539af3e6679b222f9469981e3dac7ba1ce \ + --hash=sha256:5fe9ce6c09668063b8447f85d43b8d1c4e5d3d7e92c63173e6180b2ac5d46dd8 \ + --hash=sha256:648056db9a9fa565d3fa851880f99f45e3f9a771dd3ff3bb0c048ea83fb28194 \ + --hash=sha256:69361bfdca5468c0488d7017b9b1e5ce769d40b46a9f4a2eed26b78619e9396c \ + --hash=sha256:6b0e029353361f1746bac2e4cc19b32f972ec03f0f943b390c4ab3371840aabf \ + --hash=sha256:6b88f9386ff1ad91ace19d2a1c0225896e28815ee09fc6a8932fded8cda97c3d \ + --hash=sha256:770d015888c2a598b377bd2f663adfd947d78c0124cfe7b959e1ef39f5b13869 \ + --hash=sha256:7943c414d3a8d9235f5f15c22ace69787c140c80b718dcd57caaade95f7cd93b \ + --hash=sha256:7cf5c9458e1e90e3c390c2639f1017a0379a99a94fdfad3a1fd966a2874bba52 \ + --hash=sha256:7f46acd6a194287b7e41e87957bfe2ad1ad88318d447caf5b090012f2c5bb528 \ + --hash=sha256:82e6aa28dd46374f72093eda8bcd142f7771ee1eb9d1e223ff0fa7177a96b4a5 \ + --hash=sha256:835a55b7ca49468aaaac0b217092dfdff370e6c215c9224c52f30daaa735c1c1 \ + --hash=sha256:84871a243359bb42c12728f04d181a389718710129b36b6aad0fc4655a7647d4 \ + --hash=sha256:8aacb477dc26797ee089721536a292a664846489c49d3ef9725f992449eda5a8 \ + --hash=sha256:8e2c45c208c62e955e8256949eb225bd8b66a4c9b6865729a786f2aa79b72e9d \ + --hash=sha256:90842933e5d1ff760fae6caca4b2b3edba53ba8f4b71e95dacf2818a2aca06f7 \ + --hash=sha256:938a9653e1e0c592053f815f7028e41a3062e902095e5a7dc84617c87267ebd5 \ + --hash=sha256:939677b61f9d72a4fa2a042a5eee2a99a24001a67c13da113b2e30396567db54 \ + --hash=sha256:9d3c9b50f19704552f23b4eaea1fc082fdd82c63429a6506446cbd8737823da3 \ + --hash=sha256:a6fe5571784af92b6bc2fda8d1925cccdf24642d49546d3144948a6a1ed58ca5 \ + --hash=sha256:a78ed8a53a1221393d9637c01870248a6f4ea5b214a59a92a36f18151739452c \ + --hash=sha256:ab40e6251c3873d86ea9b30a1ac6d7478c09277b32e14745d0d3c6e76e3c7e29 \ + --hash=sha256:abf151955990d23f84205286938796c55ff11bbfb4ccfada8c9c83ae6b3c89a3 \ + --hash=sha256:acef0899fea7492145d2bbaaaec7b345c87753168589cc7faf0afec9afe9b747 \ + --hash=sha256:b40670ec7e2156d8e57f70aec34a7216407848dfe6c693ef131ddf6e76feb672 \ + --hash=sha256:b791a3143681a520c0a17e26ae7465f1b6f99461a28019d1a2f425236e6eedb5 \ + --hash=sha256:b955ed993491f1a5da7f92e98d5dad3c1e14dc175f74517c4e610b1f2456fb11 \ + --hash=sha256:ba39e9c8627edc56544c8628cc180d88605df3892beeb2b94c9bc857774848ca \ + --hash=sha256:bca77a198bb6e69795ef2f09a5f4c12758487f83f33d63acde5f0d4919815768 \ + --hash=sha256:c3452ea726c76e92f3b9fae4b34a151981a9ec0a4847a627c43d71a15ac32aa6 \ + --hash=sha256:c46956ed82961e31557b6857a5ca153c67e5476972e5f7190015018760938da2 \ + --hash=sha256:c7c8b816c2b5af5c8a436df44ca08258fc1a13b449393a91484225fcb7545533 \ + --hash=sha256:cd73265a9e5ea618014802ab01babf1940cecb90c9762d8b9e7d2cc1e1969ec6 \ + --hash=sha256:dad46e6f620574b3b4801c68255492e0159d1712271cc99d8bdf35f2043ec266 \ + --hash=sha256:dc9b311743a78043b26ffaeeb9715dc360335e5517832f5a8e339f8a43581e4d \ + --hash=sha256:df822ee7feaaeffb99c1a9e5e608800bd8eda6e5f18f5cfb0dc7eeb2eaa6bbec \ + --hash=sha256:e083c285857b78ee21a96ba1eb1b5339733c3563f72980728ca2b08b53826ca5 \ + --hash=sha256:e5e46b578c0e9db71d04c4b506a2121c0cb371dd89af17a0586ff6769d4c58c1 \ + --hash=sha256:e99abf0bba688259a496f966211c49a514e65afa9b3073a1fcee08856e04425b \ + --hash=sha256:ee43080e75fc92bf36219926c8e6de497f9b247301bbf88c5c7593d931426679 \ + --hash=sha256:f033d80bc6283092613882dfe40419c6a6a1527e04fc69350e87a9df02bbc283 \ + --hash=sha256:f1088fa100bf46e7b398ffd9904f4808a0612e1d966b4aa43baa535d1b6341eb \ + --hash=sha256:f56455b0c2c7cc3b0c584815264461d07b177f903a04481dfc33e08a89f0c26b \ + --hash=sha256:f59dfe57bb1ec82ac0698ebfcdb7bcd0e99c255bd637ff613760d5f33e7c81b3 \ + --hash=sha256:f7217af2e14da0856e082e96ff637f14ae45c10a5714b63c77f26d8884cf1051 \ + --hash=sha256:f734e38fd8666f53da904c52a23ce517f1b07722118d750405af7e4123933511 \ + --hash=sha256:f95511dd5d0e05fd9728bac4096319f80615aaef4acbecb35a990afebe953b0e \ + --hash=sha256:fdd215b7b7fd4a53994f238d0f46b7ba4ac4c0adb12452beee724ddd0743ae5d \ + --hash=sha256:feeb18a801aacb098220e2c3eea59a512362eb408d4afd0c242044c33ad6d542 \ + --hash=sha256:ff30218887e62209942f91ac1be902cc80cddb86bf00fbc6783b7a43b2bea26f # via # -r requirements.in # aio-api-github @@ -811,81 +811,97 @@ monotonic==1.6 \ --hash=sha256:3a55207bcfed53ddd5c5bae174524062935efed17792e9de2ad0205ce9ad63f7 \ --hash=sha256:68687e19a14f11f26d140dd5c86f3dba4bf5df58003000ed467e0e2a69bca96c # via gsutil -multidict==6.0.4 \ - --hash=sha256:01a3a55bd90018c9c080fbb0b9f4891db37d148a0a18722b42f94694f8b6d4c9 \ - --hash=sha256:0b1a97283e0c85772d613878028fec909f003993e1007eafa715b24b377cb9b8 \ - --hash=sha256:0dfad7a5a1e39c53ed00d2dd0c2e36aed4650936dc18fd9a1826a5ae1cad6f03 \ - --hash=sha256:11bdf3f5e1518b24530b8241529d2050014c884cf18b6fc69c0c2b30ca248710 \ - --hash=sha256:1502e24330eb681bdaa3eb70d6358e818e8e8f908a22a1851dfd4e15bc2f8161 \ - --hash=sha256:16ab77bbeb596e14212e7bab8429f24c1579234a3a462105cda4a66904998664 \ - --hash=sha256:16d232d4e5396c2efbbf4f6d4df89bfa905eb0d4dc5b3549d872ab898451f569 \ - --hash=sha256:21a12c4eb6ddc9952c415f24eef97e3e55ba3af61f67c7bc388dcdec1404a067 \ - --hash=sha256:27c523fbfbdfd19c6867af7346332b62b586eed663887392cff78d614f9ec313 \ - --hash=sha256:281af09f488903fde97923c7744bb001a9b23b039a909460d0f14edc7bf59706 \ - --hash=sha256:33029f5734336aa0d4c0384525da0387ef89148dc7191aae00ca5fb23d7aafc2 \ - --hash=sha256:3601a3cece3819534b11d4efc1eb76047488fddd0c85a3948099d5da4d504636 \ - --hash=sha256:3666906492efb76453c0e7b97f2cf459b0682e7402c0489a95484965dbc1da49 \ - --hash=sha256:36c63aaa167f6c6b04ef2c85704e93af16c11d20de1d133e39de6a0e84582a93 \ - --hash=sha256:39ff62e7d0f26c248b15e364517a72932a611a9b75f35b45be078d81bdb86603 \ - --hash=sha256:43644e38f42e3af682690876cff722d301ac585c5b9e1eacc013b7a3f7b696a0 \ - --hash=sha256:4372381634485bec7e46718edc71528024fcdc6f835baefe517b34a33c731d60 \ - --hash=sha256:458f37be2d9e4c95e2d8866a851663cbc76e865b78395090786f6cd9b3bbf4f4 \ - --hash=sha256:45e1ecb0379bfaab5eef059f50115b54571acfbe422a14f668fc8c27ba410e7e \ - --hash=sha256:4b9d9e4e2b37daddb5c23ea33a3417901fa7c7b3dee2d855f63ee67a0b21e5b1 \ - --hash=sha256:4ceef517eca3e03c1cceb22030a3e39cb399ac86bff4e426d4fc6ae49052cc60 \ - --hash=sha256:4d1a3d7ef5e96b1c9e92f973e43aa5e5b96c659c9bc3124acbbd81b0b9c8a951 \ - --hash=sha256:4dcbb0906e38440fa3e325df2359ac6cb043df8e58c965bb45f4e406ecb162cc \ - --hash=sha256:509eac6cf09c794aa27bcacfd4d62c885cce62bef7b2c3e8b2e49d365b5003fe \ - --hash=sha256:52509b5be062d9eafc8170e53026fbc54cf3b32759a23d07fd935fb04fc22d95 \ - --hash=sha256:52f2dffc8acaba9a2f27174c41c9e57f60b907bb9f096b36b1a1f3be71c6284d \ - --hash=sha256:574b7eae1ab267e5f8285f0fe881f17efe4b98c39a40858247720935b893bba8 \ - --hash=sha256:5979b5632c3e3534e42ca6ff856bb24b2e3071b37861c2c727ce220d80eee9ed \ - --hash=sha256:59d43b61c59d82f2effb39a93c48b845efe23a3852d201ed2d24ba830d0b4cf2 \ - --hash=sha256:5a4dcf02b908c3b8b17a45fb0f15b695bf117a67b76b7ad18b73cf8e92608775 \ - --hash=sha256:5cad9430ab3e2e4fa4a2ef4450f548768400a2ac635841bc2a56a2052cdbeb87 \ - --hash=sha256:5fc1b16f586f049820c5c5b17bb4ee7583092fa0d1c4e28b5239181ff9532e0c \ - --hash=sha256:62501642008a8b9871ddfccbf83e4222cf8ac0d5aeedf73da36153ef2ec222d2 \ - --hash=sha256:64bdf1086b6043bf519869678f5f2757f473dee970d7abf6da91ec00acb9cb98 \ - --hash=sha256:64da238a09d6039e3bd39bb3aee9c21a5e34f28bfa5aa22518581f910ff94af3 \ - --hash=sha256:666daae833559deb2d609afa4490b85830ab0dfca811a98b70a205621a6109fe \ - --hash=sha256:67040058f37a2a51ed8ea8f6b0e6ee5bd78ca67f169ce6122f3e2ec80dfe9b78 \ - --hash=sha256:6748717bb10339c4760c1e63da040f5f29f5ed6e59d76daee30305894069a660 \ - --hash=sha256:6b181d8c23da913d4ff585afd1155a0e1194c0b50c54fcfe286f70cdaf2b7176 \ - --hash=sha256:6ed5f161328b7df384d71b07317f4d8656434e34591f20552c7bcef27b0ab88e \ - --hash=sha256:7582a1d1030e15422262de9f58711774e02fa80df0d1578995c76214f6954988 \ - --hash=sha256:7d18748f2d30f94f498e852c67d61261c643b349b9d2a581131725595c45ec6c \ - --hash=sha256:7d6ae9d593ef8641544d6263c7fa6408cc90370c8cb2bbb65f8d43e5b0351d9c \ - --hash=sha256:81a4f0b34bd92df3da93315c6a59034df95866014ac08535fc819f043bfd51f0 \ - --hash=sha256:8316a77808c501004802f9beebde51c9f857054a0c871bd6da8280e718444449 \ - --hash=sha256:853888594621e6604c978ce2a0444a1e6e70c8d253ab65ba11657659dcc9100f \ - --hash=sha256:99b76c052e9f1bc0721f7541e5e8c05db3941eb9ebe7b8553c625ef88d6eefde \ - --hash=sha256:a2e4369eb3d47d2034032a26c7a80fcb21a2cb22e1173d761a162f11e562caa5 \ - --hash=sha256:ab55edc2e84460694295f401215f4a58597f8f7c9466faec545093045476327d \ - --hash=sha256:af048912e045a2dc732847d33821a9d84ba553f5c5f028adbd364dd4765092ac \ - --hash=sha256:b1a2eeedcead3a41694130495593a559a668f382eee0727352b9a41e1c45759a \ - --hash=sha256:b1e8b901e607795ec06c9e42530788c45ac21ef3aaa11dbd0c69de543bfb79a9 \ - --hash=sha256:b41156839806aecb3641f3208c0dafd3ac7775b9c4c422d82ee2a45c34ba81ca \ - --hash=sha256:b692f419760c0e65d060959df05f2a531945af31fda0c8a3b3195d4efd06de11 \ - --hash=sha256:bc779e9e6f7fda81b3f9aa58e3a6091d49ad528b11ed19f6621408806204ad35 \ - --hash=sha256:bf6774e60d67a9efe02b3616fee22441d86fab4c6d335f9d2051d19d90a40063 \ - --hash=sha256:c048099e4c9e9d615545e2001d3d8a4380bd403e1a0578734e0d31703d1b0c0b \ - --hash=sha256:c5cb09abb18c1ea940fb99360ea0396f34d46566f157122c92dfa069d3e0e982 \ - --hash=sha256:cc8e1d0c705233c5dd0c5e6460fbad7827d5d36f310a0fadfd45cc3029762258 \ - --hash=sha256:d5e3fc56f88cc98ef8139255cf8cd63eb2c586531e43310ff859d6bb3a6b51f1 \ - --hash=sha256:d6aa0418fcc838522256761b3415822626f866758ee0bc6632c9486b179d0b52 \ - --hash=sha256:d6c254ba6e45d8e72739281ebc46ea5eb5f101234f3ce171f0e9f5cc86991480 \ - --hash=sha256:d6d635d5209b82a3492508cf5b365f3446afb65ae7ebd755e70e18f287b0adf7 \ - --hash=sha256:dcfe792765fab89c365123c81046ad4103fcabbc4f56d1c1997e6715e8015461 \ - --hash=sha256:ddd3915998d93fbcd2566ddf9cf62cdb35c9e093075f862935573d265cf8f65d \ - --hash=sha256:ddff9c4e225a63a5afab9dd15590432c22e8057e1a9a13d28ed128ecf047bbdc \ - --hash=sha256:e41b7e2b59679edfa309e8db64fdf22399eec4b0b24694e1b2104fb789207779 \ - --hash=sha256:e69924bfcdda39b722ef4d9aa762b2dd38e4632b3641b1d9a57ca9cd18f2f83a \ - --hash=sha256:ea20853c6dbbb53ed34cb4d080382169b6f4554d394015f1bef35e881bf83547 \ - --hash=sha256:ee2a1ece51b9b9e7752e742cfb661d2a29e7bcdba2d27e66e28a99f1890e4fa0 \ - --hash=sha256:eeb6dcc05e911516ae3d1f207d4b0520d07f54484c49dfc294d6e7d63b734171 \ - --hash=sha256:f70b98cd94886b49d91170ef23ec5c0e8ebb6f242d734ed7ed677b24d50c82cf \ - --hash=sha256:fc35cb4676846ef752816d5be2193a1e8367b4c1397b74a565a9d0389c433a1d \ - --hash=sha256:ff959bee35038c4624250473988b24f846cbeb2c6639de3602c073f10410ceba +multidict==6.0.5 \ + --hash=sha256:01265f5e40f5a17f8241d52656ed27192be03bfa8764d88e8220141d1e4b3556 \ + --hash=sha256:0275e35209c27a3f7951e1ce7aaf93ce0d163b28948444bec61dd7badc6d3f8c \ + --hash=sha256:04bde7a7b3de05732a4eb39c94574db1ec99abb56162d6c520ad26f83267de29 \ + --hash=sha256:04da1bb8c8dbadf2a18a452639771951c662c5ad03aefe4884775454be322c9b \ + --hash=sha256:09a892e4a9fb47331da06948690ae38eaa2426de97b4ccbfafbdcbe5c8f37ff8 \ + --hash=sha256:0d63c74e3d7ab26de115c49bffc92cc77ed23395303d496eae515d4204a625e7 \ + --hash=sha256:107c0cdefe028703fb5dafe640a409cb146d44a6ae201e55b35a4af8e95457dd \ + --hash=sha256:141b43360bfd3bdd75f15ed811850763555a251e38b2405967f8e25fb43f7d40 \ + --hash=sha256:14c2976aa9038c2629efa2c148022ed5eb4cb939e15ec7aace7ca932f48f9ba6 \ + --hash=sha256:19fe01cea168585ba0f678cad6f58133db2aa14eccaf22f88e4a6dccadfad8b3 \ + --hash=sha256:1d147090048129ce3c453f0292e7697d333db95e52616b3793922945804a433c \ + --hash=sha256:1d9ea7a7e779d7a3561aade7d596649fbecfa5c08a7674b11b423783217933f9 \ + --hash=sha256:215ed703caf15f578dca76ee6f6b21b7603791ae090fbf1ef9d865571039ade5 \ + --hash=sha256:21fd81c4ebdb4f214161be351eb5bcf385426bf023041da2fd9e60681f3cebae \ + --hash=sha256:220dd781e3f7af2c2c1053da9fa96d9cf3072ca58f057f4c5adaaa1cab8fc442 \ + --hash=sha256:228b644ae063c10e7f324ab1ab6b548bdf6f8b47f3ec234fef1093bc2735e5f9 \ + --hash=sha256:29bfeb0dff5cb5fdab2023a7a9947b3b4af63e9c47cae2a10ad58394b517fddc \ + --hash=sha256:2f4848aa3baa109e6ab81fe2006c77ed4d3cd1e0ac2c1fbddb7b1277c168788c \ + --hash=sha256:2faa5ae9376faba05f630d7e5e6be05be22913782b927b19d12b8145968a85ea \ + --hash=sha256:2ffc42c922dbfddb4a4c3b438eb056828719f07608af27d163191cb3e3aa6cc5 \ + --hash=sha256:37b15024f864916b4951adb95d3a80c9431299080341ab9544ed148091b53f50 \ + --hash=sha256:3cc2ad10255f903656017363cd59436f2111443a76f996584d1077e43ee51182 \ + --hash=sha256:3d25f19500588cbc47dc19081d78131c32637c25804df8414463ec908631e453 \ + --hash=sha256:403c0911cd5d5791605808b942c88a8155c2592e05332d2bf78f18697a5fa15e \ + --hash=sha256:411bf8515f3be9813d06004cac41ccf7d1cd46dfe233705933dd163b60e37600 \ + --hash=sha256:425bf820055005bfc8aa9a0b99ccb52cc2f4070153e34b701acc98d201693733 \ + --hash=sha256:435a0984199d81ca178b9ae2c26ec3d49692d20ee29bc4c11a2a8d4514c67eda \ + --hash=sha256:4a6a4f196f08c58c59e0b8ef8ec441d12aee4125a7d4f4fef000ccb22f8d7241 \ + --hash=sha256:4cc0ef8b962ac7a5e62b9e826bd0cd5040e7d401bc45a6835910ed699037a461 \ + --hash=sha256:51d035609b86722963404f711db441cf7134f1889107fb171a970c9701f92e1e \ + --hash=sha256:53689bb4e102200a4fafa9de9c7c3c212ab40a7ab2c8e474491914d2305f187e \ + --hash=sha256:55205d03e8a598cfc688c71ca8ea5f66447164efff8869517f175ea632c7cb7b \ + --hash=sha256:5c0631926c4f58e9a5ccce555ad7747d9a9f8b10619621f22f9635f069f6233e \ + --hash=sha256:5cb241881eefd96b46f89b1a056187ea8e9ba14ab88ba632e68d7a2ecb7aadf7 \ + --hash=sha256:60d698e8179a42ec85172d12f50b1668254628425a6bd611aba022257cac1386 \ + --hash=sha256:612d1156111ae11d14afaf3a0669ebf6c170dbb735e510a7438ffe2369a847fd \ + --hash=sha256:6214c5a5571802c33f80e6c84713b2c79e024995b9c5897f794b43e714daeec9 \ + --hash=sha256:6939c95381e003f54cd4c5516740faba40cf5ad3eeff460c3ad1d3e0ea2549bf \ + --hash=sha256:69db76c09796b313331bb7048229e3bee7928eb62bab5e071e9f7fcc4879caee \ + --hash=sha256:6bf7a982604375a8d49b6cc1b781c1747f243d91b81035a9b43a2126c04766f5 \ + --hash=sha256:766c8f7511df26d9f11cd3a8be623e59cca73d44643abab3f8c8c07620524e4a \ + --hash=sha256:76c0de87358b192de7ea9649beb392f107dcad9ad27276324c24c91774ca5271 \ + --hash=sha256:76f067f5121dcecf0d63a67f29080b26c43c71a98b10c701b0677e4a065fbd54 \ + --hash=sha256:7901c05ead4b3fb75113fb1dd33eb1253c6d3ee37ce93305acd9d38e0b5f21a4 \ + --hash=sha256:79660376075cfd4b2c80f295528aa6beb2058fd289f4c9252f986751a4cd0496 \ + --hash=sha256:79a6d2ba910adb2cbafc95dad936f8b9386e77c84c35bc0add315b856d7c3abb \ + --hash=sha256:7afcdd1fc07befad18ec4523a782cde4e93e0a2bf71239894b8d61ee578c1319 \ + --hash=sha256:7be7047bd08accdb7487737631d25735c9a04327911de89ff1b26b81745bd4e3 \ + --hash=sha256:7c6390cf87ff6234643428991b7359b5f59cc15155695deb4eda5c777d2b880f \ + --hash=sha256:7df704ca8cf4a073334e0427ae2345323613e4df18cc224f647f251e5e75a527 \ + --hash=sha256:85f67aed7bb647f93e7520633d8f51d3cbc6ab96957c71272b286b2f30dc70ed \ + --hash=sha256:896ebdcf62683551312c30e20614305f53125750803b614e9e6ce74a96232604 \ + --hash=sha256:92d16a3e275e38293623ebf639c471d3e03bb20b8ebb845237e0d3664914caef \ + --hash=sha256:99f60d34c048c5c2fabc766108c103612344c46e35d4ed9ae0673d33c8fb26e8 \ + --hash=sha256:9fe7b0653ba3d9d65cbe7698cca585bf0f8c83dbbcc710db9c90f478e175f2d5 \ + --hash=sha256:a3145cb08d8625b2d3fee1b2d596a8766352979c9bffe5d7833e0503d0f0b5e5 \ + --hash=sha256:aeaf541ddbad8311a87dd695ed9642401131ea39ad7bc8cf3ef3967fd093b626 \ + --hash=sha256:b55358304d7a73d7bdf5de62494aaf70bd33015831ffd98bc498b433dfe5b10c \ + --hash=sha256:b82cc8ace10ab5bd93235dfaab2021c70637005e1ac787031f4d1da63d493c1d \ + --hash=sha256:c0868d64af83169e4d4152ec612637a543f7a336e4a307b119e98042e852ad9c \ + --hash=sha256:c1c1496e73051918fcd4f58ff2e0f2f3066d1c76a0c6aeffd9b45d53243702cc \ + --hash=sha256:c9bf56195c6bbd293340ea82eafd0071cb3d450c703d2c93afb89f93b8386ccc \ + --hash=sha256:cbebcd5bcaf1eaf302617c114aa67569dd3f090dd0ce8ba9e35e9985b41ac35b \ + --hash=sha256:cd6c8fca38178e12c00418de737aef1261576bd1b6e8c6134d3e729a4e858b38 \ + --hash=sha256:ceb3b7e6a0135e092de86110c5a74e46bda4bd4fbfeeb3a3bcec79c0f861e450 \ + --hash=sha256:cf590b134eb70629e350691ecca88eac3e3b8b3c86992042fb82e3cb1830d5e1 \ + --hash=sha256:d3eb1ceec286eba8220c26f3b0096cf189aea7057b6e7b7a2e60ed36b373b77f \ + --hash=sha256:d65f25da8e248202bd47445cec78e0025c0fe7582b23ec69c3b27a640dd7a8e3 \ + --hash=sha256:d6f6d4f185481c9669b9447bf9d9cf3b95a0e9df9d169bbc17e363b7d5487755 \ + --hash=sha256:d84a5c3a5f7ce6db1f999fb9438f686bc2e09d38143f2d93d8406ed2dd6b9226 \ + --hash=sha256:d946b0a9eb8aaa590df1fe082cee553ceab173e6cb5b03239716338629c50c7a \ + --hash=sha256:dce1c6912ab9ff5f179eaf6efe7365c1f425ed690b03341911bf4939ef2f3046 \ + --hash=sha256:de170c7b4fe6859beb8926e84f7d7d6c693dfe8e27372ce3b76f01c46e489fcf \ + --hash=sha256:e02021f87a5b6932fa6ce916ca004c4d441509d33bbdbeca70d05dff5e9d2479 \ + --hash=sha256:e030047e85cbcedbfc073f71836d62dd5dadfbe7531cae27789ff66bc551bd5e \ + --hash=sha256:e0e79d91e71b9867c73323a3444724d496c037e578a0e1755ae159ba14f4f3d1 \ + --hash=sha256:e4428b29611e989719874670fd152b6625500ad6c686d464e99f5aaeeaca175a \ + --hash=sha256:e4972624066095e52b569e02b5ca97dbd7a7ddd4294bf4e7247d52635630dd83 \ + --hash=sha256:e7be68734bd8c9a513f2b0cfd508802d6609da068f40dc57d4e3494cefc92929 \ + --hash=sha256:e8e94e6912639a02ce173341ff62cc1201232ab86b8a8fcc05572741a5dc7d93 \ + --hash=sha256:ea1456df2a27c73ce51120fa2f519f1bea2f4a03a917f4a43c8707cf4cbbae1a \ + --hash=sha256:ebd8d160f91a764652d3e51ce0d2956b38efe37c9231cd82cfc0bed2e40b581c \ + --hash=sha256:eca2e9d0cc5a889850e9bbd68e98314ada174ff6ccd1129500103df7a94a7a44 \ + --hash=sha256:edd08e6f2f1a390bf137080507e44ccc086353c8e98c657e666c017718561b89 \ + --hash=sha256:f285e862d2f153a70586579c15c44656f888806ed0e5b56b64489afe4a2dbfba \ + --hash=sha256:f2a1dee728b52b33eebff5072817176c172050d44d67befd681609b4746e1c2e \ + --hash=sha256:f7e301075edaf50500f0b341543c41194d8df3ae5caf4702f2095f3ca73dd8da \ + --hash=sha256:fb616be3538599e797a2017cccca78e354c767165e8858ab5116813146041a24 \ + --hash=sha256:fce28b3c8a81b6b36dfac9feb1de115bab619b3c13905b419ec71d03a3fc1423 \ + --hash=sha256:fe5d7785250541f7f5019ab9cba2c71169dc7d74d0f45253f8313f436458a4ef # via # -r requirements.in # aiohttp @@ -896,57 +912,57 @@ oauth2client==4.1.3 \ # via # gcs-oauth2-boto-plugin # google-apitools -orjson==3.9.10 \ - --hash=sha256:06ad5543217e0e46fd7ab7ea45d506c76f878b87b1b4e369006bdb01acc05a83 \ - --hash=sha256:0a73160e823151f33cdc05fe2cea557c5ef12fdf276ce29bb4f1c571c8368a60 \ - --hash=sha256:1234dc92d011d3554d929b6cf058ac4a24d188d97be5e04355f1b9223e98bbe9 \ - --hash=sha256:1d0dc4310da8b5f6415949bd5ef937e60aeb0eb6b16f95041b5e43e6200821fb \ - --hash=sha256:2a11b4b1a8415f105d989876a19b173f6cdc89ca13855ccc67c18efbd7cbd1f8 \ - --hash=sha256:2e2ecd1d349e62e3960695214f40939bbfdcaeaaa62ccc638f8e651cf0970e5f \ - --hash=sha256:3a2ce5ea4f71681623f04e2b7dadede3c7435dfb5e5e2d1d0ec25b35530e277b \ - --hash=sha256:3e892621434392199efb54e69edfff9f699f6cc36dd9553c5bf796058b14b20d \ - --hash=sha256:3fb205ab52a2e30354640780ce4587157a9563a68c9beaf52153e1cea9aa0921 \ - --hash=sha256:4689270c35d4bb3102e103ac43c3f0b76b169760aff8bcf2d401a3e0e58cdb7f \ - --hash=sha256:49f8ad582da6e8d2cf663c4ba5bf9f83cc052570a3a767487fec6af839b0e777 \ - --hash=sha256:4bd176f528a8151a6efc5359b853ba3cc0e82d4cd1fab9c1300c5d957dc8f48c \ - --hash=sha256:4cf7837c3b11a2dfb589f8530b3cff2bd0307ace4c301e8997e95c7468c1378e \ - --hash=sha256:4fd72fab7bddce46c6826994ce1e7de145ae1e9e106ebb8eb9ce1393ca01444d \ - --hash=sha256:5148bab4d71f58948c7c39d12b14a9005b6ab35a0bdf317a8ade9a9e4d9d0bd5 \ - --hash=sha256:5869e8e130e99687d9e4be835116c4ebd83ca92e52e55810962446d841aba8de \ - --hash=sha256:602a8001bdf60e1a7d544be29c82560a7b49319a0b31d62586548835bbe2c862 \ - --hash=sha256:61804231099214e2f84998316f3238c4c2c4aaec302df12b21a64d72e2a135c7 \ - --hash=sha256:666c6fdcaac1f13eb982b649e1c311c08d7097cbda24f32612dae43648d8db8d \ - --hash=sha256:674eb520f02422546c40401f4efaf8207b5e29e420c17051cddf6c02783ff5ca \ - --hash=sha256:7ec960b1b942ee3c69323b8721df2a3ce28ff40e7ca47873ae35bfafeb4555ca \ - --hash=sha256:7f433be3b3f4c66016d5a20e5b4444ef833a1f802ced13a2d852c637f69729c1 \ - --hash=sha256:7f8fb7f5ecf4f6355683ac6881fd64b5bb2b8a60e3ccde6ff799e48791d8f864 \ - --hash=sha256:81a3a3a72c9811b56adf8bcc829b010163bb2fc308877e50e9910c9357e78521 \ - --hash=sha256:858379cbb08d84fe7583231077d9a36a1a20eb72f8c9076a45df8b083724ad1d \ - --hash=sha256:8b9ba0ccd5a7f4219e67fbbe25e6b4a46ceef783c42af7dbc1da548eb28b6531 \ - --hash=sha256:92af0d00091e744587221e79f68d617b432425a7e59328ca4c496f774a356071 \ - --hash=sha256:9ebbdbd6a046c304b1845e96fbcc5559cd296b4dfd3ad2509e33c4d9ce07d6a1 \ - --hash=sha256:9edd2856611e5050004f4722922b7b1cd6268da34102667bd49d2a2b18bafb81 \ - --hash=sha256:a353bf1f565ed27ba71a419b2cd3db9d6151da426b61b289b6ba1422a702e643 \ - --hash=sha256:b5b7d4a44cc0e6ff98da5d56cde794385bdd212a86563ac321ca64d7f80c80d1 \ - --hash=sha256:b90f340cb6397ec7a854157fac03f0c82b744abdd1c0941a024c3c29d1340aff \ - --hash=sha256:c18a4da2f50050a03d1da5317388ef84a16013302a5281d6f64e4a3f406aabc4 \ - --hash=sha256:c338ed69ad0b8f8f8920c13f529889fe0771abbb46550013e3c3d01e5174deef \ - --hash=sha256:c5a02360e73e7208a872bf65a7554c9f15df5fe063dc047f79738998b0506a14 \ - --hash=sha256:c62b6fa2961a1dcc51ebe88771be5319a93fd89bd247c9ddf732bc250507bc2b \ - --hash=sha256:c812312847867b6335cfb264772f2a7e85b3b502d3a6b0586aa35e1858528ab1 \ - --hash=sha256:c943b35ecdf7123b2d81d225397efddf0bce2e81db2f3ae633ead38e85cd5ade \ - --hash=sha256:ce0a29c28dfb8eccd0f16219360530bc3cfdf6bf70ca384dacd36e6c650ef8e8 \ - --hash=sha256:cf80b550092cc480a0cbd0750e8189247ff45457e5a023305f7ef1bcec811616 \ - --hash=sha256:cff7570d492bcf4b64cc862a6e2fb77edd5e5748ad715f487628f102815165e9 \ - --hash=sha256:d2c1e559d96a7f94a4f581e2a32d6d610df5840881a8cba8f25e446f4d792df3 \ - --hash=sha256:deeb3922a7a804755bbe6b5be9b312e746137a03600f488290318936c1a2d4dc \ - --hash=sha256:e28a50b5be854e18d54f75ef1bb13e1abf4bc650ab9d635e4258c58e71eb6ad5 \ - --hash=sha256:e99c625b8c95d7741fe057585176b1b8783d46ed4b8932cf98ee145c4facf499 \ - --hash=sha256:ec6f18f96b47299c11203edfbdc34e1b69085070d9a3d1f302810cc23ad36bf3 \ - --hash=sha256:ed8bc367f725dfc5cabeed1ae079d00369900231fbb5a5280cf0736c30e2adf7 \ - --hash=sha256:ee5926746232f627a3be1cc175b2cfad24d0170d520361f4ce3fa2fd83f09e1d \ - --hash=sha256:f295efcd47b6124b01255d1491f9e46f17ef40d3d7eabf7364099e463fb45f0f \ - --hash=sha256:fb0b361d73f6b8eeceba47cd37070b5e6c9de5beaeaa63a1cb35c7e1a73ef088 +orjson==3.9.13 \ + --hash=sha256:031df1026c7ea8303332d78711f180231e3ae8b564271fb748a03926587c5546 \ + --hash=sha256:0d3ba9d88e20765335260d7b25547d7c571eee2b698200f97afa7d8c7cd668fc \ + --hash=sha256:0d691c44604941945b00e0a13b19a7d9c1a19511abadf0080f373e98fdeb6b31 \ + --hash=sha256:0fd9a2101d04e85086ea6198786a3f016e45475f800712e6833e14bf9ce2832f \ + --hash=sha256:16946d095212a3dec552572c5d9bca7afa40f3116ad49695a397be07d529f1fa \ + --hash=sha256:1ab9dbdec3f13f3ea6f937564ce21651844cfbf2725099f2f490426acf683c23 \ + --hash=sha256:23f21faf072ed3b60b5954686f98157e073f6a8068eaa58dbde83e87212eda84 \ + --hash=sha256:266e55c83f81248f63cc93d11c5e3a53df49a5d2598fa9e9db5f99837a802d5d \ + --hash=sha256:2cc03a35bfc71c8ebf96ce49b82c2a7be6af4b3cd3ac34166fdb42ac510bbfff \ + --hash=sha256:2f37f0cdd026ef777a4336e599d8194c8357fc14760c2a5ddcfdf1965d45504b \ + --hash=sha256:31372ba3a9fe8ad118e7d22fba46bbc18e89039e3bfa89db7bc8c18ee722dca8 \ + --hash=sha256:31fb66b41fb2c4c817d9610f0bc7d31345728d7b5295ac78b63603407432a2b2 \ + --hash=sha256:3869d65561f10071d3e7f35ae58fd377056f67d7aaed5222f318390c3ad30339 \ + --hash=sha256:3deadd8dc0e9ff844b5b656fa30a48dbee1c3b332d8278302dd9637f6b09f627 \ + --hash=sha256:43fd6036b16bb6742d03dae62f7bdf8214d06dea47e4353cde7e2bd1358d186f \ + --hash=sha256:446d9ad04204e79229ae19502daeea56479e55cbc32634655d886f5a39e91b44 \ + --hash=sha256:4584e8eb727bc431baaf1bf97e35a1d8a0109c924ec847395673dfd5f4ef6d6f \ + --hash=sha256:49b7e3fe861cb246361825d1a238f2584ed8ea21e714bf6bb17cebb86772e61c \ + --hash=sha256:5b98cd948372f0eb219bc309dee4633db1278687161e3280d9e693b6076951d2 \ + --hash=sha256:5ef58869f3399acbbe013518d8b374ee9558659eef14bca0984f67cb1fbd3c37 \ + --hash=sha256:60da7316131185d0110a1848e9ad15311e6c8938ee0b5be8cbd7261e1d80ee8f \ + --hash=sha256:62e9a99879c4d5a04926ac2518a992134bfa00d546ea5a4cae4b9be454d35a22 \ + --hash=sha256:63ef57a53bfc2091a7cd50a640d9ae866bd7d92a5225a1bab6baa60ef62583f2 \ + --hash=sha256:6e47153db080f5e87e8ba638f1a8b18995eede6b0abb93964d58cf11bcea362f \ + --hash=sha256:730385fdb99a21fce9bb84bb7fcbda72c88626facd74956bda712834b480729d \ + --hash=sha256:7ccd5bd222e5041069ad9d9868ab59e6dbc53ecde8d8c82b919954fbba43b46b \ + --hash=sha256:7e8e4a571d958910272af8d53a9cbe6599f9f5fd496a1bc51211183bb2072cbd \ + --hash=sha256:811ac076855e33e931549340288e0761873baf29276ad00f221709933c644330 \ + --hash=sha256:828c502bb261588f7de897e06cb23c4b122997cb039d2014cb78e7dabe92ef0c \ + --hash=sha256:838b898e8c1f26eb6b8d81b180981273f6f5110c76c22c384979aca854194f1b \ + --hash=sha256:860d0f5b42d0c0afd73fa4177709f6e1b966ba691fcd72175affa902052a81d6 \ + --hash=sha256:8a730bf07feacb0863974e67b206b7c503a62199de1cece2eb0d4c233ec29c11 \ + --hash=sha256:9156b96afa38db71344522f5517077eaedf62fcd2c9148392ff93d801128809c \ + --hash=sha256:9171e8e1a1f221953e38e84ae0abffe8759002fd8968106ee379febbb5358b33 \ + --hash=sha256:978117122ca4cc59b28af5322253017f6c5fc03dbdda78c7f4b94ae984c8dd43 \ + --hash=sha256:9b1b5adc5adf596c59dca57156b71ad301d73956f5bab4039b0e34dbf50b9fa0 \ + --hash=sha256:9bcf56efdb83244cde070e82a69c0f03c47c235f0a5cb6c81d9da23af7fbaae4 \ + --hash=sha256:a8c83718346de08d68b3cb1105c5d91e5fc39885d8610fdda16613d4e3941459 \ + --hash=sha256:ae77275a28667d9c82d4522b681504642055efa0368d73108511647c6499b31c \ + --hash=sha256:b57c0954a9fdd2b05b9cec0f5a12a0bdce5bf021a5b3b09323041613972481ab \ + --hash=sha256:b812417199eeb169c25f67815cfb66fd8de7ff098bf57d065e8c1943a7ba5c8f \ + --hash=sha256:cfad553a36548262e7da0f3a7464270e13900b898800fb571a5d4b298c3f8356 \ + --hash=sha256:d3222db9df629ef3c3673124f2e05fb72bc4a320c117e953fec0d69dde82e36d \ + --hash=sha256:d714595d81efab11b42bccd119977d94b25d12d3a806851ff6bfd286a4bce960 \ + --hash=sha256:d92a3e835a5100f1d5b566fff79217eab92223ca31900dba733902a182a35ab0 \ + --hash=sha256:ddc089315d030c54f0f03fb38286e2667c05009a78d659f108a8efcfbdf2e585 \ + --hash=sha256:e3b0c4da61f39899561e08e571f54472a09fa71717d9797928af558175ae5243 \ + --hash=sha256:eaaf80957c38e9d3f796f355a80fad945e72cd745e6b64c210e635b7043b673e \ + --hash=sha256:fa6b67f8bef277c2a4aadd548d58796854e7d760964126c3209b19bccc6a74f1 \ + --hash=sha256:fc6bc65b0cf524ee042e0bc2912b9206ef242edfba7426cf95763e4af01f527a # via # -r requirements.in # envoy-base-utils @@ -1022,9 +1038,9 @@ pyflakes==3.2.0 \ --hash=sha256:1c61603ff154621fb2a9172037d84dca3500def8c8b630657d1701f026f8af3f \ --hash=sha256:84b5be138a2dfbb40689ca07e2152deb896a65c3a3e24c251c5c62489568074a # via flake8 -pygithub==2.1.1 \ - --hash=sha256:4b528d5d6f35e991ea5fd3f942f58748f24938805cb7fcf24486546637917337 \ - --hash=sha256:ecf12c2809c44147bce63b047b3d2e9dac8a41b63e90fcb263c703f64936b97c +pygithub==2.2.0 \ + --hash=sha256:41042ea53e4c372219db708c38d2ca1fd4fadab75475bac27d89d339596cfad1 \ + --hash=sha256:e39be7c4dc39418bdd6e3ecab5931c636170b8b21b4d26f9ecf7e6102a3b51c3 # via -r requirements.in pygments==2.17.2 \ --hash=sha256:b27c2826c47d0f3219f29554824c30c5e8945175d888647acd804ddd04af846c \ @@ -1088,9 +1104,7 @@ pyreadline==2.1 \ python-dateutil==2.8.2 \ --hash=sha256:0123cacc1627ae19ddf3c27a5de5bd67ee4586fbdd6440d9748f8abb483d3e86 \ --hash=sha256:961d03dc3453ebbc59dbdea9e4e11c5651520a876d0f4db161e8674aae935da9 - # via - # icalendar - # pygithub + # via icalendar python-gnupg==0.5.2 \ --hash=sha256:01d8013931c9fa3f45824bbea7054c03d6e11f258a72e7e086e168dbcb91854c \ --hash=sha256:72ce142af6da7f07e433fef148b445fb3e07854acd2f88739008838745c0e9f5 @@ -1216,14 +1230,9 @@ sphinx==7.1.2 \ # envoy-docs-sphinx-runner # sphinx-copybutton # sphinx-rtd-theme - # sphinxcontrib-applehelp - # sphinxcontrib-devhelp # sphinxcontrib-googleanalytics - # sphinxcontrib-htmlhelp # sphinxcontrib-httpdomain # sphinxcontrib-jquery - # sphinxcontrib-qthelp - # sphinxcontrib-serializinghtml # sphinxext-rediraffe sphinx-copybutton==0.5.2 \ --hash=sha256:4cf17c82fb9646d1bc9ca92ac280813a3b605d8c421225fd9913154103ee1fbd \ @@ -1233,22 +1242,28 @@ sphinx-rtd-theme==2.0.0 \ --hash=sha256:bd5d7b80622406762073a04ef8fadc5f9151261563d47027de09910ce03afe6b \ --hash=sha256:ec93d0856dc280cf3aee9a4c9807c60e027c7f7b461b77aeffed682e68f0e586 # via envoy-docs-sphinx-runner -sphinxcontrib-applehelp==1.0.7 \ - --hash=sha256:094c4d56209d1734e7d252f6e0b3ccc090bd52ee56807a5d9315b19c122ab15d \ - --hash=sha256:39fdc8d762d33b01a7d8f026a3b7d71563ea3b72787d5f00ad8465bd9d6dfbfa - # via sphinx -sphinxcontrib-devhelp==1.0.5 \ - --hash=sha256:63b41e0d38207ca40ebbeabcf4d8e51f76c03e78cd61abe118cf4435c73d4212 \ - --hash=sha256:fe8009aed765188f08fcaadbb3ea0d90ce8ae2d76710b7e29ea7d047177dae2f - # via sphinx +sphinxcontrib-applehelp==1.0.8 \ + --hash=sha256:c40a4f96f3776c4393d933412053962fac2b84f4c99a7982ba42e09576a70619 \ + --hash=sha256:cb61eb0ec1b61f349e5cc36b2028e9e7ca765be05e49641c97241274753067b4 + # via + # -r requirements.in + # sphinx +sphinxcontrib-devhelp==1.0.6 \ + --hash=sha256:6485d09629944511c893fa11355bda18b742b83a2b181f9a009f7e500595c90f \ + --hash=sha256:9893fd3f90506bc4b97bdb977ceb8fbd823989f4316b28c3841ec128544372d3 + # via + # -r requirements.in + # sphinx sphinxcontrib-googleanalytics==0.4 \ --hash=sha256:4b19c1f0fce5df6c7da5633201b64a9e5b0cb3210a14fdb4134942ceee8c5d12 \ --hash=sha256:a6574983f9a58e5864ec10d34dc99914c4d647108b22c9249c8f0038b0cb18b3 # via -r requirements.in -sphinxcontrib-htmlhelp==2.0.4 \ - --hash=sha256:6c26a118a05b76000738429b724a0568dbde5b72391a688577da08f11891092a \ - --hash=sha256:8001661c077a73c29beaf4a79968d0726103c5605e27db92b9ebed8bab1359e9 - # via sphinx +sphinxcontrib-htmlhelp==2.0.5 \ + --hash=sha256:0dc87637d5de53dd5eec3a6a01753b1ccf99494bd756aafecd74b4fa9e729015 \ + --hash=sha256:393f04f112b4d2f53d93448d4bce35842f62b307ccdc549ec1585e950bc35e04 + # via + # -r requirements.in + # sphinx sphinxcontrib-httpdomain==1.8.1 \ --hash=sha256:21eefe1270e4d9de8d717cc89ee92cc4871b8736774393bafc5e38a6bb77b1d5 \ --hash=sha256:6c2dfe6ca282d75f66df333869bb0ce7331c01b475db6809ff9d107b7cdfe04b @@ -1263,14 +1278,17 @@ sphinxcontrib-jsmath==1.0.1 \ --hash=sha256:2ec2eaebfb78f3f2078e73666b1415417a116cc848b72e5172e596c871103178 \ --hash=sha256:a9925e4a4587247ed2191a22df5f6970656cb8ca2bd6284309578f2153e0c4b8 # via sphinx -sphinxcontrib-qthelp==1.0.6 \ - --hash=sha256:62b9d1a186ab7f5ee3356d906f648cacb7a6bdb94d201ee7adf26db55092982d \ - --hash=sha256:bf76886ee7470b934e363da7a954ea2825650013d367728588732c7350f49ea4 - # via sphinx -sphinxcontrib-serializinghtml==1.1.9 \ - --hash=sha256:0c64ff898339e1fac29abd2bf5f11078f3ec413cfe9c046d3120d7ca65530b54 \ - --hash=sha256:9b36e503703ff04f20e9675771df105e58aa029cfcbc23b8ed716019b7416ae1 +sphinxcontrib-qthelp==1.0.7 \ + --hash=sha256:053dedc38823a80a7209a80860b16b722e9e0209e32fea98c90e4e6624588ed6 \ + --hash=sha256:e2ae3b5c492d58fcbd73281fbd27e34b8393ec34a073c792642cd8e529288182 # via + # -r requirements.in + # sphinx +sphinxcontrib-serializinghtml==1.1.10 \ + --hash=sha256:326369b8df80a7d2d8d7f99aa5ac577f51ea51556ed974e7716cfd4fca3f6cb7 \ + --hash=sha256:93f3f5dc458b91b192fe10c397e324f262cf163d79f3282c158e8436a2c4511f + # via + # -r requirements.in # envoy-docs-sphinx-runner # sphinx sphinxext-rediraffe==0.2.7 \ diff --git a/tools/code_format/check_format.py b/tools/code_format/check_format.py index 916e4e8f6db65..368478ac2c347 100755 --- a/tools/code_format/check_format.py +++ b/tools/code_format/check_format.py @@ -393,11 +393,19 @@ def allow_listed_for_raw_try(self, file_path): return file_path in self.config.paths["raw_try"]["include"] def deny_listed_for_exceptions(self, file_path): - # Returns true when it is a non test header file or the file_path is in DENYLIST or - # it is under tools/testdata subdirectory. - return (file_path.endswith('.h') and not file_path.startswith("./test/") and not file_path in self.config.paths["exception"]["include"]) \ - or (file_path.endswith('.cc') and file_path.startswith("./source/") and not file_path.startswith("./source/extensions/") and not file_path in self.config.paths["exception"]["include"]) \ - or self.is_in_subdir(file_path, 'tools/testdata') + # Returns if this file is deny listed for exceptions. + # Header files are strongly discouraged from throwing exceptions, both for + # core and exception code. Source files are also discouraged but + # extensions source files are currently exempt from checks as many factory creation + # calls do not yet support StatusOr. + return (( + file_path.endswith('.h') and file_path.startswith("./source/") + and not file_path.startswith("./source/extensions/") + and not file_path in self.config.paths["exception"]["include"]) or ( + file_path.endswith('.cc') and file_path.startswith("./source/") + and not file_path.startswith("./source/extensions/") + and not file_path in self.config.paths["exception"]["include"]) + or self.is_in_subdir(file_path, 'tools/testdata')) def allow_listed_for_build_urls(self, file_path): return file_path in self.config.paths["build_urls"]["include"] @@ -785,14 +793,19 @@ def check_source_line(self, line, file_path, report_error): "Don't call memcpy() directly; use safeMemcpy, safeMemcpyUnsafeSrc, safeMemcpyUnsafeDst or MemBlockBuilder instead." ) - if self.deny_listed_for_exceptions(file_path): + def has_non_comment_throw(line): # Skpping cases where 'throw' is a substring of a symbol like in "foothrowBar". if "throw" in line.split(): comment_match = self.config.re["comment"].search(line) if comment_match is None or comment_match.start(0) > line.find("throw"): - report_error( - "Don't introduce throws into exception-free files, use error " - + "statuses instead.") + return True + return False + + if self.deny_listed_for_exceptions(file_path): + if has_non_comment_throw(line) or "THROW" in line or "throwExceptionOrPanic" in line: + report_error( + "Don't introduce throws into exception-free files, use error " + "statuses instead.") def check_build_line(self, line, file_path, report_error): if "@bazel_tools" in line and not (self.is_starlark_file(file_path) diff --git a/tools/code_format/config.yaml b/tools/code_format/config.yaml index 576d5d121c311..cd089687dadd4 100644 --- a/tools/code_format/config.yaml +++ b/tools/code_format/config.yaml @@ -109,7 +109,6 @@ paths: - source/common/network/address_impl.cc - source/common/network/utility.cc - source/common/network/dns_resolver/dns_factory_util.cc - - source/common/network/socket_impl.cc - source/common/ssl/tls_certificate_config_impl.cc - source/common/formatter/http_specific_formatter.cc - source/common/formatter/stream_info_formatter.h @@ -128,6 +127,7 @@ paths: - source/common/protobuf/visitor.cc - source/common/protobuf/utility.cc - source/common/protobuf/message_validator_impl.cc + - source/common/quic/quic_server_transport_socket_factory.cc - source/common/access_log/access_log_manager_impl.cc - source/common/secret/secret_manager_impl.cc - source/common/grpc/async_client_manager_impl.cc @@ -136,7 +136,6 @@ paths: - source/common/config/subscription_factory_impl.cc - source/common/config/xds_resource.cc - source/common/config/datasource.cc - - source/common/config/utility.cc - source/common/runtime/runtime_impl.cc - source/common/filter/config_discovery_impl.cc - source/common/json/json_internal.cc @@ -144,7 +143,6 @@ paths: - source/common/router/config_impl.cc - source/common/router/scoped_config_impl.cc - source/common/router/router_ratelimit.cc - - source/common/router/vhds.cc - source/common/router/header_parser.cc - source/common/filesystem/inotify/watcher_impl.cc - source/common/filesystem/posix/directory_iterator_impl.cc @@ -163,7 +161,12 @@ paths: - source/server/hot_restarting_base.cc - source/server/hot_restart_impl.cc - source/server/ssl_context_manager.cc - - source/server/configuration_impl.cc + - source/server/config_validation/cluster_manager.cc + - source/common/upstream/health_discovery_service.cc + - source/common/secret/sds_api.h + - source/common/secret/sds_api.cc + - source/common/router/router.cc + - source/common/config/config_provider_impl.h # Only one C++ file should instantiate grpc_init grpc_init: diff --git a/tools/h3_request/h3_request.py b/tools/h3_request/h3_request.py index 17a2209aa969c..3fcf5013adb24 100644 --- a/tools/h3_request/h3_request.py +++ b/tools/h3_request/h3_request.py @@ -92,10 +92,13 @@ async def request( ], end_stream=not post_stdin, ) + self.transmit() if post_stdin: async for data in _stream_stdin_generator(): self._http.send_data(stream_id=stream_id, data=data, end_stream=False) + self.transmit() self._http.send_data(stream_id=stream_id, data=b'', end_stream=True) + self.transmit() await future diff --git a/tools/spelling/spelling_dictionary.txt b/tools/spelling/spelling_dictionary.txt index d7f46a9d8c083..9de34d2bdb5dc 100644 --- a/tools/spelling/spelling_dictionary.txt +++ b/tools/spelling/spelling_dictionary.txt @@ -747,6 +747,7 @@ exe execlp exprfor expectable +extensibility extrahelp faceplant facto