mirror of
https://github.com/spring-cloud/spring-cloud-netflix.git
synced 2026-09-18 08:09:07 +00:00
Compare commits
2
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
dedd1f471e | ||
|
|
0dadc2502e |
@@ -17,7 +17,7 @@ given the ability to merge pull requests.
|
||||
|
||||
## Code of Conduct
|
||||
This project adheres to the Contributor Covenant [code of
|
||||
conduct](https://github.com/spring-cloud/spring-cloud-build/blob/main/docs/modules/ROOT/partials/code-of-conduct.adoc). By participating, you are expected to uphold this code. Please report
|
||||
conduct](https://github.com/spring-cloud/spring-cloud-build/blob/main/docs/src/main/asciidoc/code-of-conduct.adoc). By participating, you are expected to uphold this code. Please report
|
||||
unacceptable behavior to spring-code-of-conduct@pivotal.io.
|
||||
|
||||
## Code Conventions and Housekeeping
|
||||
|
||||
@@ -1,2 +0,0 @@
|
||||
require:
|
||||
members: false
|
||||
+9
-45
@@ -2,17 +2,12 @@ version: 2
|
||||
updates:
|
||||
- package-ecosystem: "github-actions"
|
||||
directory: "/"
|
||||
target-branch: "4.1.x" # oldest OSS supported branch
|
||||
target-branch: "3.1.x" # oldest OSS supported branch
|
||||
schedule:
|
||||
interval: "weekly"
|
||||
- package-ecosystem: "github-actions"
|
||||
directory: "/"
|
||||
target-branch: "4.2.x"
|
||||
schedule:
|
||||
interval: "weekly"
|
||||
- package-ecosystem: "github-actions"
|
||||
directory: "/"
|
||||
target-branch: "4.3.x"
|
||||
target-branch: "4.0.x" # oldest OSS supported branch
|
||||
schedule:
|
||||
interval: "weekly"
|
||||
- package-ecosystem: "github-actions"
|
||||
@@ -24,7 +19,7 @@ updates:
|
||||
directory: /
|
||||
schedule:
|
||||
interval: daily
|
||||
target-branch: 4.1.x
|
||||
target-branch: 3.1.x
|
||||
ignore:
|
||||
# only upgrade patch versions for maintenance branch
|
||||
- dependency-name: "*"
|
||||
@@ -35,18 +30,7 @@ updates:
|
||||
directory: /
|
||||
schedule:
|
||||
interval: daily
|
||||
target-branch: 4.2.x
|
||||
ignore:
|
||||
# only upgrade patch versions for maintenance branch
|
||||
- dependency-name: "*"
|
||||
update-types:
|
||||
- version-update:semver-major
|
||||
- version-update:semver-minor
|
||||
- package-ecosystem: maven
|
||||
directory: /
|
||||
schedule:
|
||||
interval: daily
|
||||
target-branch: 4.3.x
|
||||
target-branch: 4.0.x
|
||||
ignore:
|
||||
# only upgrade patch versions for maintenance branch
|
||||
- dependency-name: "*"
|
||||
@@ -58,28 +42,8 @@ updates:
|
||||
schedule:
|
||||
interval: daily
|
||||
target-branch: main
|
||||
- package-ecosystem: npm
|
||||
target-branch: docs-build
|
||||
directory: /
|
||||
schedule:
|
||||
interval: weekly
|
||||
- package-ecosystem: npm
|
||||
target-branch: main
|
||||
directory: /docs
|
||||
schedule:
|
||||
interval: weekly
|
||||
- package-ecosystem: npm
|
||||
target-branch: 4.1.x
|
||||
directory: /docs
|
||||
schedule:
|
||||
interval: weekly
|
||||
- package-ecosystem: npm
|
||||
target-branch: 4.2.x
|
||||
directory: /docs
|
||||
schedule:
|
||||
interval: weekly
|
||||
- package-ecosystem: npm
|
||||
target-branch: 4.3.x
|
||||
directory: /docs
|
||||
schedule:
|
||||
interval: weekly
|
||||
ignore:
|
||||
# only upgrade by minor or patch
|
||||
- dependency-name: "*"
|
||||
update-types:
|
||||
- version-update:semver-major
|
||||
+12
-21
@@ -5,38 +5,29 @@ name: Build
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ main, 4.3.x, 4.2.x, 4.1.x ]
|
||||
branches: [ main ]
|
||||
pull_request:
|
||||
branches: [ main, 4.3.x, 4.2.x, 4.1.x ]
|
||||
branches: [ main ]
|
||||
|
||||
jobs:
|
||||
build:
|
||||
|
||||
runs-on: ubuntu-latest
|
||||
|
||||
strategy:
|
||||
matrix:
|
||||
java: ["17"]
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- name: Set up JDK
|
||||
- name: Set up JDK ${{ matrix.java }}
|
||||
uses: actions/setup-java@v4
|
||||
with:
|
||||
distribution: 'temurin'
|
||||
java-version: '17'
|
||||
- name: Cache local Maven repository
|
||||
uses: actions/cache@v4
|
||||
with:
|
||||
path: ~/.m2/repository
|
||||
key: ${{ runner.os }}-maven-${{ hashFiles('**/pom.xml') }}
|
||||
restore-keys: |
|
||||
${{ runner.os }}-maven-
|
||||
java-version: ${{ matrix.java }}
|
||||
cache: 'maven'
|
||||
- name: Build with Maven
|
||||
run: ./mvnw -s .settings.xml clean org.jacoco:jacoco-maven-plugin:prepare-agent install -U -P sonar -nsu --batch-mode -Dmaven.test.redirectTestOutputToFile=true -Dorg.slf4j.simpleLogger.log.org.apache.maven.cli.transfer.Slf4jMavenTransferListener=warn
|
||||
- name: Publish Test Report
|
||||
uses: mikepenz/action-junit-report@v5
|
||||
if: always() # always run even if the previous step fails
|
||||
run: ./mvnw clean install -B -U -P sonar
|
||||
- uses: codecov/codecov-action@v3
|
||||
with:
|
||||
report_paths: '**/surefire-reports/TEST-*.xml'
|
||||
- name: Archive code coverage results
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: surefire-reports
|
||||
path: '**/surefire-reports/*'
|
||||
fail_ci_if_error: false
|
||||
|
||||
+1
-1
@@ -33,5 +33,5 @@ _configprops.adoc
|
||||
_spans.adoc
|
||||
_metrics.adoc
|
||||
_conventions.adoc
|
||||
/package.json
|
||||
package.json
|
||||
package-lock.json
|
||||
|
||||
+2
-2
@@ -49,7 +49,7 @@ build succeed, please raise a ticket to get the settings added to
|
||||
source control.
|
||||
|
||||
The projects that require middleware (i.e. Redis) for testing generally
|
||||
require that a local instance of https://www.docker.com/get-started[Docker] is installed and running.
|
||||
require that a local instance of [Docker](https://www.docker.com/get-started) is installed and running.
|
||||
|
||||
[[documentation]]
|
||||
== Documentation
|
||||
@@ -68,7 +68,7 @@ a modified file in the correct place. Just commit it and push the change.
|
||||
[[working-with-the-code]]
|
||||
== Working with the code
|
||||
If you don't have an IDE preference we would recommend that you use
|
||||
https://spring.io/tools[Spring Tools Suite] or
|
||||
https://www.springsource.com/developer/sts[Spring Tools Suite] or
|
||||
https://eclipse.org[Eclipse] when working with the code. We use the
|
||||
https://eclipse.org/m2e/[m2eclipse] eclipse plugin for maven support. Other IDEs and tools
|
||||
should also work without issue as long as they use Maven 3.3.3 or better.
|
||||
|
||||
@@ -1,7 +1,13 @@
|
||||
antora:
|
||||
extensions:
|
||||
- require: '@springio/antora-extensions'
|
||||
- '@springio/antora-extensions/partial-build-extension'
|
||||
- require: '@springio/antora-extensions/latest-version-extension'
|
||||
- require: '@springio/antora-extensions/inject-collector-cache-config-extension'
|
||||
- '@antora/collector-extension'
|
||||
- '@antora/atlas-extension'
|
||||
- require: '@springio/antora-extensions/root-component-extension'
|
||||
root_component_name: 'cloud-netflix'
|
||||
- '@springio/antora-extensions/static-page-extension'
|
||||
site:
|
||||
title: Spring Cloud Netflix
|
||||
url: https://docs.spring.io/spring-cloud-netflix/reference/
|
||||
@@ -30,4 +36,4 @@ runtime:
|
||||
format: pretty
|
||||
ui:
|
||||
bundle:
|
||||
url: https://github.com/spring-io/antora-ui-spring/releases/download/v0.4.15/ui-bundle.zip
|
||||
url: https://github.com/spring-io/antora-ui-spring/releases/download/v0.4.2/ui-bundle.zip
|
||||
+1
-1
@@ -6,7 +6,7 @@ nav:
|
||||
ext:
|
||||
collector:
|
||||
run:
|
||||
command: ./mvnw --no-transfer-progress -B process-resources -Pdocs -pl docs -Dantora-maven-plugin.phase=none -Dgenerate-docs.phase=none -Dgenerate-readme.phase=none -Dgenerate-cloud-resources.phase=none -Dmaven-dependency-plugin-for-docs.phase=none -Dmaven-dependency-plugin-for-docs-classes.phase=none -DskipTests -DdisableConfigurationProperties
|
||||
command: ./mvnw --no-transfer-progress -B process-resources -Pdocs -pl docs -Dantora-maven-plugin.phase=none -Dgenerate-docs.phase=none -Dgenerate-readme.phase=none -Dgenerate-cloud-resources.phase=none -Dmaven-dependency-plugin-for-docs.phase=none -Dmaven-dependency-plugin-for-docs-classes.phase=none -DskipTests
|
||||
local: true
|
||||
scan:
|
||||
dir: ./target/classes/antora-resources/
|
||||
|
||||
@@ -35,9 +35,8 @@ public class Application {
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(CustomerServiceTestApplication.class, args);
|
||||
}
|
||||
|
||||
new SpringApplicationBuilder(Application.class).web(true).run(args);
|
||||
}
|
||||
|
||||
}
|
||||
----
|
||||
@@ -98,39 +97,19 @@ NOTE: Because of a limitation in Eureka, it is not possible to support per-serve
|
||||
|
||||
If you want to customize the RestTemplate used by the Eureka HTTP Client you may want to create a bean of `EurekaClientHttpRequestFactorySupplier` and provide your own logic for generating a `ClientHttpRequestFactory` instance.
|
||||
|
||||
All default timeout-related properties for RestTemplate and RestClient used by the Eureka HTTP Client are set to 3 minutes (in keeping with Apache HC5 default `RequestConfig` and `SocketConfig`). Therefore, to specify the timeout values, you must specify the value directly with the properties in `eureka.client.rest-template-timeout` or `eureka.client.restclient.timeout`. All timeout properties are in milliseconds.
|
||||
All default timeout-related properties for RestTemplate used by the Eureka HTTP Client are set to 3 minutes (in keeping with Apache HC5 default `RequestConfig` and `SocketConfig`). Therefore, to specify the timeout values, you must specify the value directly with the properties in `eureka.client.rest-template-timeout`. (All timeout properties are in milliseconds.)
|
||||
|
||||
.application.yml
|
||||
[source,yaml]
|
||||
----
|
||||
eureka:
|
||||
client:
|
||||
restclient:
|
||||
timeout:
|
||||
connect-timeout: 5000
|
||||
connect-request-timeout: 8000
|
||||
socket-timeout: 10000
|
||||
rest-template-timeout:
|
||||
connect-timeout: 5000
|
||||
connect-request-timeout: 8000
|
||||
socket-timeout: 10000
|
||||
----
|
||||
|
||||
You can also customise the `RequestConfig` for the underlying Apache HttpClient 5 by creating a bean of type `EurekaClientHttpRequestFactorySupplier.RequestConfigCustomizer`:
|
||||
|
||||
[source,java,indent=0]
|
||||
----
|
||||
@Configuration
|
||||
public class RestClientConfiguration {
|
||||
|
||||
@Bean
|
||||
EurekaClientHttpRequestFactorySupplier.RequestConfigCustomizer requestConfigCustomizer() {
|
||||
return builder -> builder.setProtocolUpgradeEnabled(false);
|
||||
}
|
||||
|
||||
}
|
||||
----
|
||||
|
||||
=== Status Page and Health Indicator
|
||||
|
||||
The status page and health indicators for a Eureka instance default to `/info` and `/health` respectively, which are the default locations of useful endpoints in a Spring Boot Actuator application.
|
||||
@@ -290,15 +269,9 @@ It is initialized in a `SmartLifecycle` (with `phase=0`), so the earliest you ca
|
||||
|
||||
==== Underlying HTTP clients
|
||||
|
||||
`EurekaClient` uses either `RestClient`, `RestTemplate`, `WebClient` or `JerseyClient` under the hood. In order to use the `EurekaClient`, you need to have one of the supported HTTP clients on your classpath.
|
||||
`EurekaClient` uses either `RestTemplate`, `WebClient` or `JerseyClient` under the hood. In order to use the `EurekaClient`, you need to have one of the supported HTTP clients on your classpath.
|
||||
|
||||
To use `RestTemplate` or `RestClient`, add `spring-boot-restclient` to your dependencies. To use `WebClient`, add `spring-boot-webclient` to your dependencies. If both `spring-boot-restclient`
|
||||
and `spring-boot-webclient` are included in the dependencies and the `eureka.client.webclient.enabled` flag is set to `true`,
|
||||
then `WebClient` will be used. If that's not the case and `eureka.client.restclient.enabled` is set to `true`, `RestClient` will be used. Otherwise, `RestTemplate` will be used.
|
||||
|
||||
NOTE: For any of those client implementations, if there's a builder bean available, it will be used to create the underlying client.
|
||||
|
||||
NOTE: We're planning on changing the default client to `RestClient` with the next major release.
|
||||
To use `RestTemplate`, add `spring-boot-starter-web` to your dependencies. To use `WebClient`, add `spring-boot-starter-webflux` to your dependencies. If both `RestTemplate` and `WebClient` are on the classpath when `eureka.client.webclient.enabled` is set to `true`, `WebClient` is used. Otherwise, `RestTemplate` is used.
|
||||
|
||||
If you wish to use Jersey instead, you need to add the Jersey dependencies to your classpath.
|
||||
The following example shows the dependencies you need to add:
|
||||
@@ -321,8 +294,6 @@ The following example shows the dependencies you need to add:
|
||||
</dependencies>
|
||||
----
|
||||
|
||||
If you have `JerseyClient` on the classpath but do not wish to use it in your `EuerekaClient`, make sure to set `eureka.client.jersey.enabled` to `false`.
|
||||
|
||||
=== Alternatives to the Native Netflix EurekaClient
|
||||
|
||||
You need not use the raw Netflix `EurekaClient`.
|
||||
@@ -403,9 +374,7 @@ We take `eureka.client.availabilityZones`, which is a map from region name to a
|
||||
|
||||
Spring Cloud Netflix Eureka Client integration supports Spring AOT transformations and native images, however, only with refresh mode disabled.
|
||||
|
||||
WARNING: If you want to run Eureka Client in AOT or native image modes, make sure to set `spring.cloud.refresh.enabled` to `false`.
|
||||
|
||||
NOTE: Given the AOT and native image closed-world assumption, using random port with Eureka clients is not supported for ahead of time compilation or native images.
|
||||
WARNING: If you want to run Eureka Client in AOT or native image modes, make sure to set `spring.cloud.refresh.enabled` to `false`
|
||||
|
||||
[[spring-cloud-eureka-server]]
|
||||
== Service Discovery: Eureka Server
|
||||
@@ -440,9 +409,8 @@ The following example shows a minimal Eureka server:
|
||||
public class Application {
|
||||
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(CustomerServiceTestApplication.class, args);
|
||||
}
|
||||
|
||||
new SpringApplicationBuilder(Application.class).web(true).run(args);
|
||||
}
|
||||
|
||||
}
|
||||
----
|
||||
@@ -636,17 +604,6 @@ when running a Eureka server you must include these dependencies in your POM or
|
||||
|
||||
Spring Cloud Netflix Eureka Server does not support Spring AOT transformations or native images.
|
||||
|
||||
=== Metrics
|
||||
|
||||
`EurekaInstanceMonitor` listens to events related to Eureka instance registration and creates/updates `Gauge`s for Eureka instance information in Micrometer's `MeterRegistry`. By default, this behavior is disabled. If you want to enable it, you need to set `eureka.server.metrics.enabled` to `true`.
|
||||
|
||||
By default, the `Gauge`s are named `eureka.server.instances` and have the following tags:
|
||||
|
||||
- `application`: application name
|
||||
- `status`: instance status (`UP`, `DOWN`, `STARTING`, `OUT_OF_SERVICE`, `UNKNOWN`, see: `com.netflix.appinfo.InstanceInfo.InstanceStatus`)
|
||||
|
||||
You can add additional tags by injecting your own implementation of `EurekaInstanceTagsProvider`.
|
||||
|
||||
== Configuration properties
|
||||
|
||||
To see the list of all Spring Cloud Netflix related configuration properties please check link:appendix.html[the Appendix page].
|
||||
|
||||
@@ -21,7 +21,7 @@
|
||||
|eureka.client.eureka-server-total-connections | `+++200+++` | Gets the total number of connections that is allowed from eureka client to all eureka servers.
|
||||
|eureka.client.eureka-server-total-connections-per-host | `+++50+++` | Gets the total number of connections that is allowed from eureka client to a eureka server host.
|
||||
|eureka.client.eureka-server-u-r-l-context | | Gets the URL context to be used to construct the service url to contact eureka server when the list of eureka servers come from the DNS. This information is not required if the contract returns the service urls from eurekaServerServiceUrls. The DNS mechanism is used when useDnsForFetchingServiceUrls is set to true and the eureka client expects the DNS to configured a certain way so that it can fetch changing eureka servers dynamically. The changes are effective at runtime.
|
||||
|eureka.client.eureka-service-url-poll-interval-seconds | `+++300+++` | Indicates how often(in seconds) to poll for changes to eureka server information. Eureka servers could be added or removed and this setting controls how soon the eureka clients should know about it.
|
||||
|eureka.client.eureka-service-url-poll-interval-seconds | `+++0+++` | Indicates how often(in seconds) to poll for changes to eureka server information. Eureka servers could be added or removed and this setting controls how soon the eureka clients should know about it.
|
||||
|eureka.client.fetch-registry | `+++true+++` | Indicates whether this client should fetch eureka registry information from eureka server.
|
||||
|eureka.client.fetch-remote-regions-registry | | Comma separated list of regions for which the eureka registry information will be fetched. It is mandatory to define the availability zones for each of these regions as returned by availabilityZones. Failing to do so, will result in failure of discovery client startup.
|
||||
|eureka.client.filter-only-up-instances | `+++true+++` | Indicates whether to get the applications after filtering the applications for instances with only InstanceStatus UP states.
|
||||
@@ -31,7 +31,6 @@
|
||||
|eureka.client.heartbeat-executor-thread-pool-size | `+++2+++` | The thread pool size for the heartbeatExecutor to initialise with.
|
||||
|eureka.client.initial-instance-info-replication-interval-seconds | `+++40+++` | Indicates how long initially (in seconds) to replicate instance info to the eureka server.
|
||||
|eureka.client.instance-info-replication-interval-seconds | `+++30+++` | Indicates how often(in seconds) to replicate instance changes to be replicated to the eureka server.
|
||||
|eureka.client.jersey.enabled | `+++true+++` | Enables the use of JerseyClient for Eureka HTTP Client.
|
||||
|eureka.client.log-delta-diff | `+++false+++` | Indicates whether to log differences between the eureka server and the eureka client in terms of registry information. Eureka client tries to retrieve only delta changes from eureka server to minimize network traffic. After receiving the deltas, eureka client reconciles the information from the server to verify it has not missed out some information. Reconciliation failures could happen when the client has had network issues communicating to server.If the reconciliation fails, eureka client gets the full registry information. While getting the full registry information, the eureka client can log the differences between the client and the server and this setting controls that. The changes are effective at runtime at the next registry fetch cycle as specified by registryFetchIntervalSecondsr
|
||||
|eureka.client.on-demand-update-status-change | `+++true+++` | If set to true, local status updates via ApplicationInfoManager will trigger on-demand (but rate limited) register/updates to remote eureka servers.
|
||||
|eureka.client.order | `+++0+++` | Order of the discovery client used by `CompositeDiscoveryClient` for sorting available clients.
|
||||
@@ -46,13 +45,9 @@
|
||||
|eureka.client.register-with-eureka | `+++true+++` | Indicates whether or not this instance should register its information with eureka server for discovery by others. In some cases, you do not want your instances to be discovered whereas you just want do discover other instances.
|
||||
|eureka.client.registry-fetch-interval-seconds | `+++30+++` | Indicates how often(in seconds) to fetch the registry information from the eureka server.
|
||||
|eureka.client.registry-refresh-single-vip-address | | Indicates whether the client is only interested in the registry information for a single VIP.
|
||||
|eureka.client.rest-template-timeout.connect-request-timeout | `+++180000+++` |
|
||||
|eureka.client.rest-template-timeout.connect-timeout | `+++180000+++` | Default values are set to 180000, in keeping with {@link RequestConfig} and {@link SocketConfig} defaults.
|
||||
|eureka.client.rest-template-timeout.socket-timeout | `+++180000+++` |
|
||||
|eureka.client.restclient.enabled | `+++false+++` | Enables the use of RestClient for Eureka HTTP Client.
|
||||
|eureka.client.restclient.timeout.connect-request-timeout | `+++180000+++` |
|
||||
|eureka.client.restclient.timeout.connect-timeout | `+++180000+++` | Default values are set to 180000, in keeping with {@link RequestConfig} and {@link SocketConfig} defaults.
|
||||
|eureka.client.restclient.timeout.socket-timeout | `+++180000+++` |
|
||||
|eureka.client.rest-template-timeout.connect-request-timeout | `+++0+++` |
|
||||
|eureka.client.rest-template-timeout.connect-timeout | `+++0+++` | Default values are set to 180000, in keeping with {@link RequestConfig} and {@link SocketConfig} defaults.
|
||||
|eureka.client.rest-template-timeout.socket-timeout | `+++0+++` |
|
||||
|eureka.client.service-url | | Map of availability zone to list of fully qualified URLs to communicate with eureka server. Each value can be a single URL or a comma separated list of alternative locations. Typically the eureka server URLs carry protocol,host,port,context and version information if any. Example: https://ec2-256-156-243-129.compute-1.amazonaws.com:7001/eureka/ The changes are effective at runtime at the next service url refresh cycle as specified by eurekaServiceUrlPollIntervalSeconds.
|
||||
|eureka.client.should-enforce-registration-at-init | `+++false+++` | Indicates whether the client should enforce registration during initialization. Defaults to false.
|
||||
|eureka.client.should-unregister-on-shutdown | `+++true+++` | Indicates whether the client should explicitly unregister itself from the remote server on client shutdown.
|
||||
@@ -73,7 +68,6 @@
|
||||
|eureka.instance.a-s-g-name | | Gets the AWS autoscaling group name associated with this instance. This information is specifically used in an AWS environment to automatically put an instance out of service after the instance is launched and it has been disabled for traffic..
|
||||
|eureka.instance.app-group-name | | Get the name of the application group to be registered with eureka.
|
||||
|eureka.instance.appname | `+++unknown+++` | Get the name of the application to be registered with eureka.
|
||||
|eureka.instance.async-client-initialization | `+++false+++` | If true the EurekaClient will be initialized asynchronously when the InstanceRegistry bean is created.
|
||||
|eureka.instance.data-center-info | | Returns the data center this instance is deployed. This information is used to get some AWS specific instance information if the instance is deployed in AWS.
|
||||
|eureka.instance.default-address-resolution-order | `+++[]+++` |
|
||||
|eureka.instance.environment | |
|
||||
@@ -82,7 +76,7 @@
|
||||
|eureka.instance.home-page-url | | Gets the absolute home page URL for this instance. The users can provide the homePageUrlPath if the home page resides in the same instance talking to eureka, else in the cases where the instance is a proxy for some other server, users can provide the full URL. If the full URL is provided it takes precedence. It is normally used for informational purposes for other services to use it as a landing page. The full URL should follow the format http://${eureka.hostname}:7001/ where the value ${eureka.hostname} is replaced at runtime.
|
||||
|eureka.instance.home-page-url-path | `+++/+++` | Gets the relative home page URL Path for this instance. The home page URL is then constructed out of the hostName and the type of communication - secure or unsecure. It is normally used for informational purposes for other services to use it as a landing page.
|
||||
|eureka.instance.hostname | | The hostname if it can be determined at configuration time (otherwise it will be guessed from OS primitives).
|
||||
|eureka.instance.initial-status | `+++up+++` | Initial status to register with remote Eureka server.
|
||||
|eureka.instance.initial-status | | Initial status to register with remote Eureka server.
|
||||
|eureka.instance.instance-enabled-onit | `+++false+++` | Indicates whether the instance should be enabled for taking traffic as soon as it is registered with eureka. Sometimes the application might need to do some pre-processing before it is ready to take traffic.
|
||||
|eureka.instance.instance-id | | Get the unique Id (within the scope of the appName) of this instance to be registered with eureka.
|
||||
|eureka.instance.ip-address | | Get the IPAdress of the instance. This information is for academic purposes only as the communication from other instances primarily happen using the information supplied in {@link #getHostName(boolean)}.
|
||||
@@ -103,23 +97,23 @@
|
||||
|eureka.instance.status-page-url | | Gets the absolute status page URL path for this instance. The users can provide the statusPageUrlPath if the status page resides in the same instance talking to eureka, else in the cases where the instance is a proxy for some other server, users can provide the full URL. If the full URL is provided it takes precedence. It is normally used for informational purposes for other services to find about the status of this instance. Users can provide a simple HTML indicating what is the current status of the instance.
|
||||
|eureka.instance.status-page-url-path | | Gets the relative status page URL path for this instance. The status page URL is then constructed out of the hostName and the type of communication - secure or unsecure as specified in securePort and nonSecurePort. It is normally used for informational purposes for other services to find about the status of this instance. Users can provide a simple HTML indicating what is the current status of the instance.
|
||||
|eureka.instance.virtual-host-name | `+++unknown+++` | Gets the virtual host name defined for this instance. This is typically the way other instance would find this instance by using the virtual host name.Think of this as similar to the fully qualified domain name, that the users of your services will need to find this instance.
|
||||
|eureka.server.a-s-g-cache-expiry-timeout-ms | `+++600000+++` |
|
||||
|eureka.server.a-s-g-cache-expiry-timeout-ms | `+++0+++` |
|
||||
|eureka.server.a-s-g-query-timeout-ms | `+++300+++` |
|
||||
|eureka.server.a-s-g-update-interval-ms | `+++300000+++` |
|
||||
|eureka.server.a-s-g-update-interval-ms | `+++0+++` |
|
||||
|eureka.server.a-w-s-access-id | |
|
||||
|eureka.server.a-w-s-secret-key | |
|
||||
|eureka.server.batch-replication | `+++false+++` |
|
||||
|eureka.server.binding-strategy | `+++eip+++` |
|
||||
|eureka.server.delta-retention-timer-interval-in-ms | `+++30000+++` |
|
||||
|eureka.server.binding-strategy | |
|
||||
|eureka.server.delta-retention-timer-interval-in-ms | `+++0+++` |
|
||||
|eureka.server.disable-delta | `+++false+++` |
|
||||
|eureka.server.disable-delta-for-remote-regions | `+++false+++` |
|
||||
|eureka.server.disable-transparent-fallback-to-other-region | `+++false+++` |
|
||||
|eureka.server.e-i-p-bind-rebind-retries | `+++3+++` |
|
||||
|eureka.server.e-i-p-binding-retry-interval-ms | `+++300000+++` |
|
||||
|eureka.server.e-i-p-binding-retry-interval-ms-when-unbound | `+++60000+++` |
|
||||
|eureka.server.e-i-p-binding-retry-interval-ms | `+++0+++` |
|
||||
|eureka.server.e-i-p-binding-retry-interval-ms-when-unbound | `+++0+++` |
|
||||
|eureka.server.enable-replicated-request-compression | `+++false+++` |
|
||||
|eureka.server.enable-self-preservation | `+++true+++` |
|
||||
|eureka.server.eviction-interval-timer-in-ms | |
|
||||
|eureka.server.eviction-interval-timer-in-ms | `+++0+++` |
|
||||
|eureka.server.expected-client-renewal-interval-seconds | `+++30+++` |
|
||||
|eureka.server.g-zip-content-from-remote-region | `+++true+++` |
|
||||
|eureka.server.initial-capacity-of-response-cache | `+++1000+++` |
|
||||
@@ -133,14 +127,13 @@
|
||||
|eureka.server.max-threads-for-peer-replication | `+++20+++` |
|
||||
|eureka.server.max-threads-for-status-replication | `+++1+++` |
|
||||
|eureka.server.max-time-for-replication | `+++30000+++` |
|
||||
|eureka.server.metrics.enabled | `+++false+++` | Indicates whether the metrics should be enabled for eureka instances.
|
||||
|eureka.server.min-available-instances-for-peer-replication | `+++-1+++` |
|
||||
|eureka.server.min-threads-for-peer-replication | `+++5+++` |
|
||||
|eureka.server.min-threads-for-status-replication | `+++1+++` |
|
||||
|eureka.server.my-url | |
|
||||
|eureka.server.number-of-replication-retries | `+++5+++` |
|
||||
|eureka.server.peer-eureka-nodes-update-interval-ms | `+++600000+++` |
|
||||
|eureka.server.peer-eureka-status-refresh-time-interval-ms | |
|
||||
|eureka.server.peer-eureka-nodes-update-interval-ms | `+++0+++` |
|
||||
|eureka.server.peer-eureka-status-refresh-time-interval-ms | `+++0+++` |
|
||||
|eureka.server.peer-node-connect-timeout-ms | `+++200+++` |
|
||||
|eureka.server.peer-node-connection-idle-timeout-seconds | `+++30+++` |
|
||||
|eureka.server.peer-node-read-timeout-ms | `+++200+++` |
|
||||
@@ -155,7 +148,7 @@
|
||||
|eureka.server.rate-limiter-registry-fetch-average-rate | `+++500+++` |
|
||||
|eureka.server.rate-limiter-throttle-standard-clients | `+++false+++` |
|
||||
|eureka.server.registry-sync-retries | `+++0+++` |
|
||||
|eureka.server.registry-sync-retry-wait-ms | |
|
||||
|eureka.server.registry-sync-retry-wait-ms | `+++0+++` |
|
||||
|eureka.server.remote-region-app-whitelist | |
|
||||
|eureka.server.remote-region-connect-timeout-ms | `+++1000+++` |
|
||||
|eureka.server.remote-region-connection-idle-timeout-seconds | `+++30+++` |
|
||||
@@ -169,18 +162,18 @@
|
||||
|eureka.server.remote-region-urls | |
|
||||
|eureka.server.remote-region-urls-with-name | |
|
||||
|eureka.server.renewal-percent-threshold | `+++0.85+++` |
|
||||
|eureka.server.renewal-threshold-update-interval-ms | `+++900000+++` |
|
||||
|eureka.server.renewal-threshold-update-interval-ms | `+++0+++` |
|
||||
|eureka.server.response-cache-auto-expiration-in-seconds | `+++180+++` |
|
||||
|eureka.server.response-cache-update-interval-ms | `+++30000+++` |
|
||||
|eureka.server.retention-time-in-m-s-in-delta-queue | `+++180000+++` |
|
||||
|eureka.server.response-cache-update-interval-ms | `+++0+++` |
|
||||
|eureka.server.retention-time-in-m-s-in-delta-queue | `+++0+++` |
|
||||
|eureka.server.route53-bind-rebind-retries | `+++3+++` |
|
||||
|eureka.server.route53-binding-retry-interval-ms | `+++300000+++` |
|
||||
|eureka.server.route53-binding-retry-interval-ms | `+++0+++` |
|
||||
|eureka.server.route53-domain-t-t-l | `+++30+++` |
|
||||
|eureka.server.sync-when-timestamp-differs | `+++true+++` |
|
||||
|eureka.server.use-read-only-response-cache | `+++true+++` |
|
||||
|eureka.server.wait-time-in-ms-when-sync-empty | `+++300000+++` |
|
||||
|eureka.server.wait-time-in-ms-when-sync-empty | `+++0+++` |
|
||||
|eureka.server.xml-codec-name | |
|
||||
|spring.cloud.compatibility-verifier.compatible-boot-versions | `+++4.0.x+++` | Default accepted versions for the Spring Boot dependency. You can set {@code x} for the patch version if you don't want to specify a concrete value. Example: {@code 3.5.x}
|
||||
|spring.cloud.compatibility-verifier.compatible-boot-versions | `+++3.2.x+++` | Default accepted versions for the Spring Boot dependency. You can set {@code x} for the patch version if you don't want to specify a concrete value. Example: {@code 3.4.x}
|
||||
|spring.cloud.compatibility-verifier.enabled | `+++false+++` | Enables creation of Spring Cloud compatibility verification.
|
||||
|spring.cloud.config.allow-override | `+++true+++` | Flag to indicate that {@link #isOverrideSystemProperties() systemPropertiesOverride} can be used. Set to false to prevent users from changing the default accidentally. Default true.
|
||||
|spring.cloud.config.initialize-on-context-refresh | `+++false+++` | Flag to initialize bootstrap configuration on context refresh event. Default false.
|
||||
@@ -224,6 +217,7 @@
|
||||
|spring.cloud.loadbalancer.eureka.approximate-zone-from-hostname | `+++false+++` | Used to determine whether we should try to get the `zone` value from host name.
|
||||
|spring.cloud.loadbalancer.health-check.initial-delay | `+++0+++` | Initial delay value for the HealthCheck scheduler.
|
||||
|spring.cloud.loadbalancer.health-check.interval | `+++25s+++` | Interval for rerunning the HealthCheck scheduler.
|
||||
|spring.cloud.loadbalancer.health-check.interval | `+++25s+++` | Interval for rerunning the HealthCheck scheduler.
|
||||
|spring.cloud.loadbalancer.health-check.path | | Path at which the health-check request should be made. Can be set up per `serviceId`. A `default` value can be set up as well. If none is set up, `/actuator/health` will be used.
|
||||
|spring.cloud.loadbalancer.health-check.port | | Path at which the health-check request should be made. If none is set, the port under which the requested service is available at the service instance.
|
||||
|spring.cloud.loadbalancer.health-check.refetch-instances | `+++false+++` | Indicates whether the instances should be refetched by the `HealthCheckServiceInstanceListSupplier`. This can be used if the instances can be updated and the underlying delegate does not provide an ongoing flux.
|
||||
@@ -245,7 +239,6 @@
|
||||
|spring.cloud.loadbalancer.retry.retryable-exceptions | `+++{}+++` | A `Set` of `Throwable` classes that should trigger a retry.
|
||||
|spring.cloud.loadbalancer.retry.retryable-status-codes | `+++{}+++` | A `Set` of status codes that should trigger a retry.
|
||||
|spring.cloud.loadbalancer.service-discovery.timeout | | String representation of Duration of the timeout for calls to service discovery.
|
||||
|spring.cloud.loadbalancer.stats.include-path | `+++true+++` | Indicates whether the {@code path} should be added to {@code uri} tag in metrics. When {@link RestTemplate} is used to execute load-balanced requests with high cardinality paths, setting it to {@code false} is recommended.
|
||||
|spring.cloud.loadbalancer.stats.micrometer.enabled | `+++false+++` | Enables Spring Cloud LoadBalancer Micrometer stats.
|
||||
|spring.cloud.loadbalancer.sticky-session.add-service-instance-cookie | `+++false+++` | Indicates whether a cookie with the newly selected instance should be added by LoadBalancer.
|
||||
|spring.cloud.loadbalancer.sticky-session.instance-id-cookie-name | `+++sc-lb-instance-id+++` | The name of the cookie holding the preferred instance id.
|
||||
@@ -255,8 +248,8 @@
|
||||
|spring.cloud.loadbalancer.zone | | Spring Cloud LoadBalancer zone.
|
||||
|spring.cloud.refresh.additional-property-sources-to-retain | | Additional property sources to retain during a refresh. Typically only system property sources are retained. This property allows property sources, such as property sources created by EnvironmentPostProcessors to be retained as well.
|
||||
|spring.cloud.refresh.enabled | `+++true+++` | Enables autoconfiguration for the refresh scope and associated features.
|
||||
|spring.cloud.refresh.extra-refreshable | `+++true+++` | Additional bean names or class names for beans to post process into refresh scope.
|
||||
|spring.cloud.refresh.never-refreshable | `+++true+++` | Comma separated list of bean names or class names for beans to never be refreshed or rebound.
|
||||
|spring.cloud.refresh.extra-refreshable | `+++true+++` | Additional class names for beans to post process into refresh scope.
|
||||
|spring.cloud.refresh.never-refreshable | `+++true+++` | Comma separated list of class names for beans to never be refreshed or rebound.
|
||||
|spring.cloud.refresh.on-restart.enabled | `+++true+++` | Enable refreshing context on start.
|
||||
|spring.cloud.service-registry.auto-registration.enabled | `+++true+++` | Whether service auto-registration is enabled. Defaults to true.
|
||||
|spring.cloud.service-registry.auto-registration.fail-fast | `+++false+++` | Whether startup fails if there is no AutoServiceRegistration. Defaults to false.
|
||||
|
||||
@@ -1,10 +0,0 @@
|
||||
{
|
||||
"dependencies": {
|
||||
"antora": "3.2.0-alpha.8",
|
||||
"@antora/atlas-extension": "1.0.0-alpha.2",
|
||||
"@antora/collector-extension": "1.0.1",
|
||||
"@asciidoctor/tabs": "1.0.0-beta.6",
|
||||
"@springio/antora-extensions": "1.14.7",
|
||||
"@springio/asciidoctor-extensions": "1.0.0-alpha.17"
|
||||
}
|
||||
}
|
||||
+12
-21
@@ -8,7 +8,7 @@
|
||||
<parent>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-netflix</artifactId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<relativePath>..</relativePath>
|
||||
</parent>
|
||||
<packaging>jar</packaging>
|
||||
@@ -21,28 +21,20 @@
|
||||
<!-- Don't upload docs jar to central / repo.spring.io -->
|
||||
<maven-deploy-plugin-default.phase>none</maven-deploy-plugin-default.phase>
|
||||
</properties>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>${project.groupId}</groupId>
|
||||
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>${project.groupId}</groupId>
|
||||
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<build>
|
||||
<sourceDirectory>src/main/asciidoc</sourceDirectory>
|
||||
</build>
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>enable-configuration-properties</id>
|
||||
<activation>
|
||||
<property>
|
||||
<name>!disableConfigurationProperties</name>
|
||||
</property>
|
||||
</activation>
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>${project.groupId}</groupId>
|
||||
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>${project.groupId}</groupId>
|
||||
<artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</profile>
|
||||
<profile>
|
||||
<id>docs</id>
|
||||
<build>
|
||||
@@ -70,7 +62,7 @@
|
||||
<artifactId>antora-component-version-maven-plugin</artifactId>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.antora</groupId>
|
||||
<groupId>io.spring.maven.antora</groupId>
|
||||
<artifactId>antora-maven-plugin</artifactId>
|
||||
</plugin>
|
||||
<plugin>
|
||||
@@ -78,7 +70,6 @@
|
||||
<artifactId>maven-antrun-plugin</artifactId>
|
||||
</plugin>
|
||||
<plugin>
|
||||
<groupId>org.apache.maven.plugins</groupId>
|
||||
<artifactId>maven-deploy-plugin</artifactId>
|
||||
</plugin>
|
||||
</plugins>
|
||||
|
||||
@@ -3,15 +3,14 @@
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
<artifactId>spring-cloud-netflix</artifactId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<packaging>pom</packaging>
|
||||
<name>Spring Cloud Netflix</name>
|
||||
<description>Spring Cloud Netflix</description>
|
||||
<url>https://github.com/spring-cloud/spring-cloud-netflix</url>
|
||||
<parent>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-build</artifactId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<relativePath />
|
||||
</parent>
|
||||
<scm>
|
||||
@@ -20,69 +19,11 @@
|
||||
<developerConnection>scm:git:ssh://git@github.com/spring-cloud/spring-cloud-netflix.git</developerConnection>
|
||||
<tag>HEAD</tag>
|
||||
</scm>
|
||||
<licenses>
|
||||
<license>
|
||||
<name>Apache License, Version 2.0</name>
|
||||
<url>https://www.apache.org/licenses/LICENSE-2.0</url>
|
||||
</license>
|
||||
</licenses>
|
||||
<developers>
|
||||
<developer>
|
||||
<id>dsyer</id>
|
||||
<name>Dave Syer</name>
|
||||
<email>david.syer at broadcom.com</email>
|
||||
<organization>Broadcom, Inc.</organization>
|
||||
<organizationUrl>https://www.spring.io</organizationUrl>
|
||||
<roles>
|
||||
<role>lead</role>
|
||||
</roles>
|
||||
</developer>
|
||||
<developer>
|
||||
<id>sgibb</id>
|
||||
<name>Spencer Gibb</name>
|
||||
<email>spencer.gibb at broadcom.com</email>
|
||||
<organization>Broadcom, Inc.</organization>
|
||||
<organizationUrl>https://www.spring.io</organizationUrl>
|
||||
<roles>
|
||||
<role>lead</role>
|
||||
</roles>
|
||||
</developer>
|
||||
<developer>
|
||||
<id>mgrzejszczak</id>
|
||||
<name>Marcin Grzejszczak</name>
|
||||
<email>>marcin.grzejszczak at broadcom.com</email>
|
||||
<organization>Broadcom, Inc.</organization>
|
||||
<organizationUrl>https://www.spring.io</organizationUrl>
|
||||
<roles>
|
||||
<role>developer</role>
|
||||
</roles>
|
||||
</developer>
|
||||
<developer>
|
||||
<id>rbaxter</id>
|
||||
<name>Ryan Baxter</name>
|
||||
<email>ryan.baxter at broadcom.com</email>
|
||||
<organization>Broadcom, Inc.</organization>
|
||||
<organizationUrl>https://www.spring.io</organizationUrl>
|
||||
<roles>
|
||||
<role>developer</role>
|
||||
</roles>
|
||||
</developer>
|
||||
<developer>
|
||||
<id>omaciaszeksharma</id>
|
||||
<name>Olga Maciaszek-Sharma</name>
|
||||
<email>olga.maciaszek-sharma at broadcom.com</email>
|
||||
<organization>Broadcom, Inc.</organization>
|
||||
<organizationUrl>https://www.spring.io</organizationUrl>
|
||||
<roles>
|
||||
<role>developer</role>
|
||||
</roles>
|
||||
</developer>
|
||||
</developers>
|
||||
<properties>
|
||||
<bintray.package>netflix</bintray.package>
|
||||
<spring-cloud-commons.version>5.0.0-M2</spring-cloud-commons.version>
|
||||
<spring-cloud-config.version>5.0.0-M2</spring-cloud-config.version>
|
||||
<testcontainers.version>1.21.3</testcontainers.version>
|
||||
<spring-cloud-commons.version>4.1.1-SNAPSHOT</spring-cloud-commons.version>
|
||||
<spring-cloud-config.version>4.1.1-SNAPSHOT</spring-cloud-config.version>
|
||||
<testcontainers.version>1.19.3</testcontainers.version>
|
||||
<mockserverclient.version>5.15.0</mockserverclient.version>
|
||||
|
||||
<!-- Sonar -->
|
||||
@@ -91,6 +32,8 @@
|
||||
<sonar.jacoco.reportPath>${project.basedir}/../target/jacoco.exec</sonar.jacoco.reportPath>
|
||||
<sonar.language>java</sonar.language>
|
||||
<maven-resources-plugin.version>3.1.0</maven-resources-plugin.version>
|
||||
<!-- FIXME: 4.0.0 -->
|
||||
<duplicate-finder-maven-plugin.skip>true</duplicate-finder-maven-plugin.skip>
|
||||
</properties>
|
||||
<build>
|
||||
<plugins>
|
||||
@@ -189,12 +132,6 @@
|
||||
<groupId>org.mock-server</groupId>
|
||||
<artifactId>mockserver-client-java</artifactId>
|
||||
<version>${mockserverclient.version}</version>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<groupId>commons-logging</groupId>
|
||||
<artifactId>commons-logging</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
</dependencyManagement>
|
||||
@@ -216,22 +153,6 @@
|
||||
<module>docs</module>
|
||||
</modules>
|
||||
<profiles>
|
||||
<profile>
|
||||
<id>central</id>
|
||||
<build>
|
||||
<plugins>
|
||||
<plugin>
|
||||
<groupId>org.sonatype.central</groupId>
|
||||
<artifactId>central-publishing-maven-plugin</artifactId>
|
||||
<configuration>
|
||||
<excludeArtifacts>
|
||||
<artifact>spring-cloud-netflix-eureka-client-tls-tests</artifact>
|
||||
</excludeArtifacts>
|
||||
</configuration>
|
||||
</plugin>
|
||||
</plugins>
|
||||
</build>
|
||||
</profile>
|
||||
<profile>
|
||||
<id>spring</id>
|
||||
<repositories>
|
||||
|
||||
@@ -5,16 +5,16 @@
|
||||
<parent>
|
||||
<artifactId>spring-cloud-dependencies-parent</artifactId>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<relativePath/>
|
||||
</parent>
|
||||
<artifactId>spring-cloud-netflix-dependencies</artifactId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<packaging>pom</packaging>
|
||||
<name>spring-cloud-netflix-dependencies</name>
|
||||
<description>Spring Cloud Netflix Dependencies</description>
|
||||
<properties>
|
||||
<eureka.version>2.0.5</eureka.version>
|
||||
<eureka.version>2.0.1</eureka.version>
|
||||
</properties>
|
||||
<dependencyManagement>
|
||||
<dependencies>
|
||||
@@ -138,12 +138,9 @@
|
||||
<groupId>aopalliance</groupId>
|
||||
<artifactId>aopalliance</artifactId>
|
||||
</exclusion>
|
||||
<exclusion>
|
||||
<groupId>commons-logging</groupId>
|
||||
<artifactId>commons-logging</artifactId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<!-- TODO: Move back to Eureka dependency when 1.10.17 released -->
|
||||
</dependencies>
|
||||
</dependencyManagement>
|
||||
<profiles>
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
<parent>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-netflix</artifactId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<relativePath>..</relativePath> <!-- lookup parent from repository -->
|
||||
</parent>
|
||||
<artifactId>spring-cloud-netflix-eureka-client-tls-tests</artifactId>
|
||||
@@ -92,17 +92,7 @@
|
||||
<artifactId>spring-boot-starter-test</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.junit.platform</groupId>
|
||||
<artifactId>junit-platform-suite-api</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.junit.platform</groupId>
|
||||
<artifactId>junit-platform-suite-engine</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
|
||||
<dependency>
|
||||
<groupId>org.junit.vintage</groupId>
|
||||
<artifactId>junit-vintage-engine</artifactId>
|
||||
@@ -114,11 +104,6 @@
|
||||
<version>1.70</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-restclient</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
<build>
|
||||
<plugins>
|
||||
|
||||
+3
-3
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -48,14 +48,14 @@ public class AppRunner implements AutoCloseable {
|
||||
SpringApplicationBuilder builder = new SpringApplicationBuilder(appClass);
|
||||
builder.properties("spring.application.name=" + appClass.getName());
|
||||
builder.properties("spring.jmx.enabled=false");
|
||||
builder.properties(String.format("server.port=%d", availableTcpPort()));
|
||||
builder.properties(String.format("server.port=%d", availabeTcpPort()));
|
||||
builder.properties(props());
|
||||
|
||||
app = builder.build().run();
|
||||
}
|
||||
}
|
||||
|
||||
private int availableTcpPort() {
|
||||
private int availabeTcpPort() {
|
||||
return TestSocketUtils.findAvailableTcpPort();
|
||||
}
|
||||
|
||||
|
||||
+14
-6
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -25,17 +25,17 @@ import java.util.function.Supplier;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.junit.jupiter.api.AfterAll;
|
||||
import org.junit.jupiter.api.Assertions;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.beans.factory.BeanCreationException;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
|
||||
|
||||
abstract class BaseCertTests {
|
||||
abstract class BaseCertTest {
|
||||
|
||||
private static final Log log = LogFactory.getLog(BaseCertTests.class);
|
||||
private static final Log log = LogFactory.getLog(BaseCertTest.class);
|
||||
|
||||
protected static final String KEY_STORE_PASSWORD = "test-key-store-password";
|
||||
|
||||
@@ -53,7 +53,7 @@ abstract class BaseCertTests {
|
||||
|
||||
protected static File wrongClientCert;
|
||||
|
||||
protected BaseCertTests() {
|
||||
protected BaseCertTest() {
|
||||
}
|
||||
|
||||
@SuppressWarnings("rawtypes")
|
||||
@@ -155,7 +155,15 @@ abstract class BaseCertTests {
|
||||
EurekaClientRunner client = createEurekaClient();
|
||||
enableTlsClient(client);
|
||||
client.setKeyStore(clientCert, WRONG_PASSWORD, WRONG_PASSWORD);
|
||||
assertThatExceptionOfType(BeanCreationException.class).isThrownBy(client::start);
|
||||
Assertions.assertThrows(BeanCreationException.class, client::start);
|
||||
}
|
||||
|
||||
@Test
|
||||
void nonExistKeyStoreCauseFailure() {
|
||||
EurekaClientRunner client = createEurekaClient();
|
||||
enableTlsClient(client);
|
||||
client.setKeyStore(new File("nonExistFile"));
|
||||
Assertions.assertThrows(BeanCreationException.class, client::start);
|
||||
}
|
||||
|
||||
@Test
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+5
-5
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,8 +16,8 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import org.junit.platform.suite.api.SelectClasses;
|
||||
import org.junit.platform.suite.api.Suite;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.junit.runners.Suite;
|
||||
|
||||
/**
|
||||
* We need to use a suite cause we need to first run all the Eureka Servers, then close
|
||||
@@ -26,8 +26,8 @@ import org.junit.platform.suite.api.Suite;
|
||||
* That means that when the new context starts we will fail cause the executor service is
|
||||
* already shutdown.
|
||||
*/
|
||||
@SelectClasses({ EurekaClientTests.class, RestTemplateEurekaClientTests.class })
|
||||
@Suite
|
||||
@RunWith(Suite.class)
|
||||
@Suite.SuiteClasses({ EurekaClientTest.class, RestTemplateEurekaClientTest.class })
|
||||
public class EurekaClientSuite {
|
||||
|
||||
}
|
||||
|
||||
+7
-24
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,25 +16,20 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import java.util.Collections;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
|
||||
import org.springframework.cloud.netflix.eureka.http.DefaultEurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateTransportClientFactories;
|
||||
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
public class EurekaClientTests extends BaseCertTests {
|
||||
public class EurekaClientTest extends BaseCertTest {
|
||||
|
||||
private static final Log LOG = LogFactory.getLog(EurekaClientTests.class);
|
||||
private static final Log log = LogFactory.getLog(EurekaClientTest.class);
|
||||
|
||||
static EurekaServerRunner server;
|
||||
|
||||
@@ -42,11 +37,11 @@ public class EurekaClientTests extends BaseCertTests {
|
||||
|
||||
@BeforeAll
|
||||
public static void setupAll() {
|
||||
server = startEurekaServer(EurekaClientTests.TestEurekaServer.class);
|
||||
service = startService(server, EurekaClientTests.TestApp.class);
|
||||
server = startEurekaServer(EurekaClientTest.TestEurekaServer.class);
|
||||
service = startService(server, EurekaClientTest.TestApp.class);
|
||||
assertThat(service.discoveryClientOptionalArgs()).isInstanceOf(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
LOG.info("Successfully asserted that Jersey will be used");
|
||||
waitForRegistration(() -> new EurekaClientTests().createEurekaClient());
|
||||
log.info("Successfully asserted that Jersey will be used");
|
||||
waitForRegistration(() -> new EurekaClientTest().createEurekaClient());
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -58,18 +53,6 @@ public class EurekaClientTests extends BaseCertTests {
|
||||
@EnableAutoConfiguration
|
||||
public static class TestApp {
|
||||
|
||||
@Bean
|
||||
public RestTemplateTransportClientFactories forceRestTemplateTransportClientFactories(
|
||||
RestTemplateDiscoveryClientOptionalArgs discoveryClientOptionalArgs) {
|
||||
return new RestTemplateTransportClientFactories(discoveryClientOptionalArgs);
|
||||
}
|
||||
|
||||
@Bean
|
||||
public RestTemplateDiscoveryClientOptionalArgs discoveryClientOptionalArgs() {
|
||||
return new RestTemplateDiscoveryClientOptionalArgs(new DefaultEurekaClientHttpRequestFactorySupplier(
|
||||
new RestTemplateTimeoutProperties(), Collections.emptySet()));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@SpringBootConfiguration
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
-106
@@ -1,106 +0,0 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.security.GeneralSecurityException;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.junit.jupiter.api.AfterAll;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.cloud.netflix.eureka.http.EurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientTransportClientFactories;
|
||||
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.web.client.RestClient;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.cloud.netflix.eureka.config.DiscoveryClientOptionalArgsConfiguration.setupTLS;
|
||||
|
||||
/**
|
||||
* Tests for verifying TLS setup with {@link RestClientTransportClientFactories}.
|
||||
*
|
||||
* @author Olga Maciaszek-Sharma
|
||||
*/
|
||||
public class RestClientEurekaClientTests extends BaseCertTests {
|
||||
|
||||
private static final Log LOG = LogFactory.getLog(RestClientEurekaClientTests.class);
|
||||
|
||||
private static EurekaServerRunner server;
|
||||
|
||||
private static EurekaClientRunner service;
|
||||
|
||||
@BeforeAll
|
||||
public static void setupAll() {
|
||||
server = startEurekaServer(TestEurekaServer.class);
|
||||
service = startService(server, TestApp.class);
|
||||
// Will use RestClient
|
||||
assertThat(service.discoveryClientOptionalArgs()).isInstanceOf(RestClientDiscoveryClientOptionalArgs.class);
|
||||
LOG.info("Successfully asserted that RestClient will be used");
|
||||
waitForRegistration(() -> new RestClientEurekaClientTests().createEurekaClient());
|
||||
}
|
||||
|
||||
@AfterAll
|
||||
public static void tearDownAll() {
|
||||
stopService(service);
|
||||
stopEurekaServer(server);
|
||||
}
|
||||
|
||||
@Override
|
||||
EurekaClientRunner createEurekaClient() {
|
||||
return new EurekaClientRunner(TestApp.class, server);
|
||||
}
|
||||
|
||||
@SpringBootConfiguration
|
||||
@EnableAutoConfiguration
|
||||
public static class TestApp {
|
||||
|
||||
// Want to force reusing exactly the same bean as on production without excluding
|
||||
// jersey from the classpath
|
||||
@Bean
|
||||
public RestClientDiscoveryClientOptionalArgs forceRestClientDiscoveryClientOptionalArgs(
|
||||
TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier)
|
||||
throws GeneralSecurityException, IOException {
|
||||
RestClientDiscoveryClientOptionalArgs result = new RestClientDiscoveryClientOptionalArgs(
|
||||
eurekaClientHttpRequestFactorySupplier, RestClient::builder);
|
||||
setupTLS(result, tlsProperties);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public RestClientTransportClientFactories forceRestClientTransportClientFactories(
|
||||
RestClientDiscoveryClientOptionalArgs discoveryClientOptionalArgs) {
|
||||
return new RestClientTransportClientFactories(discoveryClientOptionalArgs);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@SpringBootConfiguration
|
||||
@EnableAutoConfiguration
|
||||
@EnableEurekaServer
|
||||
public static class TestEurekaServer {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
+13
-28
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2018-present the original author or authors.
|
||||
* Copyright 2018-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -26,21 +26,18 @@ import org.junit.jupiter.api.BeforeAll;
|
||||
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
|
||||
import org.springframework.boot.restclient.RestTemplateBuilder;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.cloud.netflix.eureka.http.DefaultEurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.config.DiscoveryClientOptionalArgsConfiguration;
|
||||
import org.springframework.cloud.netflix.eureka.http.EurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateTransportClientFactories;
|
||||
import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.cloud.netflix.eureka.config.DiscoveryClientOptionalArgsConfiguration.setupTLS;
|
||||
|
||||
public class RestTemplateEurekaClientTests extends BaseCertTests {
|
||||
public class RestTemplateEurekaClientTest extends BaseCertTest {
|
||||
|
||||
private static final Log log = LogFactory.getLog(RestTemplateEurekaClientTests.class);
|
||||
private static final Log log = LogFactory.getLog(RestTemplateEurekaClientTest.class);
|
||||
|
||||
private static EurekaServerRunner server;
|
||||
|
||||
@@ -48,12 +45,12 @@ public class RestTemplateEurekaClientTests extends BaseCertTests {
|
||||
|
||||
@BeforeAll
|
||||
public static void setupAll() {
|
||||
server = startEurekaServer(TestEurekaServer.class);
|
||||
service = startService(server, RestTemplateEurekaClientTests.RestTemplateTestApp.class);
|
||||
server = startEurekaServer(RestTemplateEurekaClientTest.RestTemplateTestEurekaServer.class);
|
||||
service = startService(server, RestTemplateEurekaClientTest.RestTemplateTestApp.class);
|
||||
// Will use RestTemplate
|
||||
assertThat(service.discoveryClientOptionalArgs()).isInstanceOf(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
log.info("Successfully asserted that RestTemplate will be used");
|
||||
waitForRegistration(() -> new RestTemplateEurekaClientTests().createEurekaClient());
|
||||
waitForRegistration(() -> new RestTemplateEurekaClientTest().createEurekaClient());
|
||||
}
|
||||
|
||||
@AfterAll
|
||||
@@ -71,27 +68,15 @@ public class RestTemplateEurekaClientTests extends BaseCertTests {
|
||||
@EnableAutoConfiguration
|
||||
public static class RestTemplateTestApp {
|
||||
|
||||
// Want to force reusing exactly the same bean as on production without excluding
|
||||
// jersey from the classpath
|
||||
@Bean
|
||||
public RestTemplateDiscoveryClientOptionalArgs forceRestTemplateDiscoveryClientOptionalArgs(
|
||||
TlsProperties tlsProperties,
|
||||
TlsProperties tlsProperties, DiscoveryClientOptionalArgsConfiguration configuration,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier)
|
||||
throws GeneralSecurityException, IOException {
|
||||
RestTemplateDiscoveryClientOptionalArgs result = new RestTemplateDiscoveryClientOptionalArgs(
|
||||
eurekaClientHttpRequestFactorySupplier, RestTemplateBuilder::new);
|
||||
setupTLS(result, tlsProperties);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Bean
|
||||
public RestTemplateTransportClientFactories forceRestTemplateTransportClientFactories(
|
||||
RestTemplateDiscoveryClientOptionalArgs discoveryClientOptionalArgs) {
|
||||
return new RestTemplateTransportClientFactories(discoveryClientOptionalArgs);
|
||||
}
|
||||
|
||||
@Bean
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier(
|
||||
RestTemplateTimeoutProperties restTemplateTimeoutProperties) {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier(restTemplateTimeoutProperties);
|
||||
return configuration.restTemplateDiscoveryClientOptionalArgs(tlsProperties,
|
||||
eurekaClientHttpRequestFactorySupplier);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -99,7 +84,7 @@ public class RestTemplateEurekaClientTests extends BaseCertTests {
|
||||
@SpringBootConfiguration
|
||||
@EnableAutoConfiguration
|
||||
@EnableEurekaServer
|
||||
public static class TestEurekaServer {
|
||||
public static class RestTemplateTestEurekaServer {
|
||||
|
||||
}
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
<parent>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-netflix</artifactId>
|
||||
<version>5.0.0-M2</version>
|
||||
<version>4.1.1-SNAPSHOT</version>
|
||||
<relativePath>..</relativePath> <!-- lookup parent from repository -->
|
||||
</parent>
|
||||
<artifactId>spring-cloud-netflix-eureka-client</artifactId>
|
||||
@@ -23,21 +23,6 @@
|
||||
<artifactId>spring-boot-configuration-processor</artifactId>
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-http-codec</artifactId>
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-restclient</artifactId>
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-webclient</artifactId>
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-actuator</artifactId>
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+15
-38
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -193,43 +193,20 @@ public class CloudEurekaTransportConfig implements EurekaTransportConfig {
|
||||
@Override
|
||||
public String toString() {
|
||||
return new StringBuilder("CloudEurekaTransportConfig{").append("sessionedClientReconnectIntervalSeconds=")
|
||||
.append(sessionedClientReconnectIntervalSeconds)
|
||||
.append(", ")
|
||||
.append("retryableClientQuarantineRefreshPercentage=")
|
||||
.append(retryableClientQuarantineRefreshPercentage)
|
||||
.append(", ")
|
||||
.append("bootstrapResolverRefreshIntervalSeconds=")
|
||||
.append(bootstrapResolverRefreshIntervalSeconds)
|
||||
.append(", ")
|
||||
.append("applicationsResolverDataStalenessThresholdSeconds=")
|
||||
.append(applicationsResolverDataStalenessThresholdSeconds)
|
||||
.append(", ")
|
||||
.append("asyncResolverRefreshIntervalMs=")
|
||||
.append(asyncResolverRefreshIntervalMs)
|
||||
.append(", ")
|
||||
.append("asyncResolverWarmUpTimeoutMs=")
|
||||
.append(asyncResolverWarmUpTimeoutMs)
|
||||
.append(", ")
|
||||
.append("asyncExecutorThreadPoolSize=")
|
||||
.append(asyncExecutorThreadPoolSize)
|
||||
.append(", ")
|
||||
.append("readClusterVip='")
|
||||
.append(readClusterVip)
|
||||
.append("', ")
|
||||
.append("writeClusterVip='")
|
||||
.append(writeClusterVip)
|
||||
.append("', ")
|
||||
.append("bootstrapResolverForQuery=")
|
||||
.append(bootstrapResolverForQuery)
|
||||
.append(", ")
|
||||
.append("bootstrapResolverStrategy='")
|
||||
.append(bootstrapResolverStrategy)
|
||||
.append("', ")
|
||||
.append("applicationsResolverUseIp=")
|
||||
.append(applicationsResolverUseIp)
|
||||
.append(", ")
|
||||
.append("}")
|
||||
.toString();
|
||||
.append(sessionedClientReconnectIntervalSeconds).append(", ")
|
||||
.append("retryableClientQuarantineRefreshPercentage=")
|
||||
.append(retryableClientQuarantineRefreshPercentage).append(", ")
|
||||
.append("bootstrapResolverRefreshIntervalSeconds=").append(bootstrapResolverRefreshIntervalSeconds)
|
||||
.append(", ").append("applicationsResolverDataStalenessThresholdSeconds=")
|
||||
.append(applicationsResolverDataStalenessThresholdSeconds).append(", ")
|
||||
.append("asyncResolverRefreshIntervalMs=").append(asyncResolverRefreshIntervalMs).append(", ")
|
||||
.append("asyncResolverWarmUpTimeoutMs=").append(asyncResolverWarmUpTimeoutMs).append(", ")
|
||||
.append("asyncExecutorThreadPoolSize=").append(asyncExecutorThreadPoolSize).append(", ")
|
||||
.append("readClusterVip='").append(readClusterVip).append("', ").append("writeClusterVip='")
|
||||
.append(writeClusterVip).append("', ").append("bootstrapResolverForQuery=")
|
||||
.append(bootstrapResolverForQuery).append(", ").append("bootstrapResolverStrategy='")
|
||||
.append(bootstrapResolverStrategy).append("', ").append("applicationsResolverUseIp=")
|
||||
.append(applicationsResolverUseIp).append(", ").append("}").toString();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+78
-41
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2023 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -56,6 +56,8 @@ import org.springframework.aot.hint.RuntimeHintsRegistrar;
|
||||
import org.springframework.aot.hint.TypeReference;
|
||||
import org.springframework.beans.factory.ObjectProvider;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.actuate.autoconfigure.health.ConditionalOnEnabledHealthIndicator;
|
||||
import org.springframework.boot.actuate.health.Health;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureAfter;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigureBefore;
|
||||
import org.springframework.boot.autoconfigure.condition.AnyNestedCondition;
|
||||
@@ -66,8 +68,6 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingClas
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.autoconfigure.condition.SearchStrategy;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.boot.health.autoconfigure.contributor.ConditionalOnEnabledHealthIndicator;
|
||||
import org.springframework.boot.health.contributor.Health;
|
||||
import org.springframework.cloud.autoconfigure.RefreshAutoConfiguration;
|
||||
import org.springframework.cloud.client.CommonsClientAutoConfiguration;
|
||||
import org.springframework.cloud.client.ConditionalOnDiscoveryEnabled;
|
||||
@@ -103,7 +103,6 @@ import static org.springframework.cloud.commons.util.IdUtils.getDefaultInstanceI
|
||||
* @author Daniel Lavoie
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @author Tim Ysewyn
|
||||
* @author Robert Bleyl
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@EnableConfigurationProperties
|
||||
@@ -225,8 +224,8 @@ public class EurekaClientAutoConfiguration {
|
||||
}
|
||||
|
||||
@Bean
|
||||
public EurekaServiceRegistry eurekaServiceRegistry(EurekaInstanceConfigBean eurekaInstanceConfigBean) {
|
||||
return new EurekaServiceRegistry(eurekaInstanceConfigBean);
|
||||
public EurekaServiceRegistry eurekaServiceRegistry() {
|
||||
return new EurekaServiceRegistry();
|
||||
}
|
||||
|
||||
// @Bean
|
||||
@@ -281,11 +280,8 @@ public class EurekaClientAutoConfiguration {
|
||||
public EurekaRegistration eurekaRegistration(EurekaClient eurekaClient,
|
||||
CloudEurekaInstanceConfig instanceConfig, ApplicationInfoManager applicationInfoManager,
|
||||
@Autowired(required = false) ObjectProvider<HealthCheckHandler> healthCheckHandler) {
|
||||
return EurekaRegistration.builder(instanceConfig)
|
||||
.with(applicationInfoManager)
|
||||
.with(eurekaClient)
|
||||
.with(healthCheckHandler)
|
||||
.build();
|
||||
return EurekaRegistration.builder(instanceConfig).with(applicationInfoManager).with(eurekaClient)
|
||||
.with(healthCheckHandler).build();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -343,11 +339,8 @@ public class EurekaClientAutoConfiguration {
|
||||
public EurekaRegistration eurekaRegistration(EurekaClient eurekaClient,
|
||||
CloudEurekaInstanceConfig instanceConfig, ApplicationInfoManager applicationInfoManager,
|
||||
@Autowired(required = false) ObjectProvider<HealthCheckHandler> healthCheckHandler) {
|
||||
return EurekaRegistration.builder(instanceConfig)
|
||||
.with(applicationInfoManager)
|
||||
.with(eurekaClient)
|
||||
.with(healthCheckHandler)
|
||||
.build();
|
||||
return EurekaRegistration.builder(instanceConfig).with(applicationInfoManager).with(eurekaClient)
|
||||
.with(healthCheckHandler).build();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -399,7 +392,6 @@ public class EurekaClientAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
@ConditionalOnClass(ConditionalOnEnabledHealthIndicator.class)
|
||||
@ConditionalOnEnabledHealthIndicator("eureka")
|
||||
public EurekaHealthIndicator eurekaHealthIndicator(EurekaClient eurekaClient,
|
||||
EurekaInstanceConfig instanceConfig, EurekaClientConfig clientConfig) {
|
||||
@@ -418,30 +410,75 @@ class EurekaClientHints implements RuntimeHintsRegistrar {
|
||||
if (!ClassUtils.isPresent("com.netflix.discovery.DiscoveryClient", classLoader)) {
|
||||
return;
|
||||
}
|
||||
hints.reflection()
|
||||
.registerTypes(TypeReference.listOf(ApplicationInfoManager.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS))
|
||||
.registerTypes(
|
||||
TypeReference.listOf(DiscoveryClient.class, EurekaHttpClientDecorator.class,
|
||||
InstanceInfo.ActionType.class, InstanceInfoJsonMixIn.class, SessionedEurekaHttpClient.class,
|
||||
RetryableEurekaHttpClient.class, AsyncResolver.class, Applications.class,
|
||||
TimedSupervisorTask.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS,
|
||||
MemberCategory.INTROSPECT_DECLARED_METHODS))
|
||||
.registerTypes(
|
||||
TypeReference.listOf(EurekaEndpoint.class, EurekaHttpClientDecorator.RequestExecutor.class,
|
||||
EurekaClient.class, DiscoveryClient.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS))
|
||||
.registerTypes(TypeReference.listOf(DataCenterTypeInfoResolver.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_PUBLIC_CONSTRUCTORS))
|
||||
.registerTypes(TypeReference.listOf(Application.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS, MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_PUBLIC_CONSTRUCTORS))
|
||||
.registerTypes(TypeReference.listOf(DefaultEndpoint.class, EurekaHttpResponse.class, InstanceInfo.class,
|
||||
InstanceInfo.PortWrapper.class, LeaseInfo.class, MyDataCenterInfo.class, DataCenterInfo.class,
|
||||
DataCenterInfo.Name.class, ApplicationsJacksonBuilder.class, EurekaServiceInstance.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS, MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS));
|
||||
hints.reflection().registerType(TypeReference.of(DiscoveryClient.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS, MemberCategory.INTROSPECT_DECLARED_METHODS))
|
||||
.registerType(TypeReference.of(EurekaEndpoint.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS))
|
||||
.registerType(TypeReference.of(DefaultEndpoint.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS, MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS))
|
||||
.registerType(TypeReference.of(EurekaHttpClientDecorator.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS,
|
||||
MemberCategory.INTROSPECT_DECLARED_METHODS))
|
||||
.registerType(TypeReference.of(EurekaHttpResponse.class),
|
||||
hint -> hint.withMembers(MemberCategory.DECLARED_FIELDS, MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS))
|
||||
.registerType(TypeReference.of(EurekaHttpClientDecorator.RequestExecutor.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS))
|
||||
.registerType(TypeReference.of(ApplicationInfoManager.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS))
|
||||
.registerType(TypeReference.of(InstanceInfo.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS, MemberCategory.DECLARED_FIELDS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS))
|
||||
.registerType(TypeReference.of(InstanceInfo.ActionType.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(InstanceInfo.PortWrapper.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(LeaseInfo.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(MyDataCenterInfo.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(DataCenterInfo.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(DataCenterInfo.Name.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(EurekaClient.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_PUBLIC_METHODS))
|
||||
.registerType(TypeReference.of(TimedSupervisorTask.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(DataCenterTypeInfoResolver.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_PUBLIC_CONSTRUCTORS))
|
||||
.registerType(TypeReference.of(ApplicationsJacksonBuilder.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(InstanceInfoJsonMixIn.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(Application.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_PUBLIC_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(Applications.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(AsyncResolver.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(RetryableEurekaHttpClient.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(SessionedEurekaHttpClient.class),
|
||||
hint -> hint.withMembers(MemberCategory.INTROSPECT_DECLARED_METHODS,
|
||||
MemberCategory.DECLARED_FIELDS))
|
||||
.registerType(TypeReference.of(EurekaServiceInstance.class),
|
||||
hint -> hint.withMembers(MemberCategory.INVOKE_DECLARED_METHODS,
|
||||
MemberCategory.INVOKE_DECLARED_CONSTRUCTORS, MemberCategory.DECLARED_FIELDS));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+45
-144
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -41,7 +41,6 @@ import static org.springframework.cloud.netflix.eureka.EurekaConstants.DEFAULT_P
|
||||
*
|
||||
* @author Dave Syer
|
||||
* @author Gregor Zurowski
|
||||
* @author Mooyong Lee
|
||||
*/
|
||||
@ConfigurationProperties(EurekaClientConfigBean.PREFIX)
|
||||
public class EurekaClientConfigBean implements EurekaClientConfig, Ordered {
|
||||
@@ -61,6 +60,8 @@ public class EurekaClientConfigBean implements EurekaClientConfig, Ordered {
|
||||
*/
|
||||
public static final String DEFAULT_ZONE = "defaultZone";
|
||||
|
||||
private static final int MINUTES = 60;
|
||||
|
||||
@Autowired(required = false)
|
||||
PropertyResolver propertyResolver;
|
||||
|
||||
@@ -95,7 +96,7 @@ public class EurekaClientConfigBean implements EurekaClientConfig, Ordered {
|
||||
* Eureka servers could be added or removed and this setting controls how soon the
|
||||
* eureka clients should know about it.
|
||||
*/
|
||||
private int eurekaServiceUrlPollIntervalSeconds = 300; // 5 * MINUTES
|
||||
private int eurekaServiceUrlPollIntervalSeconds = 5 * MINUTES;
|
||||
|
||||
/**
|
||||
* Gets the proxy port to eureka server if any.
|
||||
@@ -997,147 +998,47 @@ public class EurekaClientConfigBean implements EurekaClientConfig, Ordered {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return new StringBuilder("EurekaClientConfigBean{").append("propertyResolver=")
|
||||
.append(propertyResolver)
|
||||
.append(", ")
|
||||
.append("enabled=")
|
||||
.append(enabled)
|
||||
.append(", ")
|
||||
.append("transport=")
|
||||
.append(transport)
|
||||
.append(", ")
|
||||
.append("registryFetchIntervalSeconds=")
|
||||
.append(registryFetchIntervalSeconds)
|
||||
.append(", ")
|
||||
.append("instanceInfoReplicationIntervalSeconds=")
|
||||
.append(instanceInfoReplicationIntervalSeconds)
|
||||
.append(", ")
|
||||
.append("initialInstanceInfoReplicationIntervalSeconds=")
|
||||
.append(initialInstanceInfoReplicationIntervalSeconds)
|
||||
.append(", ")
|
||||
.append("eurekaServiceUrlPollIntervalSeconds=")
|
||||
.append(eurekaServiceUrlPollIntervalSeconds)
|
||||
.append(", ")
|
||||
.append("proxyPort='")
|
||||
.append(proxyPort)
|
||||
.append("', ")
|
||||
.append("proxyHost='")
|
||||
.append(proxyHost)
|
||||
.append("', ")
|
||||
.append("proxyUserName='")
|
||||
.append(proxyUserName)
|
||||
.append("', ")
|
||||
.append("proxyPassword='")
|
||||
.append(proxyPassword)
|
||||
.append("', ")
|
||||
.append("eurekaServerReadTimeoutSeconds=")
|
||||
.append(eurekaServerReadTimeoutSeconds)
|
||||
.append(", ")
|
||||
.append("eurekaServerConnectTimeoutSeconds=")
|
||||
.append(eurekaServerConnectTimeoutSeconds)
|
||||
.append(", ")
|
||||
.append("backupRegistryImpl='")
|
||||
.append(backupRegistryImpl)
|
||||
.append("', ")
|
||||
.append("eurekaServerTotalConnections=")
|
||||
.append(eurekaServerTotalConnections)
|
||||
.append(", ")
|
||||
.append("eurekaServerTotalConnectionsPerHost=")
|
||||
.append(eurekaServerTotalConnectionsPerHost)
|
||||
.append(", ")
|
||||
.append("eurekaServerURLContext='")
|
||||
.append(eurekaServerURLContext)
|
||||
.append("', ")
|
||||
.append("eurekaServerPort='")
|
||||
.append(eurekaServerPort)
|
||||
.append("', ")
|
||||
.append("eurekaServerDNSName='")
|
||||
.append(eurekaServerDNSName)
|
||||
.append("', ")
|
||||
.append("region='")
|
||||
.append(region)
|
||||
.append("', ")
|
||||
.append("eurekaConnectionIdleTimeoutSeconds=")
|
||||
.append(eurekaConnectionIdleTimeoutSeconds)
|
||||
.append(", ")
|
||||
.append("registryRefreshSingleVipAddress='")
|
||||
.append(registryRefreshSingleVipAddress)
|
||||
.append("', ")
|
||||
.append("heartbeatExecutorThreadPoolSize=")
|
||||
.append(heartbeatExecutorThreadPoolSize)
|
||||
.append(", ")
|
||||
.append("heartbeatExecutorExponentialBackOffBound=")
|
||||
.append(heartbeatExecutorExponentialBackOffBound)
|
||||
.append(", ")
|
||||
.append("cacheRefreshExecutorThreadPoolSize=")
|
||||
.append(cacheRefreshExecutorThreadPoolSize)
|
||||
.append(", ")
|
||||
.append("cacheRefreshExecutorExponentialBackOffBound=")
|
||||
.append(cacheRefreshExecutorExponentialBackOffBound)
|
||||
.append(", ")
|
||||
.append("serviceUrl=")
|
||||
.append(serviceUrl)
|
||||
.append(", ")
|
||||
.append("gZipContent=")
|
||||
.append(gZipContent)
|
||||
.append(", ")
|
||||
.append("useDnsForFetchingServiceUrls=")
|
||||
.append(useDnsForFetchingServiceUrls)
|
||||
.append(", ")
|
||||
.append("registerWithEureka=")
|
||||
.append(registerWithEureka)
|
||||
.append(", ")
|
||||
.append("preferSameZoneEureka=")
|
||||
.append(preferSameZoneEureka)
|
||||
.append(", ")
|
||||
.append("logDeltaDiff=")
|
||||
.append(logDeltaDiff)
|
||||
.append(", ")
|
||||
.append("disableDelta=")
|
||||
.append(disableDelta)
|
||||
.append(", ")
|
||||
.append("fetchRemoteRegionsRegistry='")
|
||||
.append(fetchRemoteRegionsRegistry)
|
||||
.append("', ")
|
||||
.append("availabilityZones=")
|
||||
.append(availabilityZones)
|
||||
.append(", ")
|
||||
.append("filterOnlyUpInstances=")
|
||||
.append(filterOnlyUpInstances)
|
||||
.append(", ")
|
||||
.append("fetchRegistry=")
|
||||
.append(fetchRegistry)
|
||||
.append(", ")
|
||||
.append("dollarReplacement='")
|
||||
.append(dollarReplacement)
|
||||
.append("', ")
|
||||
.append("escapeCharReplacement='")
|
||||
.append(escapeCharReplacement)
|
||||
.append("', ")
|
||||
.append("allowRedirects=")
|
||||
.append(allowRedirects)
|
||||
.append(", ")
|
||||
.append("onDemandUpdateStatusChange=")
|
||||
.append(onDemandUpdateStatusChange)
|
||||
.append(", ")
|
||||
.append("encoderName='")
|
||||
.append(encoderName)
|
||||
.append("', ")
|
||||
.append("decoderName='")
|
||||
.append(decoderName)
|
||||
.append("', ")
|
||||
.append("clientDataAccept='")
|
||||
.append(clientDataAccept)
|
||||
.append("', ")
|
||||
.append("shouldUnregisterOnShutdown='")
|
||||
.append(shouldUnregisterOnShutdown)
|
||||
.append("shouldEnforceRegistrationAtInit='")
|
||||
.append(shouldEnforceRegistrationAtInit)
|
||||
.append("', ")
|
||||
.append("order='")
|
||||
.append(order)
|
||||
.append("'}")
|
||||
.toString();
|
||||
return new StringBuilder("EurekaClientConfigBean{").append("propertyResolver=").append(propertyResolver)
|
||||
.append(", ").append("enabled=").append(enabled).append(", ").append("transport=").append(transport)
|
||||
.append(", ").append("registryFetchIntervalSeconds=").append(registryFetchIntervalSeconds).append(", ")
|
||||
.append("instanceInfoReplicationIntervalSeconds=").append(instanceInfoReplicationIntervalSeconds)
|
||||
.append(", ").append("initialInstanceInfoReplicationIntervalSeconds=")
|
||||
.append(initialInstanceInfoReplicationIntervalSeconds).append(", ")
|
||||
.append("eurekaServiceUrlPollIntervalSeconds=").append(eurekaServiceUrlPollIntervalSeconds).append(", ")
|
||||
.append("proxyPort='").append(proxyPort).append("', ").append("proxyHost='").append(proxyHost)
|
||||
.append("', ").append("proxyUserName='").append(proxyUserName).append("', ").append("proxyPassword='")
|
||||
.append(proxyPassword).append("', ").append("eurekaServerReadTimeoutSeconds=")
|
||||
.append(eurekaServerReadTimeoutSeconds).append(", ").append("eurekaServerConnectTimeoutSeconds=")
|
||||
.append(eurekaServerConnectTimeoutSeconds).append(", ").append("backupRegistryImpl='")
|
||||
.append(backupRegistryImpl).append("', ").append("eurekaServerTotalConnections=")
|
||||
.append(eurekaServerTotalConnections).append(", ").append("eurekaServerTotalConnectionsPerHost=")
|
||||
.append(eurekaServerTotalConnectionsPerHost).append(", ").append("eurekaServerURLContext='")
|
||||
.append(eurekaServerURLContext).append("', ").append("eurekaServerPort='").append(eurekaServerPort)
|
||||
.append("', ").append("eurekaServerDNSName='").append(eurekaServerDNSName).append("', ")
|
||||
.append("region='").append(region).append("', ").append("eurekaConnectionIdleTimeoutSeconds=")
|
||||
.append(eurekaConnectionIdleTimeoutSeconds).append(", ").append("registryRefreshSingleVipAddress='")
|
||||
.append(registryRefreshSingleVipAddress).append("', ").append("heartbeatExecutorThreadPoolSize=")
|
||||
.append(heartbeatExecutorThreadPoolSize).append(", ")
|
||||
.append("heartbeatExecutorExponentialBackOffBound=").append(heartbeatExecutorExponentialBackOffBound)
|
||||
.append(", ").append("cacheRefreshExecutorThreadPoolSize=").append(cacheRefreshExecutorThreadPoolSize)
|
||||
.append(", ").append("cacheRefreshExecutorExponentialBackOffBound=")
|
||||
.append(cacheRefreshExecutorExponentialBackOffBound).append(", ").append("serviceUrl=")
|
||||
.append(serviceUrl).append(", ").append("gZipContent=").append(gZipContent).append(", ")
|
||||
.append("useDnsForFetchingServiceUrls=").append(useDnsForFetchingServiceUrls).append(", ")
|
||||
.append("registerWithEureka=").append(registerWithEureka).append(", ").append("preferSameZoneEureka=")
|
||||
.append(preferSameZoneEureka).append(", ").append("logDeltaDiff=").append(logDeltaDiff).append(", ")
|
||||
.append("disableDelta=").append(disableDelta).append(", ").append("fetchRemoteRegionsRegistry='")
|
||||
.append(fetchRemoteRegionsRegistry).append("', ").append("availabilityZones=").append(availabilityZones)
|
||||
.append(", ").append("filterOnlyUpInstances=").append(filterOnlyUpInstances).append(", ")
|
||||
.append("fetchRegistry=").append(fetchRegistry).append(", ").append("dollarReplacement='")
|
||||
.append(dollarReplacement).append("', ").append("escapeCharReplacement='").append(escapeCharReplacement)
|
||||
.append("', ").append("allowRedirects=").append(allowRedirects).append(", ")
|
||||
.append("onDemandUpdateStatusChange=").append(onDemandUpdateStatusChange).append(", ")
|
||||
.append("encoderName='").append(encoderName).append("', ").append("decoderName='").append(decoderName)
|
||||
.append("', ").append("clientDataAccept='").append(clientDataAccept).append("', ")
|
||||
.append("shouldUnregisterOnShutdown='").append(shouldUnregisterOnShutdown)
|
||||
.append("shouldEnforceRegistrationAtInit='").append(shouldEnforceRegistrationAtInit).append("', ")
|
||||
.append("order='").append(order).append("'}").toString();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+2
-4
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -19,7 +19,6 @@ package org.springframework.cloud.netflix.eureka;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.discovery.EurekaClient;
|
||||
@@ -36,7 +35,6 @@ import org.springframework.core.Ordered;
|
||||
*
|
||||
* @author Spencer Gibb
|
||||
* @author Tim Ysewyn
|
||||
* @author Olga Maciaszek-Sharma
|
||||
*/
|
||||
public class EurekaDiscoveryClient implements DiscoveryClient {
|
||||
|
||||
@@ -81,7 +79,7 @@ public class EurekaDiscoveryClient implements DiscoveryClient {
|
||||
if (app.getInstances().isEmpty()) {
|
||||
continue;
|
||||
}
|
||||
names.add(app.getName().toLowerCase(Locale.ROOT));
|
||||
names.add(app.getName().toLowerCase());
|
||||
|
||||
}
|
||||
return names;
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+14
-15
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -27,17 +27,16 @@ import com.netflix.appinfo.InstanceInfo.InstanceStatus;
|
||||
|
||||
import org.springframework.beans.BeansException;
|
||||
import org.springframework.beans.factory.InitializingBean;
|
||||
import org.springframework.boot.actuate.health.CompositeHealthContributor;
|
||||
import org.springframework.boot.actuate.health.CompositeReactiveHealthContributor;
|
||||
import org.springframework.boot.actuate.health.Health;
|
||||
import org.springframework.boot.actuate.health.HealthContributor;
|
||||
import org.springframework.boot.actuate.health.HealthIndicator;
|
||||
import org.springframework.boot.actuate.health.NamedContributor;
|
||||
import org.springframework.boot.actuate.health.ReactiveHealthContributor;
|
||||
import org.springframework.boot.actuate.health.ReactiveHealthIndicator;
|
||||
import org.springframework.boot.actuate.health.Status;
|
||||
import org.springframework.boot.actuate.health.StatusAggregator;
|
||||
import org.springframework.boot.health.contributor.CompositeHealthContributor;
|
||||
import org.springframework.boot.health.contributor.CompositeReactiveHealthContributor;
|
||||
import org.springframework.boot.health.contributor.Health;
|
||||
import org.springframework.boot.health.contributor.HealthContributor;
|
||||
import org.springframework.boot.health.contributor.HealthContributors;
|
||||
import org.springframework.boot.health.contributor.HealthIndicator;
|
||||
import org.springframework.boot.health.contributor.ReactiveHealthContributor;
|
||||
import org.springframework.boot.health.contributor.ReactiveHealthContributors;
|
||||
import org.springframework.boot.health.contributor.ReactiveHealthIndicator;
|
||||
import org.springframework.boot.health.contributor.Status;
|
||||
import org.springframework.cloud.client.discovery.health.DiscoveryCompositeHealthContributor;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.context.ApplicationContextAware;
|
||||
@@ -155,8 +154,8 @@ public class EurekaHealthCheckHandler
|
||||
|
||||
private void processContributor(Set<Status> statusSet, HealthContributor contributor) {
|
||||
if (contributor instanceof CompositeHealthContributor) {
|
||||
for (HealthContributors.Entry contrib : (CompositeHealthContributor) contributor) {
|
||||
processContributor(statusSet, contrib.contributor());
|
||||
for (NamedContributor<HealthContributor> contrib : (CompositeHealthContributor) contributor) {
|
||||
processContributor(statusSet, contrib.getContributor());
|
||||
}
|
||||
}
|
||||
else if (contributor instanceof HealthIndicator) {
|
||||
@@ -166,8 +165,8 @@ public class EurekaHealthCheckHandler
|
||||
|
||||
private void processContributor(Set<Status> statusSet, ReactiveHealthContributor contributor) {
|
||||
if (contributor instanceof CompositeReactiveHealthContributor) {
|
||||
for (ReactiveHealthContributors.Entry contrib : (CompositeReactiveHealthContributor) contributor) {
|
||||
processContributor(statusSet, contrib.contributor());
|
||||
for (NamedContributor<ReactiveHealthContributor> contrib : (CompositeReactiveHealthContributor) contributor) {
|
||||
processContributor(statusSet, contrib.getContributor());
|
||||
}
|
||||
}
|
||||
else if (contributor instanceof ReactiveHealthIndicator) {
|
||||
|
||||
+4
-4
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -28,9 +28,9 @@ import com.netflix.discovery.shared.Application;
|
||||
import com.netflix.discovery.shared.Applications;
|
||||
|
||||
import org.springframework.aop.support.AopUtils;
|
||||
import org.springframework.boot.health.contributor.Health;
|
||||
import org.springframework.boot.health.contributor.Health.Builder;
|
||||
import org.springframework.boot.health.contributor.Status;
|
||||
import org.springframework.boot.actuate.health.Health;
|
||||
import org.springframework.boot.actuate.health.Health.Builder;
|
||||
import org.springframework.boot.actuate.health.Status;
|
||||
import org.springframework.cloud.client.discovery.health.DiscoveryHealthIndicator;
|
||||
import org.springframework.cloud.util.ProxyUtils;
|
||||
|
||||
|
||||
+25
-116
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -38,7 +38,6 @@ import org.springframework.util.StringUtils;
|
||||
* @author Spencer Gibb
|
||||
* @author Ryan Baxter
|
||||
* @author Gregor Zurowski
|
||||
* @author Robert Bleyl
|
||||
*/
|
||||
@ConfigurationProperties("eureka.instance")
|
||||
public class EurekaInstanceConfigBean implements CloudEurekaInstanceConfig, EnvironmentAware {
|
||||
@@ -270,12 +269,6 @@ public class EurekaInstanceConfigBean implements CloudEurekaInstanceConfig, Envi
|
||||
*/
|
||||
private boolean preferIpAddress = false;
|
||||
|
||||
/**
|
||||
* If true the EurekaClient will be initialized asynchronously when the
|
||||
* InstanceRegistry bean is created.
|
||||
*/
|
||||
private boolean asyncClientInitialization;
|
||||
|
||||
/**
|
||||
* Initial status to register with remote Eureka server.
|
||||
*/
|
||||
@@ -554,14 +547,6 @@ public class EurekaInstanceConfigBean implements CloudEurekaInstanceConfig, Envi
|
||||
this.preferIpAddress = preferIpAddress;
|
||||
}
|
||||
|
||||
public boolean isAsyncClientInitialization() {
|
||||
return asyncClientInitialization;
|
||||
}
|
||||
|
||||
public void setAsyncClientInitialization(boolean asyncClientInitialization) {
|
||||
this.asyncClientInitialization = asyncClientInitialization;
|
||||
}
|
||||
|
||||
public InstanceStatus getInitialStatus() {
|
||||
return initialStatus;
|
||||
}
|
||||
@@ -612,7 +597,6 @@ public class EurekaInstanceConfigBean implements CloudEurekaInstanceConfig, Envi
|
||||
&& Objects.equals(namespace, that.namespace) && Objects.equals(hostname, that.hostname)
|
||||
&& preferIpAddress == that.preferIpAddress && Objects.equals(initialStatus, that.initialStatus)
|
||||
&& Arrays.equals(defaultAddressResolutionOrder, that.defaultAddressResolutionOrder)
|
||||
&& asyncClientInitialization == that.asyncClientInitialization
|
||||
&& Objects.equals(environment, that.environment);
|
||||
}
|
||||
|
||||
@@ -623,109 +607,34 @@ public class EurekaInstanceConfigBean implements CloudEurekaInstanceConfig, Envi
|
||||
leaseExpirationDurationInSeconds, virtualHostName, instanceId, secureVirtualHostName, aSGName,
|
||||
metadataMap, dataCenterInfo, ipAddress, statusPageUrlPath, statusPageUrl, homePageUrlPath, homePageUrl,
|
||||
healthCheckUrlPath, healthCheckUrl, secureHealthCheckUrl, namespace, hostname, preferIpAddress,
|
||||
asyncClientInitialization, initialStatus, Arrays.hashCode(defaultAddressResolutionOrder), environment);
|
||||
initialStatus, Arrays.hashCode(defaultAddressResolutionOrder), environment);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return new StringBuilder("EurekaInstanceConfigBean{").append("hostInfo=")
|
||||
.append(hostInfo)
|
||||
.append(", ")
|
||||
.append("inetUtils=")
|
||||
.append(inetUtils)
|
||||
.append(", ")
|
||||
.append("appname='")
|
||||
.append(appname)
|
||||
.append("', ")
|
||||
.append("appGroupName='")
|
||||
.append(appGroupName)
|
||||
.append("', ")
|
||||
.append("instanceEnabledOnit=")
|
||||
.append(instanceEnabledOnit)
|
||||
.append(", ")
|
||||
.append("nonSecurePort=")
|
||||
.append(nonSecurePort)
|
||||
.append(", ")
|
||||
.append("securePort=")
|
||||
.append(securePort)
|
||||
.append(", ")
|
||||
.append("nonSecurePortEnabled=")
|
||||
.append(nonSecurePortEnabled)
|
||||
.append(", ")
|
||||
.append("securePortEnabled=")
|
||||
.append(securePortEnabled)
|
||||
.append(", ")
|
||||
.append("leaseRenewalIntervalInSeconds=")
|
||||
.append(leaseRenewalIntervalInSeconds)
|
||||
.append(", ")
|
||||
.append("leaseExpirationDurationInSeconds=")
|
||||
.append(leaseExpirationDurationInSeconds)
|
||||
.append(", ")
|
||||
.append("virtualHostName='")
|
||||
.append(virtualHostName)
|
||||
.append("', ")
|
||||
.append("instanceId='")
|
||||
.append(instanceId)
|
||||
.append("', ")
|
||||
.append("secureVirtualHostName='")
|
||||
.append(secureVirtualHostName)
|
||||
.append("', ")
|
||||
.append("aSGName='")
|
||||
.append(aSGName)
|
||||
.append("', ")
|
||||
.append("metadataMap=")
|
||||
.append(metadataMap)
|
||||
.append(", ")
|
||||
.append("dataCenterInfo=")
|
||||
.append(dataCenterInfo)
|
||||
.append(", ")
|
||||
.append("ipAddress='")
|
||||
.append(ipAddress)
|
||||
.append("', ")
|
||||
.append("statusPageUrlPath='")
|
||||
.append(statusPageUrlPath)
|
||||
.append("', ")
|
||||
.append("statusPageUrl='")
|
||||
.append(statusPageUrl)
|
||||
.append("', ")
|
||||
.append("homePageUrlPath='")
|
||||
.append(homePageUrlPath)
|
||||
.append("', ")
|
||||
.append("homePageUrl='")
|
||||
.append(homePageUrl)
|
||||
.append("', ")
|
||||
.append("healthCheckUrlPath='")
|
||||
.append(healthCheckUrlPath)
|
||||
.append("', ")
|
||||
.append("healthCheckUrl='")
|
||||
.append(healthCheckUrl)
|
||||
.append("', ")
|
||||
.append("secureHealthCheckUrl='")
|
||||
.append(secureHealthCheckUrl)
|
||||
.append("', ")
|
||||
.append("namespace='")
|
||||
.append(namespace)
|
||||
.append("', ")
|
||||
.append("hostname='")
|
||||
.append(hostname)
|
||||
.append("', ")
|
||||
.append("asyncClientInitialization=")
|
||||
.append(asyncClientInitialization)
|
||||
.append(", ")
|
||||
.append("preferIpAddress=")
|
||||
.append(preferIpAddress)
|
||||
.append(", ")
|
||||
.append("initialStatus=")
|
||||
.append(initialStatus)
|
||||
.append(", ")
|
||||
.append("defaultAddressResolutionOrder=")
|
||||
.append(Arrays.toString(defaultAddressResolutionOrder))
|
||||
.append(", ")
|
||||
.append("environment=")
|
||||
.append(environment)
|
||||
.append(", ")
|
||||
.append("}")
|
||||
.toString();
|
||||
return new StringBuilder("EurekaInstanceConfigBean{").append("hostInfo=").append(hostInfo).append(", ")
|
||||
.append("inetUtils=").append(inetUtils).append(", ").append("appname='").append(appname).append("', ")
|
||||
.append("appGroupName='").append(appGroupName).append("', ").append("instanceEnabledOnit=")
|
||||
.append(instanceEnabledOnit).append(", ").append("nonSecurePort=").append(nonSecurePort).append(", ")
|
||||
.append("securePort=").append(securePort).append(", ").append("nonSecurePortEnabled=")
|
||||
.append(nonSecurePortEnabled).append(", ").append("securePortEnabled=").append(securePortEnabled)
|
||||
.append(", ").append("leaseRenewalIntervalInSeconds=").append(leaseRenewalIntervalInSeconds)
|
||||
.append(", ").append("leaseExpirationDurationInSeconds=").append(leaseExpirationDurationInSeconds)
|
||||
.append(", ").append("virtualHostName='").append(virtualHostName).append("', ").append("instanceId='")
|
||||
.append(instanceId).append("', ").append("secureVirtualHostName='").append(secureVirtualHostName)
|
||||
.append("', ").append("aSGName='").append(aSGName).append("', ").append("metadataMap=")
|
||||
.append(metadataMap).append(", ").append("dataCenterInfo=").append(dataCenterInfo).append(", ")
|
||||
.append("ipAddress='").append(ipAddress).append("', ").append("statusPageUrlPath='")
|
||||
.append(statusPageUrlPath).append("', ").append("statusPageUrl='").append(statusPageUrl).append("', ")
|
||||
.append("homePageUrlPath='").append(homePageUrlPath).append("', ").append("homePageUrl='")
|
||||
.append(homePageUrl).append("', ").append("healthCheckUrlPath='").append(healthCheckUrlPath)
|
||||
.append("', ").append("healthCheckUrl='").append(healthCheckUrl).append("', ")
|
||||
.append("secureHealthCheckUrl='").append(secureHealthCheckUrl).append("', ").append("namespace='")
|
||||
.append(namespace).append("', ").append("hostname='").append(hostname).append("', ")
|
||||
.append("preferIpAddress=").append(preferIpAddress).append(", ").append("initialStatus=")
|
||||
.append(initialStatus).append(", ").append("defaultAddressResolutionOrder=")
|
||||
.append(Arrays.toString(defaultAddressResolutionOrder)).append(", ").append("environment=")
|
||||
.append(environment).append(", ").append("}").toString();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+16
-21
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -35,8 +35,8 @@ public class InstanceInfoFactory {
|
||||
|
||||
public InstanceInfo create(EurekaInstanceConfig config) {
|
||||
LeaseInfo.Builder leaseInfoBuilder = LeaseInfo.Builder.newBuilder()
|
||||
.setRenewalIntervalInSecs(config.getLeaseRenewalIntervalInSeconds())
|
||||
.setDurationInSecs(config.getLeaseExpirationDurationInSeconds());
|
||||
.setRenewalIntervalInSecs(config.getLeaseRenewalIntervalInSeconds())
|
||||
.setDurationInSecs(config.getLeaseExpirationDurationInSeconds());
|
||||
|
||||
// Builder the instance information to be registered with eureka
|
||||
// server
|
||||
@@ -46,24 +46,19 @@ public class InstanceInfoFactory {
|
||||
if (!namespace.endsWith(".")) {
|
||||
namespace = namespace + ".";
|
||||
}
|
||||
builder.setNamespace(namespace)
|
||||
.setAppName(config.getAppname())
|
||||
.setInstanceId(config.getInstanceId())
|
||||
.setAppGroupName(config.getAppGroupName())
|
||||
.setDataCenterInfo(config.getDataCenterInfo())
|
||||
.setIPAddr(config.getIpAddress())
|
||||
.setHostName(config.getHostName(false))
|
||||
.setPort(config.getNonSecurePort())
|
||||
.enablePort(InstanceInfo.PortType.UNSECURE, config.isNonSecurePortEnabled())
|
||||
.setSecurePort(config.getSecurePort())
|
||||
.enablePort(InstanceInfo.PortType.SECURE, config.getSecurePortEnabled())
|
||||
.setVIPAddress(config.getVirtualHostName())
|
||||
.setSecureVIPAddress(config.getSecureVirtualHostName())
|
||||
.setHomePageUrl(config.getHomePageUrlPath(), config.getHomePageUrl())
|
||||
.setStatusPageUrl(config.getStatusPageUrlPath(), config.getStatusPageUrl())
|
||||
.setHealthCheckUrls(config.getHealthCheckUrlPath(), config.getHealthCheckUrl(),
|
||||
config.getSecureHealthCheckUrl())
|
||||
.setASGName(config.getASGName());
|
||||
builder.setNamespace(namespace).setAppName(config.getAppname()).setInstanceId(config.getInstanceId())
|
||||
.setAppGroupName(config.getAppGroupName()).setDataCenterInfo(config.getDataCenterInfo())
|
||||
.setIPAddr(config.getIpAddress()).setHostName(config.getHostName(false))
|
||||
.setPort(config.getNonSecurePort())
|
||||
.enablePort(InstanceInfo.PortType.UNSECURE, config.isNonSecurePortEnabled())
|
||||
.setSecurePort(config.getSecurePort())
|
||||
.enablePort(InstanceInfo.PortType.SECURE, config.getSecurePortEnabled())
|
||||
.setVIPAddress(config.getVirtualHostName()).setSecureVIPAddress(config.getSecureVirtualHostName())
|
||||
.setHomePageUrl(config.getHomePageUrlPath(), config.getHomePageUrl())
|
||||
.setStatusPageUrl(config.getStatusPageUrlPath(), config.getStatusPageUrl())
|
||||
.setHealthCheckUrls(config.getHealthCheckUrlPath(), config.getHealthCheckUrl(),
|
||||
config.getSecureHealthCheckUrl())
|
||||
.setASGName(config.getASGName());
|
||||
|
||||
// Start off with the STARTING state to avoid traffic
|
||||
if (!config.isInstanceEnabledOnit()) {
|
||||
|
||||
-37
@@ -1,37 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.web.client.RestClient;
|
||||
|
||||
/**
|
||||
* A {@link RestClient}-specific {@link TimeoutProperties} implementation.
|
||||
*
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.0
|
||||
*/
|
||||
@ConfigurationProperties("eureka.client.restclient.timeout")
|
||||
public class RestClientTimeoutProperties extends TimeoutProperties {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "RestClientTimeoutProperties{" + ", connectTimeout=" + connectTimeout + ", connectRequestTimeout="
|
||||
+ connectRequestTimeout + ", socketTimeout=" + socketTimeout + '}';
|
||||
}
|
||||
|
||||
}
|
||||
+64
-9
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,23 +16,78 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
import org.apache.hc.client5.http.config.RequestConfig;
|
||||
import org.apache.hc.core5.http.io.SocketConfig;
|
||||
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateEurekaHttpClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
/**
|
||||
* A {@link RestTemplate}-specific {@link TimeoutProperties} implementation.
|
||||
* Properties for configuring timeouts used in {@link RestTemplate} required by
|
||||
* {@link RestTemplateEurekaHttpClient}.
|
||||
*
|
||||
* @author Jiwon Jeon
|
||||
* @author Mooyong Lee
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 3.1.6
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
@ConfigurationProperties("eureka.client.rest-template-timeout")
|
||||
public class RestTemplateTimeoutProperties extends TimeoutProperties {
|
||||
public class RestTemplateTimeoutProperties {
|
||||
|
||||
/**
|
||||
* Default values are set to 180000, in keeping with {@link RequestConfig} and
|
||||
* {@link SocketConfig} defaults.
|
||||
*/
|
||||
private int connectTimeout = 3 * 60 * 1000;
|
||||
|
||||
private int connectRequestTimeout = 3 * 60 * 1000;
|
||||
|
||||
private int socketTimeout = 3 * 60 * 1000;
|
||||
|
||||
public int getConnectTimeout() {
|
||||
return connectTimeout;
|
||||
}
|
||||
|
||||
public int getConnectRequestTimeout() {
|
||||
return connectRequestTimeout;
|
||||
}
|
||||
|
||||
public int getSocketTimeout() {
|
||||
return socketTimeout;
|
||||
}
|
||||
|
||||
public void setConnectTimeout(int connectTimeout) {
|
||||
this.connectTimeout = connectTimeout;
|
||||
}
|
||||
|
||||
public void setConnectRequestTimeout(int connectRequestTimeout) {
|
||||
this.connectRequestTimeout = connectRequestTimeout;
|
||||
}
|
||||
|
||||
public void setSocketTimeout(int socketTimeout) {
|
||||
this.socketTimeout = socketTimeout;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) {
|
||||
return true;
|
||||
}
|
||||
if (o == null || getClass() != o.getClass()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
RestTemplateTimeoutProperties that = (RestTemplateTimeoutProperties) o;
|
||||
|
||||
return connectTimeout == that.connectTimeout && connectRequestTimeout == that.connectRequestTimeout
|
||||
&& socketTimeout == that.socketTimeout;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(connectTimeout, connectRequestTimeout, socketTimeout);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
|
||||
-92
@@ -1,92 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import java.util.Objects;
|
||||
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
import org.apache.hc.client5.http.config.RequestConfig;
|
||||
import org.apache.hc.core5.http.io.SocketConfig;
|
||||
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
/**
|
||||
* Properties for configuring timeouts used in {@link RestTemplate} required by
|
||||
* {@link EurekaHttpClient}.
|
||||
*
|
||||
* @author Jiwon Jeon
|
||||
* @author Mooyong Lee
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.0
|
||||
*/
|
||||
public abstract class TimeoutProperties {
|
||||
|
||||
/**
|
||||
* Default values are set to 180000, in keeping with {@link RequestConfig} and
|
||||
* {@link SocketConfig} defaults.
|
||||
*/
|
||||
protected int connectTimeout = 180000; // 3 * MINUTES
|
||||
|
||||
protected int connectRequestTimeout = 180000; // 3 * MINUTES
|
||||
|
||||
protected int socketTimeout = 180000; // 3 * MINUTES
|
||||
|
||||
public int getConnectTimeout() {
|
||||
return connectTimeout;
|
||||
}
|
||||
|
||||
public int getConnectRequestTimeout() {
|
||||
return connectRequestTimeout;
|
||||
}
|
||||
|
||||
public int getSocketTimeout() {
|
||||
return socketTimeout;
|
||||
}
|
||||
|
||||
public void setConnectTimeout(int connectTimeout) {
|
||||
this.connectTimeout = connectTimeout;
|
||||
}
|
||||
|
||||
public void setConnectRequestTimeout(int connectRequestTimeout) {
|
||||
this.connectRequestTimeout = connectRequestTimeout;
|
||||
}
|
||||
|
||||
public void setSocketTimeout(int socketTimeout) {
|
||||
this.socketTimeout = socketTimeout;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) {
|
||||
return true;
|
||||
}
|
||||
if (o == null || getClass() != o.getClass()) {
|
||||
return false;
|
||||
}
|
||||
|
||||
RestTemplateTimeoutProperties that = (RestTemplateTimeoutProperties) o;
|
||||
|
||||
return connectTimeout == that.connectTimeout && connectRequestTimeout == that.connectRequestTimeout
|
||||
&& socketTimeout == that.socketTimeout;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
return Objects.hash(connectTimeout, connectRequestTimeout, socketTimeout);
|
||||
}
|
||||
|
||||
}
|
||||
+53
-219
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -18,7 +18,6 @@ package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.security.GeneralSecurityException;
|
||||
import java.util.Set;
|
||||
|
||||
import com.netflix.discovery.AbstractDiscoveryClientOptionalArgs;
|
||||
import com.netflix.discovery.shared.transport.jersey.TransportClientFactories;
|
||||
@@ -26,8 +25,7 @@ import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.beans.factory.ObjectProvider;
|
||||
import org.springframework.boot.autoconfigure.condition.AllNestedConditions;
|
||||
import org.springframework.boot.autoconfigure.condition.AnyNestedCondition;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
@@ -36,34 +34,24 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.autoconfigure.condition.SearchStrategy;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.boot.restclient.RestTemplateBuilder;
|
||||
import org.springframework.cloud.configuration.SSLContextFactory;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.cloud.netflix.eureka.RestClientTimeoutProperties;
|
||||
import org.springframework.cloud.netflix.eureka.RestTemplateTimeoutProperties;
|
||||
import org.springframework.cloud.netflix.eureka.http.DefaultEurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.EurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientTransportClientFactories;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateTransportClientFactories;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientTransportClientFactories;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.reactive.function.client.WebClient;
|
||||
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
* @author Armin Krezovic
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @author Wonchul Heo
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@EnableConfigurationProperties({ RestTemplateTimeoutProperties.class, RestClientTimeoutProperties.class })
|
||||
@EnableConfigurationProperties(RestTemplateTimeoutProperties.class)
|
||||
public class DiscoveryClientOptionalArgsConfiguration {
|
||||
|
||||
protected static final Log logger = LogFactory.getLog(DiscoveryClientOptionalArgsConfiguration.class);
|
||||
@@ -74,8 +62,42 @@ public class DiscoveryClientOptionalArgsConfiguration {
|
||||
return new TlsProperties();
|
||||
}
|
||||
|
||||
// Visible for tests
|
||||
public static void setupTLS(AbstractDiscoveryClientOptionalArgs<?> args, TlsProperties properties)
|
||||
@Bean
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestTemplate")
|
||||
@ConditionalOnMissingClass("org.glassfish.jersey.client.JerseyClient")
|
||||
@ConditionalOnMissingBean(value = { AbstractDiscoveryClientOptionalArgs.class }, search = SearchStrategy.CURRENT)
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
public RestTemplateDiscoveryClientOptionalArgs restTemplateDiscoveryClientOptionalArgs(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier)
|
||||
throws GeneralSecurityException, IOException {
|
||||
logger.info("Eureka HTTP Client uses RestTemplate.");
|
||||
RestTemplateDiscoveryClientOptionalArgs result = new RestTemplateDiscoveryClientOptionalArgs(
|
||||
eurekaClientHttpRequestFactorySupplier);
|
||||
setupTLS(result, tlsProperties);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestTemplate")
|
||||
@ConditionalOnMissingClass("org.glassfish.jersey.client.JerseyClient")
|
||||
@ConditionalOnMissingBean(value = { TransportClientFactories.class }, search = SearchStrategy.CURRENT)
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
public RestTemplateTransportClientFactories restTemplateTransportClientFactories(
|
||||
RestTemplateDiscoveryClientOptionalArgs optionalArgs) {
|
||||
return new RestTemplateTransportClientFactories(optionalArgs);
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestTemplate")
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier(
|
||||
RestTemplateTimeoutProperties restTemplateTimeoutProperties) {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier(restTemplateTimeoutProperties);
|
||||
}
|
||||
|
||||
private static void setupTLS(AbstractDiscoveryClientOptionalArgs<?> args, TlsProperties properties)
|
||||
throws GeneralSecurityException, IOException {
|
||||
if (properties.isEnabled()) {
|
||||
SSLContextFactory factory = new SSLContextFactory(properties);
|
||||
@@ -83,79 +105,34 @@ public class DiscoveryClientOptionalArgsConfiguration {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(OnRestTemplatePresentAndEnabledCondition.class)
|
||||
@Deprecated
|
||||
static class RestTemplateConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier(
|
||||
RestTemplateTimeoutProperties restTemplateTimeoutProperties,
|
||||
Set<EurekaClientHttpRequestFactorySupplier.RequestConfigCustomizer> requestConfigCustomizers) {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier(restTemplateTimeoutProperties,
|
||||
requestConfigCustomizers);
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(value = { AbstractDiscoveryClientOptionalArgs.class },
|
||||
search = SearchStrategy.CURRENT)
|
||||
public RestTemplateDiscoveryClientOptionalArgs restTemplateDiscoveryClientOptionalArgs(
|
||||
TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
ObjectProvider<RestTemplateBuilder> restTemplateBuilders) throws GeneralSecurityException, IOException {
|
||||
if (logger.isInfoEnabled()) {
|
||||
logger.info("Eureka HTTP Client uses RestTemplate.");
|
||||
}
|
||||
RestTemplateDiscoveryClientOptionalArgs result = new RestTemplateDiscoveryClientOptionalArgs(
|
||||
eurekaClientHttpRequestFactorySupplier, restTemplateBuilders::getIfAvailable);
|
||||
setupTLS(result, tlsProperties);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(value = { TransportClientFactories.class }, search = SearchStrategy.CURRENT)
|
||||
public RestTemplateTransportClientFactories restTemplateTransportClientFactories(
|
||||
RestTemplateDiscoveryClientOptionalArgs optionalArgs) {
|
||||
return new RestTemplateTransportClientFactories(optionalArgs);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(OnJerseyClientPresentAndEnabledCondition.class)
|
||||
@ConditionalOnClass(name = "org.glassfish.jersey.client.JerseyClient")
|
||||
@ConditionalOnBean(value = AbstractDiscoveryClientOptionalArgs.class, search = SearchStrategy.CURRENT)
|
||||
static class DiscoveryClientOptionalArgsTlsConfiguration {
|
||||
|
||||
DiscoveryClientOptionalArgsTlsConfiguration(TlsProperties tlsProperties,
|
||||
AbstractDiscoveryClientOptionalArgs optionalArgs) throws GeneralSecurityException, IOException {
|
||||
if (logger.isInfoEnabled()) {
|
||||
logger.info("Eureka HTTP Client uses Jersey");
|
||||
}
|
||||
logger.info("Eureka HTTP Client uses Jersey");
|
||||
setupTLS(optionalArgs, tlsProperties);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(OnJerseyClientNotPresentOrNotEnabledCondition.class)
|
||||
@ConditionalOnMissingClass("org.glassfish.jersey.client.JerseyClient")
|
||||
@ConditionalOnClass(name = "org.springframework.web.reactive.function.client.WebClient")
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", havingValue = "true")
|
||||
protected static class WebClientConfiguration {
|
||||
|
||||
@Autowired
|
||||
private TlsProperties tlsProperties;
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(
|
||||
value = { AbstractDiscoveryClientOptionalArgs.class, RestTemplateDiscoveryClientOptionalArgs.class },
|
||||
search = SearchStrategy.CURRENT)
|
||||
public WebClientDiscoveryClientOptionalArgs webClientDiscoveryClientOptionalArgs(TlsProperties tlsProperties,
|
||||
public WebClientDiscoveryClientOptionalArgs webClientDiscoveryClientOptionalArgs(
|
||||
ObjectProvider<WebClient.Builder> builder) throws GeneralSecurityException, IOException {
|
||||
if (logger.isInfoEnabled()) {
|
||||
logger.info("Eureka HTTP Client uses WebClient.");
|
||||
}
|
||||
logger.info("Eureka HTTP Client uses WebClient.");
|
||||
WebClientDiscoveryClientOptionalArgs result = new WebClientDiscoveryClientOptionalArgs(
|
||||
builder::getIfAvailable);
|
||||
setupTLS(result, tlsProperties);
|
||||
@@ -171,159 +148,16 @@ public class DiscoveryClientOptionalArgsConfiguration {
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(OnJerseyClientNotPresentOrNotEnabledCondition.class)
|
||||
@ConditionalOnMissingClass("org.springframework.web.reactive.function.client.WebClient")
|
||||
@Configuration
|
||||
@ConditionalOnMissingClass({ "org.glassfish.jersey.client.JerseyClient",
|
||||
"org.springframework.web.reactive.function.client.WebClient" })
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", havingValue = "true")
|
||||
protected static class WebClientNotFoundConfiguration {
|
||||
|
||||
public WebClientNotFoundConfiguration() {
|
||||
throw new IllegalStateException("eureka.client.webclient.enabled is true, "
|
||||
+ "but WebClient is not on the classpath. Please add " + "spring-boot-webclient as a dependency.");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(OnRestClientPresentAndEnabledCondition.class)
|
||||
protected static class RestClientConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier(
|
||||
RestClientTimeoutProperties restClientTimeoutProperties,
|
||||
Set<EurekaClientHttpRequestFactorySupplier.RequestConfigCustomizer> requestConfigCustomizers) {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier(restClientTimeoutProperties,
|
||||
requestConfigCustomizers);
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(value = { AbstractDiscoveryClientOptionalArgs.class },
|
||||
search = SearchStrategy.CURRENT)
|
||||
public RestClientDiscoveryClientOptionalArgs restClientDiscoveryClientOptionalArgs(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
ObjectProvider<RestClient.Builder> restClientBuilderProvider)
|
||||
throws GeneralSecurityException, IOException {
|
||||
if (logger.isInfoEnabled()) {
|
||||
logger.info("Eureka HTTP Client uses RestClient.");
|
||||
}
|
||||
RestClientDiscoveryClientOptionalArgs result = new RestClientDiscoveryClientOptionalArgs(
|
||||
eurekaClientHttpRequestFactorySupplier,
|
||||
() -> restClientBuilderProvider.getIfAvailable(RestClient::builder));
|
||||
setupTLS(result, tlsProperties);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(value = TransportClientFactories.class, search = SearchStrategy.CURRENT)
|
||||
public RestClientTransportClientFactories restClientTransportClientFactories(
|
||||
RestClientDiscoveryClientOptionalArgs args) {
|
||||
return new RestClientTransportClientFactories(args);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class OnJerseyClientPresentAndEnabledCondition extends AllNestedConditions {
|
||||
|
||||
OnJerseyClientPresentAndEnabledCondition() {
|
||||
super(ConfigurationPhase.REGISTER_BEAN);
|
||||
}
|
||||
|
||||
@ConditionalOnClass(name = "org.glassfish.jersey.client.JerseyClient")
|
||||
static class OnJerseyClientPresent {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(value = "eureka.client.jersey.enabled", matchIfMissing = true)
|
||||
static class OnJerseyClientEnabled {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class OnJerseyClientNotPresentOrNotEnabledCondition extends AnyNestedCondition {
|
||||
|
||||
OnJerseyClientNotPresentOrNotEnabledCondition() {
|
||||
super(ConfigurationPhase.REGISTER_BEAN);
|
||||
}
|
||||
|
||||
@ConditionalOnMissingClass("org.glassfish.jersey.client.JerseyClient")
|
||||
static class OnJerseyClientMissing {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(value = "eureka.client.jersey.enabled", havingValue = "false")
|
||||
static class OnJerseyClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
static class OnRestTemplatePresentAndEnabledCondition extends AllNestedConditions {
|
||||
|
||||
OnRestTemplatePresentAndEnabledCondition() {
|
||||
super(ConfigurationPhase.REGISTER_BEAN);
|
||||
}
|
||||
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestTemplate")
|
||||
static class OnRestTemplatePresent {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnClass(name = "org.springframework.boot.restclient.RestTemplateBuilder")
|
||||
static class OnRestTemplateBuilderPresent {
|
||||
|
||||
}
|
||||
|
||||
@Conditional(OnJerseyClientNotPresentOrNotEnabledCondition.class)
|
||||
static class OnJerseyClientNotPresentOrNotEnabled {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
static class OnWebClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "restclient.enabled", havingValue = "false",
|
||||
matchIfMissing = true)
|
||||
static class OnRestClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static class OnRestClientPresentAndEnabledCondition extends AllNestedConditions {
|
||||
|
||||
OnRestClientPresentAndEnabledCondition() {
|
||||
super(ConfigurationPhase.REGISTER_BEAN);
|
||||
}
|
||||
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestClient")
|
||||
static class OnRestClientPresent {
|
||||
|
||||
}
|
||||
|
||||
@Conditional(OnJerseyClientNotPresentOrNotEnabledCondition.class)
|
||||
static class OnJerseyClientNotPresentOrNotEnabled {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
static class OnWebClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "restclient.enabled", havingValue = "true")
|
||||
static class OnRestClientEnabled {
|
||||
|
||||
throw new IllegalStateException(
|
||||
"eureka.client.webclient.enabled is true, " + "but WebClient is not on the classpath. Please add "
|
||||
+ "spring-boot-starter-webflux as a dependency.");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+25
-131
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,8 +16,6 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import java.util.Set;
|
||||
|
||||
import com.netflix.discovery.EurekaClientConfig;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
|
||||
@@ -28,20 +26,15 @@ import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.autoconfigure.condition.SearchStrategy;
|
||||
import org.springframework.boot.autoconfigure.http.codec.CodecsAutoConfiguration;
|
||||
import org.springframework.boot.autoconfigure.web.reactive.function.client.WebClientAutoConfiguration;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.boot.http.codec.autoconfigure.CodecsAutoConfiguration;
|
||||
import org.springframework.boot.restclient.RestTemplateBuilder;
|
||||
import org.springframework.boot.webclient.autoconfigure.WebClientAutoConfiguration;
|
||||
import org.springframework.cloud.config.client.ConfigServerInstanceProvider;
|
||||
import org.springframework.cloud.config.client.ConfigServicePropertySourceLocator;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.cloud.netflix.eureka.EurekaClientConfigBean;
|
||||
import org.springframework.cloud.netflix.eureka.RestClientTimeoutProperties;
|
||||
import org.springframework.cloud.netflix.eureka.RestTemplateTimeoutProperties;
|
||||
import org.springframework.cloud.netflix.eureka.http.DefaultEurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.EurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientEurekaHttpClient;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientTransportClientFactory;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateEurekaHttpClient;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateTransportClientFactory;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientEurekaHttpClient;
|
||||
@@ -51,23 +44,18 @@ import org.springframework.context.annotation.Conditional;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.lang.Nullable;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.reactive.function.client.WebClient;
|
||||
|
||||
/**
|
||||
* Bootstrap configuration for config client that wants to look the config server up via
|
||||
* Bootstrap configuration for config client that wants to lookup the config server via
|
||||
* discovery.
|
||||
*
|
||||
* @author Dave Syer
|
||||
* @author Armin Krezovic
|
||||
* @author Wonchul Heo
|
||||
* @author Olga Maciaszek-Sharma
|
||||
*/
|
||||
@ConditionalOnClass(ConfigServicePropertySourceLocator.class)
|
||||
@Conditional(EurekaConfigServerBootstrapConfiguration.EurekaConfigServerBootstrapCondition.class)
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@EnableConfigurationProperties({ RestTemplateTimeoutProperties.class, RestClientTimeoutProperties.class })
|
||||
@EnableConfigurationProperties
|
||||
public class EurekaConfigServerBootstrapConfiguration {
|
||||
|
||||
@Bean
|
||||
@@ -76,75 +64,32 @@ public class EurekaConfigServerBootstrapConfiguration {
|
||||
return new EurekaClientConfigBean();
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(EurekaHttpClient.class)
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
public RestTemplateEurekaHttpClient configDiscoveryRestTemplateEurekaHttpClient(EurekaClientConfigBean config,
|
||||
Environment env, @Nullable TlsProperties properties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
return (RestTemplateEurekaHttpClient) new RestTemplateTransportClientFactory(properties,
|
||||
eurekaClientHttpRequestFactorySupplier)
|
||||
.newClient(HostnameBasedUrlRandomizer.randomEndpoint(config, env));
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier() {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier();
|
||||
}
|
||||
|
||||
@Bean
|
||||
public ConfigServerInstanceProvider.Function eurekaConfigServerInstanceProvider(EurekaHttpClient client,
|
||||
EurekaClientConfig config) {
|
||||
return new EurekaConfigServerInstanceProvider(client, config)::getInstances;
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(RestTemplateConfiguration.OnRestTemplatePresentAndEnabledCondition.class)
|
||||
@Deprecated
|
||||
static class RestTemplateConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(EurekaHttpClient.class)
|
||||
public RestTemplateEurekaHttpClient configDiscoveryRestTemplateEurekaHttpClient(EurekaClientConfigBean config,
|
||||
Environment env, @Nullable TlsProperties properties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
ObjectProvider<RestTemplateBuilder> restTemplateBuilders) {
|
||||
return (RestTemplateEurekaHttpClient) new RestTemplateTransportClientFactory(properties,
|
||||
eurekaClientHttpRequestFactorySupplier, restTemplateBuilders::getIfAvailable)
|
||||
.newClient(HostnameBasedUrlRandomizer.randomEndpoint(config, env));
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier(
|
||||
RestTemplateTimeoutProperties restTemplateTimeoutProperties,
|
||||
Set<EurekaClientHttpRequestFactorySupplier.RequestConfigCustomizer> requestConfigCustomizers) {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier(restTemplateTimeoutProperties,
|
||||
requestConfigCustomizers);
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour
|
||||
* of {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
static class OnRestTemplatePresentAndEnabledCondition extends AllNestedConditions {
|
||||
|
||||
OnRestTemplatePresentAndEnabledCondition() {
|
||||
super(ConfigurationPhase.REGISTER_BEAN);
|
||||
}
|
||||
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestTemplate")
|
||||
static class OnRestTemplatePresent {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
static class OnWebClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "restclient.enabled", havingValue = "false",
|
||||
matchIfMissing = true)
|
||||
static class OnRestClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@ConditionalOnClass({ WebClient.class, WebClientAutoConfiguration.class, CodecsAutoConfiguration.class })
|
||||
@ConditionalOnClass(name = "org.springframework.web.reactive.function.client.WebClient")
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", havingValue = "true")
|
||||
@ImportAutoConfiguration({ CodecsAutoConfiguration.class, WebClientAutoConfiguration.class })
|
||||
protected static class WebClientConfiguration {
|
||||
@@ -154,58 +99,7 @@ public class EurekaConfigServerBootstrapConfiguration {
|
||||
public WebClientEurekaHttpClient configDiscoveryWebClientEurekaHttpClient(EurekaClientConfigBean config,
|
||||
ObjectProvider<WebClient.Builder> builder, Environment env) {
|
||||
return (WebClientEurekaHttpClient) new WebClientTransportClientFactory(builder::getIfAvailable)
|
||||
.newClient(HostnameBasedUrlRandomizer.randomEndpoint(config, env));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@Conditional(RestClientConfiguration.OnRestClientPresentAndEnabledCondition.class)
|
||||
static class RestClientConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(EurekaHttpClient.class)
|
||||
public RestClientEurekaHttpClient configDiscoveryRestClientEurekaHttpClient(EurekaClientConfigBean config,
|
||||
@Nullable TlsProperties properties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
ObjectProvider<RestClient.Builder> restClientBuilderProvider, Environment env) {
|
||||
return (RestClientEurekaHttpClient) new RestClientTransportClientFactory(properties,
|
||||
eurekaClientHttpRequestFactorySupplier,
|
||||
() -> restClientBuilderProvider.getIfAvailable(RestClient::builder))
|
||||
.newClient(HostnameBasedUrlRandomizer.randomEndpoint(config, env));
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
EurekaClientHttpRequestFactorySupplier defaultEurekaClientHttpRequestFactorySupplier(
|
||||
RestClientTimeoutProperties restClientTimeoutProperties,
|
||||
Set<EurekaClientHttpRequestFactorySupplier.RequestConfigCustomizer> requestConfigCustomizers) {
|
||||
return new DefaultEurekaClientHttpRequestFactorySupplier(restClientTimeoutProperties,
|
||||
requestConfigCustomizers);
|
||||
}
|
||||
|
||||
static class OnRestClientPresentAndEnabledCondition extends AllNestedConditions {
|
||||
|
||||
OnRestClientPresentAndEnabledCondition() {
|
||||
super(ConfigurationPhase.REGISTER_BEAN);
|
||||
}
|
||||
|
||||
@ConditionalOnClass(name = "org.springframework.web.client.RestClient")
|
||||
static class OnRestClientPresentCondition {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "webclient.enabled", matchIfMissing = true,
|
||||
havingValue = "false")
|
||||
static class OnWebClientDisabled {
|
||||
|
||||
}
|
||||
|
||||
@ConditionalOnProperty(prefix = "eureka.client", name = "restclient.enabled", havingValue = "true")
|
||||
static class OnRestClientEnabled {
|
||||
|
||||
}
|
||||
|
||||
.newClient(HostnameBasedUrlRandomizer.randomEndpoint(config, env));
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+5
-7
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -30,10 +30,9 @@ import org.springframework.cloud.config.client.ConfigServerConfigDataLocationRes
|
||||
import org.springframework.cloud.config.client.ConfigServerInstanceProvider;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.cloud.netflix.eureka.EurekaClientConfigBean;
|
||||
import org.springframework.cloud.netflix.eureka.RestClientTimeoutProperties;
|
||||
import org.springframework.cloud.netflix.eureka.http.DefaultEurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.EurekaClientHttpRequestFactorySupplier;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientTransportClientFactory;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateTransportClientFactory;
|
||||
import org.springframework.util.ClassUtils;
|
||||
|
||||
public class EurekaConfigServerBootstrapper implements BootstrapRegistryInitializer {
|
||||
@@ -58,12 +57,11 @@ public class EurekaConfigServerBootstrapper implements BootstrapRegistryInitiali
|
||||
return (id) -> Collections.emptyList();
|
||||
}
|
||||
EurekaClientConfigBean config = context.get(EurekaClientConfigBean.class);
|
||||
EurekaHttpClient httpClient = new RestClientTransportClientFactory(
|
||||
EurekaHttpClient httpClient = new RestTemplateTransportClientFactory(
|
||||
context.getOrElse(TlsProperties.class, null),
|
||||
context.getOrElse(EurekaClientHttpRequestFactorySupplier.class,
|
||||
new DefaultEurekaClientHttpRequestFactorySupplier(new RestClientTimeoutProperties(),
|
||||
Collections.emptySet())))
|
||||
.newClient(HostnameBasedUrlRandomizer.randomEndpoint(config, getPropertyResolver(context)));
|
||||
new DefaultEurekaClientHttpRequestFactorySupplier())).newClient(
|
||||
HostnameBasedUrlRandomizer.randomEndpoint(config, getPropertyResolver(context)));
|
||||
return new EurekaConfigServerInstanceProvider(httpClient, config)::getInstances;
|
||||
});
|
||||
}
|
||||
|
||||
+2
-9
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -31,9 +31,6 @@ import org.springframework.cloud.client.ServiceInstance;
|
||||
import org.springframework.cloud.netflix.eureka.EurekaServiceInstance;
|
||||
import org.springframework.http.HttpStatus;
|
||||
|
||||
/**
|
||||
* @author Tang Xiong
|
||||
*/
|
||||
public class EurekaConfigServerInstanceProvider {
|
||||
|
||||
private final Log log;
|
||||
@@ -56,11 +53,7 @@ public class EurekaConfigServerInstanceProvider {
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("eurekaConfigServerInstanceProvider finding instances for " + serviceId);
|
||||
}
|
||||
String remoteRegionsStr = config.fetchRegistryForRemoteRegions();
|
||||
String[] remoteRegions = remoteRegionsStr == null ? null : remoteRegionsStr.split(",");
|
||||
EurekaHttpResponse<Applications> response = config.getRegistryRefreshSingleVipAddress() == null
|
||||
? client.getApplications(remoteRegions)
|
||||
: client.getVip(config.getRegistryRefreshSingleVipAddress(), remoteRegions);
|
||||
EurekaHttpResponse<Applications> response = client.getApplications(config.getRegion());
|
||||
List<ServiceInstance> instances = new ArrayList<>();
|
||||
if (!isSuccessful(response) || response.getEntity() == null) {
|
||||
return instances;
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+24
-54
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,14 +16,11 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
import org.apache.hc.client5.http.config.ConnectionConfig;
|
||||
import org.apache.hc.client5.http.config.RequestConfig;
|
||||
import org.apache.hc.client5.http.impl.classic.CloseableHttpClient;
|
||||
import org.apache.hc.client5.http.impl.classic.HttpClientBuilder;
|
||||
@@ -35,7 +32,6 @@ import org.apache.hc.core5.http.io.SocketConfig;
|
||||
import org.apache.hc.core5.util.Timeout;
|
||||
|
||||
import org.springframework.cloud.netflix.eureka.RestTemplateTimeoutProperties;
|
||||
import org.springframework.cloud.netflix.eureka.TimeoutProperties;
|
||||
import org.springframework.http.client.ClientHttpRequestFactory;
|
||||
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
|
||||
import org.springframework.lang.Nullable;
|
||||
@@ -51,52 +47,31 @@ import org.springframework.lang.Nullable;
|
||||
*/
|
||||
public class DefaultEurekaClientHttpRequestFactorySupplier implements EurekaClientHttpRequestFactorySupplier {
|
||||
|
||||
private final TimeoutProperties timeoutProperties;
|
||||
|
||||
// TODO: switch to final after removing deprecated interfaces
|
||||
private Set<RequestConfigCustomizer> requestConfigCustomizers = Collections.emptySet();
|
||||
private final RestTemplateTimeoutProperties restTemplateTimeoutProperties;
|
||||
|
||||
/**
|
||||
* @deprecated in favour of
|
||||
* {@link DefaultEurekaClientHttpRequestFactorySupplier#DefaultEurekaClientHttpRequestFactorySupplier(TimeoutProperties, Set)}
|
||||
* {@link DefaultEurekaClientHttpRequestFactorySupplier#DefaultEurekaClientHttpRequestFactorySupplier(RestTemplateTimeoutProperties)}
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
@Deprecated
|
||||
public DefaultEurekaClientHttpRequestFactorySupplier() {
|
||||
this.timeoutProperties = new RestTemplateTimeoutProperties();
|
||||
this.restTemplateTimeoutProperties = new RestTemplateTimeoutProperties();
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated in favour of
|
||||
* {@link DefaultEurekaClientHttpRequestFactorySupplier#DefaultEurekaClientHttpRequestFactorySupplier(TimeoutProperties, Set)}
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
public DefaultEurekaClientHttpRequestFactorySupplier(RestTemplateTimeoutProperties timeoutProperties) {
|
||||
this.timeoutProperties = timeoutProperties;
|
||||
}
|
||||
|
||||
/**
|
||||
* @deprecated in favour of
|
||||
* {@link DefaultEurekaClientHttpRequestFactorySupplier#DefaultEurekaClientHttpRequestFactorySupplier(TimeoutProperties, Set)}
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
public DefaultEurekaClientHttpRequestFactorySupplier(TimeoutProperties timeoutProperties) {
|
||||
this.timeoutProperties = timeoutProperties;
|
||||
}
|
||||
|
||||
public DefaultEurekaClientHttpRequestFactorySupplier(TimeoutProperties timeoutProperties,
|
||||
Set<RequestConfigCustomizer> requestConfigCustomizers) {
|
||||
this.timeoutProperties = timeoutProperties;
|
||||
this.requestConfigCustomizers = requestConfigCustomizers;
|
||||
public DefaultEurekaClientHttpRequestFactorySupplier(RestTemplateTimeoutProperties restTemplateTimeoutProperties) {
|
||||
this.restTemplateTimeoutProperties = restTemplateTimeoutProperties;
|
||||
}
|
||||
|
||||
@Override
|
||||
public ClientHttpRequestFactory get(SSLContext sslContext, @Nullable HostnameVerifier hostnameVerifier) {
|
||||
HttpClientBuilder httpClientBuilder = HttpClientBuilder.create();
|
||||
if (sslContext != null || hostnameVerifier != null || timeoutProperties != null) {
|
||||
httpClientBuilder
|
||||
.setConnectionManager(buildConnectionManager(sslContext, hostnameVerifier, timeoutProperties));
|
||||
if (sslContext != null || hostnameVerifier != null || restTemplateTimeoutProperties != null) {
|
||||
httpClientBuilder.setConnectionManager(
|
||||
buildConnectionManager(sslContext, hostnameVerifier, restTemplateTimeoutProperties));
|
||||
}
|
||||
if (restTemplateTimeoutProperties != null) {
|
||||
httpClientBuilder.setDefaultRequestConfig(buildRequestConfig());
|
||||
}
|
||||
httpClientBuilder.setDefaultRequestConfig(buildRequestConfig());
|
||||
|
||||
CloseableHttpClient httpClient = httpClientBuilder.build();
|
||||
HttpComponentsClientHttpRequestFactory requestFactory = new HttpComponentsClientHttpRequestFactory();
|
||||
@@ -105,11 +80,11 @@ public class DefaultEurekaClientHttpRequestFactorySupplier implements EurekaClie
|
||||
}
|
||||
|
||||
private HttpClientConnectionManager buildConnectionManager(SSLContext sslContext, HostnameVerifier hostnameVerifier,
|
||||
TimeoutProperties timeoutProperties) {
|
||||
RestTemplateTimeoutProperties restTemplateTimeoutProperties) {
|
||||
PoolingHttpClientConnectionManagerBuilder connectionManagerBuilder = PoolingHttpClientConnectionManagerBuilder
|
||||
.create();
|
||||
.create();
|
||||
SSLConnectionSocketFactoryBuilder sslConnectionSocketFactoryBuilder = SSLConnectionSocketFactoryBuilder
|
||||
.create();
|
||||
.create();
|
||||
if (sslContext != null) {
|
||||
sslConnectionSocketFactoryBuilder.setSslContext(sslContext);
|
||||
}
|
||||
@@ -117,25 +92,20 @@ public class DefaultEurekaClientHttpRequestFactorySupplier implements EurekaClie
|
||||
sslConnectionSocketFactoryBuilder.setHostnameVerifier(hostnameVerifier);
|
||||
}
|
||||
connectionManagerBuilder.setSSLSocketFactory(sslConnectionSocketFactoryBuilder.build());
|
||||
if (timeoutProperties != null) {
|
||||
if (restTemplateTimeoutProperties != null) {
|
||||
connectionManagerBuilder.setDefaultSocketConfig(SocketConfig.custom()
|
||||
.setSoTimeout(Timeout.of(timeoutProperties.getSocketTimeout(), TimeUnit.MILLISECONDS))
|
||||
.build());
|
||||
connectionManagerBuilder.setDefaultConnectionConfig(ConnectionConfig.custom()
|
||||
.setConnectTimeout(Timeout.of(timeoutProperties.getConnectTimeout(), TimeUnit.MILLISECONDS))
|
||||
.build());
|
||||
.setSoTimeout(Timeout.of(restTemplateTimeoutProperties.getSocketTimeout(), TimeUnit.MILLISECONDS))
|
||||
.build());
|
||||
}
|
||||
return connectionManagerBuilder.build();
|
||||
}
|
||||
|
||||
private RequestConfig buildRequestConfig() {
|
||||
RequestConfig.Builder requestConfigBuilder = RequestConfig.custom();
|
||||
if (timeoutProperties != null) {
|
||||
requestConfigBuilder.setConnectionRequestTimeout(
|
||||
Timeout.of(timeoutProperties.getConnectRequestTimeout(), TimeUnit.MILLISECONDS));
|
||||
}
|
||||
requestConfigCustomizers.forEach(customizer -> customizer.customize(requestConfigBuilder));
|
||||
return requestConfigBuilder.build();
|
||||
return RequestConfig.custom()
|
||||
.setConnectTimeout(Timeout.of(restTemplateTimeoutProperties.getConnectTimeout(), TimeUnit.MILLISECONDS))
|
||||
.setConnectionRequestTimeout(
|
||||
Timeout.of(restTemplateTimeoutProperties.getConnectRequestTimeout(), TimeUnit.MILLISECONDS))
|
||||
.build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-16
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -19,8 +19,6 @@ package org.springframework.cloud.netflix.eureka.http;
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
import org.apache.hc.client5.http.config.RequestConfig;
|
||||
|
||||
import org.springframework.http.client.ClientHttpRequestFactory;
|
||||
import org.springframework.lang.Nullable;
|
||||
|
||||
@@ -40,17 +38,4 @@ public interface EurekaClientHttpRequestFactorySupplier {
|
||||
*/
|
||||
ClientHttpRequestFactory get(SSLContext sslContext, @Nullable HostnameVerifier hostnameVerifier);
|
||||
|
||||
/**
|
||||
* Allows customising the {@link RequestConfig} of the underlying Apache HC5 instance.
|
||||
*
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.1
|
||||
*/
|
||||
@FunctionalInterface
|
||||
interface RequestConfigCustomizer {
|
||||
|
||||
void customize(RequestConfig.Builder builder);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
-147
@@ -1,147 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.util.Optional;
|
||||
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
import com.fasterxml.jackson.databind.BeanDescription;
|
||||
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.PropertyNamingStrategies;
|
||||
import com.fasterxml.jackson.databind.SerializationConfig;
|
||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||
import com.fasterxml.jackson.databind.module.SimpleModule;
|
||||
import com.fasterxml.jackson.databind.ser.BeanSerializerModifier;
|
||||
import com.fasterxml.jackson.databind.ser.std.BeanSerializerBase;
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.discovery.converters.jackson.mixin.ApplicationsJsonMixIn;
|
||||
import com.netflix.discovery.converters.jackson.mixin.InstanceInfoJsonMixIn;
|
||||
import com.netflix.discovery.converters.jackson.serializer.InstanceInfoJsonBeanSerializer;
|
||||
import com.netflix.discovery.shared.Applications;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
|
||||
import org.springframework.cloud.configuration.SSLContextFactory;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
|
||||
import org.springframework.lang.Nullable;
|
||||
|
||||
/**
|
||||
* Utility class for dealing with {@link EurekaHttpClient}.
|
||||
*
|
||||
* @author Daniel Lavoie
|
||||
* @author Wonchul Heo
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.0
|
||||
*/
|
||||
final class EurekaHttpClientUtils {
|
||||
|
||||
private EurekaHttpClientUtils() {
|
||||
throw new AssertionError("Must not instantiate constant utility class");
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides the serialization configurations required by the Eureka Server. JSON
|
||||
* content exchanged with eureka requires a root node matching the entity being
|
||||
* serialized or deserialized. Achieved with
|
||||
* {@link SerializationFeature#WRAP_ROOT_VALUE} and
|
||||
* {@link DeserializationFeature#UNWRAP_ROOT_VALUE}.
|
||||
* {@link PropertyNamingStrategies.SnakeCaseStrategy} is applied to the underlying
|
||||
* {@link ObjectMapper}.
|
||||
* @return a {@link MappingJackson2HttpMessageConverter} object
|
||||
*/
|
||||
static MappingJackson2HttpMessageConverter mappingJacksonHttpMessageConverter() {
|
||||
final MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
|
||||
converter.setObjectMapper(objectMapper());
|
||||
return converter;
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides the serialization configurations required by the Eureka Server. JSON
|
||||
* content exchanged with eureka requires a root node matching the entity being
|
||||
* serialized or deserialized. Achieved with
|
||||
* {@link SerializationFeature#WRAP_ROOT_VALUE} and
|
||||
* {@link DeserializationFeature#UNWRAP_ROOT_VALUE}.
|
||||
* {@link PropertyNamingStrategies.SnakeCaseStrategy} is applied to the underlying
|
||||
* {@link ObjectMapper}.
|
||||
* @return a {@link ObjectMapper} object
|
||||
*/
|
||||
static ObjectMapper objectMapper() {
|
||||
final ObjectMapper objectMapper = new ObjectMapper();
|
||||
objectMapper.setPropertyNamingStrategy(PropertyNamingStrategies.SNAKE_CASE);
|
||||
|
||||
final SimpleModule jsonModule = new SimpleModule();
|
||||
jsonModule.setSerializerModifier(createJsonSerializerModifier());
|
||||
objectMapper.registerModule(jsonModule);
|
||||
|
||||
objectMapper.configure(SerializationFeature.WRAP_ROOT_VALUE, true);
|
||||
objectMapper.configure(DeserializationFeature.UNWRAP_ROOT_VALUE, true);
|
||||
objectMapper.addMixIn(Applications.class, ApplicationsJsonMixIn.class);
|
||||
objectMapper.addMixIn(InstanceInfo.class, InstanceInfoJsonMixIn.class);
|
||||
|
||||
return objectMapper;
|
||||
}
|
||||
|
||||
private static BeanSerializerModifier createJsonSerializerModifier() {
|
||||
return new BeanSerializerModifier() {
|
||||
@Override
|
||||
public JsonSerializer<?> modifySerializer(SerializationConfig config, BeanDescription beanDesc,
|
||||
JsonSerializer<?> serializer) {
|
||||
if (beanDesc.getBeanClass().isAssignableFrom(InstanceInfo.class)) {
|
||||
return new InstanceInfoJsonBeanSerializer((BeanSerializerBase) serializer, false);
|
||||
}
|
||||
return serializer;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Nullable
|
||||
static UserInfo extractUserInfo(String serviceUrl) {
|
||||
try {
|
||||
final URI serviceURI = new URI(serviceUrl);
|
||||
if (serviceURI.getUserInfo() != null) {
|
||||
final String[] credentials = serviceURI.getUserInfo().split(":");
|
||||
if (credentials.length == 2) {
|
||||
return new UserInfo(credentials[0], credentials[1]);
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (URISyntaxException ignore) {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
static Optional<SSLContext> context(TlsProperties properties) {
|
||||
if (properties == null || !properties.isEnabled()) {
|
||||
return Optional.empty();
|
||||
}
|
||||
try {
|
||||
return Optional.of(new SSLContextFactory(properties).createSSLContext());
|
||||
}
|
||||
catch (Exception e) {
|
||||
throw new IllegalStateException(e);
|
||||
}
|
||||
}
|
||||
|
||||
record UserInfo(String username, String password) {
|
||||
}
|
||||
|
||||
}
|
||||
-67
@@ -1,67 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
||||
import org.springframework.http.HttpHeaders;
|
||||
import org.springframework.http.HttpStatusCode;
|
||||
import org.springframework.http.client.ClientHttpResponse;
|
||||
|
||||
/**
|
||||
* Response that ignores body, specifically for 404 errors.
|
||||
*
|
||||
* @author Spencer Gibb
|
||||
* @author Wonchul Heo
|
||||
* @since 4.2.0
|
||||
*/
|
||||
class NotFoundHttpResponse implements ClientHttpResponse {
|
||||
|
||||
private final ClientHttpResponse response;
|
||||
|
||||
NotFoundHttpResponse(ClientHttpResponse response) {
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
@Override
|
||||
public HttpStatusCode getStatusCode() throws IOException {
|
||||
return response.getStatusCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getStatusText() throws IOException {
|
||||
return response.getStatusText();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() {
|
||||
response.close();
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream getBody() throws IOException {
|
||||
// ignore body on 404 for heartbeat, see gh-4145
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public HttpHeaders getHeaders() {
|
||||
return response.getHeaders();
|
||||
}
|
||||
|
||||
}
|
||||
-55
@@ -1,55 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import com.netflix.discovery.AbstractDiscoveryClientOptionalArgs;
|
||||
import jakarta.ws.rs.client.ClientRequestFilter;
|
||||
|
||||
import org.springframework.web.client.RestClient;
|
||||
|
||||
/**
|
||||
* {@link RestClient} implementation of DiscoveryClientOptionalArgs that supports
|
||||
* supplying {@link ClientRequestFilter}.
|
||||
*
|
||||
* @author Wonchul Heo
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.0
|
||||
*/
|
||||
public class RestClientDiscoveryClientOptionalArgs extends AbstractDiscoveryClientOptionalArgs<Void> {
|
||||
|
||||
private final EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier;
|
||||
|
||||
private final Supplier<RestClient.Builder> restClientBuilderSupplier;
|
||||
|
||||
public RestClientDiscoveryClientOptionalArgs(
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
Supplier<RestClient.Builder> restClientBuilderSupplier) {
|
||||
this.eurekaClientHttpRequestFactorySupplier = eurekaClientHttpRequestFactorySupplier;
|
||||
this.restClientBuilderSupplier = restClientBuilderSupplier;
|
||||
}
|
||||
|
||||
EurekaClientHttpRequestFactorySupplier getEurekaClientHttpRequestFactorySupplier() {
|
||||
return eurekaClientHttpRequestFactorySupplier;
|
||||
}
|
||||
|
||||
Supplier<RestClient.Builder> getRestClientBuilderSupplier() {
|
||||
return restClientBuilderSupplier;
|
||||
}
|
||||
|
||||
}
|
||||
-238
@@ -1,238 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
import java.util.function.Function;
|
||||
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.appinfo.InstanceInfo.InstanceStatus;
|
||||
import com.netflix.discovery.shared.Application;
|
||||
import com.netflix.discovery.shared.Applications;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpResponse;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpResponse.EurekaHttpResponseBuilder;
|
||||
import com.netflix.discovery.util.StringUtil;
|
||||
|
||||
import org.springframework.http.HttpHeaders;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.util.UriBuilder;
|
||||
|
||||
import static com.netflix.discovery.shared.transport.EurekaHttpResponse.anEurekaHttpResponse;
|
||||
|
||||
/**
|
||||
* {@link RestClient} implementation of {@link EurekaHttpClient}.
|
||||
*
|
||||
* @author Wonchul Heo
|
||||
* @since 4.2.0
|
||||
*/
|
||||
public class RestClientEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
private final RestClient restClient;
|
||||
|
||||
public RestClientEurekaHttpClient(RestClient restClient) {
|
||||
this.restClient = restClient;
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> register(InstanceInfo info) {
|
||||
final ResponseEntity<Void> response = restClient.post()
|
||||
.uri(builder -> builder.pathSegment("apps", info.getAppName()).build())
|
||||
.body(info)
|
||||
.header(HttpHeaders.ACCEPT_ENCODING, "gzip")
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toBodilessEntity();
|
||||
return eurekaHttpResponse(response);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> cancel(String appName, String id) {
|
||||
final ResponseEntity<Void> response = restClient.delete()
|
||||
.uri(builder -> builder.pathSegment("apps", appName, id).build())
|
||||
.retrieve()
|
||||
.toBodilessEntity();
|
||||
return eurekaHttpResponse(response);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> sendHeartBeat(String appName, String id, InstanceInfo info,
|
||||
InstanceStatus overriddenStatus) {
|
||||
final Function<UriBuilder, URI> uriFunction = builder -> builder.pathSegment("apps", appName, id)
|
||||
.queryParam("status", info.getStatus().toString())
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.queryParamIfPresent("overriddenstatus", Optional.ofNullable(overriddenStatus).map(InstanceStatus::name))
|
||||
.build();
|
||||
|
||||
final ResponseEntity<InstanceInfo> response = restClient.put()
|
||||
.uri(uriFunction)
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toEntity(InstanceInfo.class);
|
||||
|
||||
final EurekaHttpResponseBuilder<InstanceInfo> builder = anEurekaHttpResponse(statusCodeValueOf(response),
|
||||
InstanceInfo.class)
|
||||
.headers(headersOf(response));
|
||||
|
||||
final InstanceInfo entity = response.getBody();
|
||||
if (entity != null) {
|
||||
builder.entity(entity);
|
||||
}
|
||||
|
||||
return builder.build();
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> statusUpdate(String appName, String id, InstanceStatus newStatus,
|
||||
InstanceInfo info) {
|
||||
final Function<UriBuilder, URI> uriFunction = builder -> builder.pathSegment("apps", appName, id, "status")
|
||||
.queryParam("value", newStatus.name())
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.build();
|
||||
|
||||
final ResponseEntity<Void> response = restClient.put()
|
||||
.uri(uriFunction)
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toBodilessEntity();
|
||||
return eurekaHttpResponse(response);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> deleteStatusOverride(String appName, String id, InstanceInfo info) {
|
||||
final Function<UriBuilder, URI> uriFunction = builder -> builder.pathSegment("apps", appName, id, "status")
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.build();
|
||||
|
||||
final ResponseEntity<Void> response = restClient.delete()
|
||||
.uri(uriFunction)
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toBodilessEntity();
|
||||
return eurekaHttpResponse(response);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Applications> getApplications(String... regions) {
|
||||
return getApplicationsInternal("/apps/", regions);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Applications> getDelta(String... regions) {
|
||||
return getApplicationsInternal("/apps/delta", regions);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Applications> getVip(String vipAddress, String... regions) {
|
||||
return getApplicationsInternal("/vips/" + vipAddress, regions);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Applications> getSecureVip(String secureVipAddress, String... regions) {
|
||||
return getApplicationsInternal("/svips/" + secureVipAddress, regions);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Application> getApplication(String appName) {
|
||||
|
||||
final ResponseEntity<Application> response = restClient.get()
|
||||
.uri("/apps/" + appName)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toEntity(Application.class);
|
||||
|
||||
final int statusCode = statusCodeValueOf(response);
|
||||
final Application body = response.getBody();
|
||||
|
||||
final Application application = statusCode == HttpStatus.OK.value() && body != null ? body : null;
|
||||
|
||||
return anEurekaHttpResponse(statusCode, application).headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> getInstance(String appName, String id) {
|
||||
return getInstanceInternal("/apps/" + appName + '/' + id);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> getInstance(String id) {
|
||||
return getInstanceInternal("/instances/" + id);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void shutdown() {
|
||||
}
|
||||
|
||||
public RestClient getRestClient() {
|
||||
return restClient;
|
||||
}
|
||||
|
||||
private EurekaHttpResponse<Applications> getApplicationsInternal(String urlPath, String[] regions) {
|
||||
final Function<UriBuilder, URI> uriFunction = builder -> builder
|
||||
.queryParamIfPresent("regions",
|
||||
Optional.ofNullable(regions).filter(it -> it.length > 0).map(StringUtil::join))
|
||||
.build();
|
||||
|
||||
final ResponseEntity<Applications> response = restClient.get()
|
||||
.uri(urlPath, uriFunction)
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toEntity(Applications.class);
|
||||
|
||||
final int statusCode = statusCodeValueOf(response);
|
||||
final Applications body = response.getBody();
|
||||
|
||||
return anEurekaHttpResponse(statusCode, statusCode == HttpStatus.OK.value() && body != null ? body : null)
|
||||
.headers(headersOf(response))
|
||||
.build();
|
||||
}
|
||||
|
||||
private EurekaHttpResponse<InstanceInfo> getInstanceInternal(String urlPath) {
|
||||
final ResponseEntity<InstanceInfo> response = restClient.get()
|
||||
.uri(urlPath)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.toEntity(InstanceInfo.class);
|
||||
|
||||
final int statusCode = statusCodeValueOf(response);
|
||||
final InstanceInfo body = response.getBody();
|
||||
|
||||
return anEurekaHttpResponse(statusCode, statusCode == HttpStatus.OK.value() && body != null ? body : null)
|
||||
.headers(headersOf(response))
|
||||
.build();
|
||||
}
|
||||
|
||||
private static Map<String, String> headersOf(ResponseEntity<?> response) {
|
||||
return response.getHeaders().toSingleValueMap();
|
||||
}
|
||||
|
||||
private static int statusCodeValueOf(ResponseEntity<?> response) {
|
||||
return response.getStatusCode().value();
|
||||
}
|
||||
|
||||
private static EurekaHttpResponse<Void> eurekaHttpResponse(ResponseEntity<?> response) {
|
||||
return anEurekaHttpResponse(statusCodeValueOf(response)).headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
}
|
||||
-58
@@ -1,58 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Optional;
|
||||
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.discovery.EurekaClientConfig;
|
||||
import com.netflix.discovery.shared.transport.TransportClientFactory;
|
||||
import com.netflix.discovery.shared.transport.jersey.TransportClientFactories;
|
||||
|
||||
/**
|
||||
* @author Wonchul Heo
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.0
|
||||
*/
|
||||
public class RestClientTransportClientFactories implements TransportClientFactories<Void> {
|
||||
|
||||
private final RestClientDiscoveryClientOptionalArgs args;
|
||||
|
||||
public RestClientTransportClientFactories(RestClientDiscoveryClientOptionalArgs args) {
|
||||
this.args = args;
|
||||
}
|
||||
|
||||
@Override
|
||||
public TransportClientFactory newTransportClientFactory(EurekaClientConfig clientConfig,
|
||||
Collection<Void> additionalFilters, InstanceInfo myInstanceInfo) {
|
||||
return new RestClientTransportClientFactory(args.getSSLContext(), args.getHostnameVerifier(),
|
||||
args.getEurekaClientHttpRequestFactorySupplier(), args.getRestClientBuilderSupplier());
|
||||
}
|
||||
|
||||
@Override
|
||||
public TransportClientFactory newTransportClientFactory(final EurekaClientConfig clientConfig,
|
||||
final Collection<Void> additionalFilters, final InstanceInfo myInstanceInfo,
|
||||
final Optional<SSLContext> sslContext, final Optional<HostnameVerifier> hostnameVerifier) {
|
||||
return new RestClientTransportClientFactory(args.getSSLContext(), args.getHostnameVerifier(),
|
||||
args.getEurekaClientHttpRequestFactorySupplier(), args.getRestClientBuilderSupplier());
|
||||
}
|
||||
|
||||
}
|
||||
-122
@@ -1,122 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.util.Optional;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
import com.netflix.discovery.shared.resolver.EurekaEndpoint;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
import com.netflix.discovery.shared.transport.TransportClientFactory;
|
||||
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.HttpStatusCode;
|
||||
import org.springframework.http.client.ClientHttpRequestFactory;
|
||||
import org.springframework.http.client.ClientHttpResponse;
|
||||
import org.springframework.http.client.support.BasicAuthenticationInterceptor;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.util.UriComponentsBuilder;
|
||||
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.context;
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.extractUserInfo;
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.mappingJacksonHttpMessageConverter;
|
||||
|
||||
/**
|
||||
* Provides the custom {@link RestClient} required by the
|
||||
* {@link RestClientEurekaHttpClient}. Relies on Jackson for serialization and
|
||||
* deserialization.
|
||||
*
|
||||
* @author Wonchul Heo
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @since 4.2.0
|
||||
*/
|
||||
public class RestClientTransportClientFactory implements TransportClientFactory {
|
||||
|
||||
private final Optional<SSLContext> sslContext;
|
||||
|
||||
private final Optional<HostnameVerifier> hostnameVerifier;
|
||||
|
||||
private final EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier;
|
||||
|
||||
private final Supplier<RestClient.Builder> builderSupplier;
|
||||
|
||||
public RestClientTransportClientFactory(Optional<SSLContext> sslContext,
|
||||
Optional<HostnameVerifier> hostnameVerifier,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
Supplier<RestClient.Builder> builderSupplier) {
|
||||
this.sslContext = sslContext;
|
||||
this.hostnameVerifier = hostnameVerifier;
|
||||
this.eurekaClientHttpRequestFactorySupplier = eurekaClientHttpRequestFactorySupplier;
|
||||
this.builderSupplier = builderSupplier;
|
||||
}
|
||||
|
||||
public RestClientTransportClientFactory(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
Supplier<RestClient.Builder> builderSupplier) {
|
||||
this(context(tlsProperties), Optional.empty(), eurekaClientHttpRequestFactorySupplier, builderSupplier);
|
||||
}
|
||||
|
||||
public RestClientTransportClientFactory(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
this(tlsProperties, eurekaClientHttpRequestFactorySupplier, RestClient::builder);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpClient newClient(EurekaEndpoint endpoint) {
|
||||
// we want a copy to modify. Don't change the original
|
||||
final RestClient.Builder builder = builderSupplier.get().clone();
|
||||
|
||||
ClientHttpRequestFactory requestFactory = this.eurekaClientHttpRequestFactorySupplier
|
||||
.get(this.sslContext.orElse(null), this.hostnameVerifier.orElse(null));
|
||||
|
||||
builder.requestFactory(requestFactory);
|
||||
setUrl(builder, endpoint.getServiceUrl());
|
||||
builder.messageConverters(converters -> converters.add(0, mappingJacksonHttpMessageConverter()));
|
||||
|
||||
builder.defaultStatusHandler(HttpStatusCode::isError, (req, res) -> {
|
||||
});
|
||||
|
||||
builder.requestInterceptor((request, body, execution) -> {
|
||||
final ClientHttpResponse response = execution.execute(request, body);
|
||||
if (!response.getStatusCode().equals(HttpStatus.NOT_FOUND)) {
|
||||
return response;
|
||||
}
|
||||
return new NotFoundHttpResponse(response);
|
||||
});
|
||||
|
||||
return new RestClientEurekaHttpClient(builder.build());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void shutdown() {
|
||||
}
|
||||
|
||||
private static void setUrl(RestClient.Builder builder, String serviceUrl) {
|
||||
final String url = UriComponentsBuilder.fromUriString(serviceUrl).userInfo(null).toUriString();
|
||||
|
||||
final EurekaHttpClientUtils.UserInfo userInfo = extractUserInfo(serviceUrl);
|
||||
if (userInfo != null) {
|
||||
builder.requestInterceptor(new BasicAuthenticationInterceptor(userInfo.username(), userInfo.password()));
|
||||
}
|
||||
builder.baseUrl(url);
|
||||
}
|
||||
|
||||
}
|
||||
+1
-20
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,37 +16,18 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import com.netflix.discovery.AbstractDiscoveryClientOptionalArgs;
|
||||
|
||||
import org.springframework.boot.restclient.RestTemplateBuilder;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
* @author Armin Krezovic
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated
|
||||
public class RestTemplateDiscoveryClientOptionalArgs extends AbstractDiscoveryClientOptionalArgs<Void> {
|
||||
|
||||
protected final EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier;
|
||||
|
||||
protected final Supplier<RestTemplateBuilder> restTemplateBuilderSupplier;
|
||||
|
||||
public RestTemplateDiscoveryClientOptionalArgs(
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
this(eurekaClientHttpRequestFactorySupplier, RestTemplateBuilder::new);
|
||||
}
|
||||
|
||||
public RestTemplateDiscoveryClientOptionalArgs(
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
Supplier<RestTemplateBuilder> restTemplateBuilderSupplier) {
|
||||
this.eurekaClientHttpRequestFactorySupplier = eurekaClientHttpRequestFactorySupplier;
|
||||
this.restTemplateBuilderSupplier = restTemplateBuilderSupplier;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+31
-63
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,7 +16,6 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.net.URI;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
@@ -38,19 +37,13 @@ import org.springframework.http.HttpMethod;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.util.UriComponentsBuilder;
|
||||
|
||||
import static com.netflix.discovery.shared.transport.EurekaHttpResponse.anEurekaHttpResponse;
|
||||
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
* @author Václav Plic
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
private final RestTemplate restTemplate;
|
||||
@@ -75,16 +68,13 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> register(InstanceInfo info) {
|
||||
URI uri = UriComponentsBuilder.fromUriString(serviceUrl)
|
||||
.path("apps/{appName}")
|
||||
.buildAndExpand(info.getAppName())
|
||||
.toUri();
|
||||
String urlPath = serviceUrl + "apps/" + info.getAppName();
|
||||
|
||||
HttpHeaders headers = new HttpHeaders();
|
||||
headers.add(HttpHeaders.ACCEPT_ENCODING, "gzip");
|
||||
headers.add(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE);
|
||||
|
||||
ResponseEntity<Void> response = restTemplate.exchange(uri, HttpMethod.POST, new HttpEntity<>(info, headers),
|
||||
ResponseEntity<Void> response = restTemplate.exchange(urlPath, HttpMethod.POST, new HttpEntity<>(info, headers),
|
||||
Void.class);
|
||||
|
||||
return anEurekaHttpResponse(response.getStatusCode().value()).headers(headersOf(response)).build();
|
||||
@@ -92,12 +82,9 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> cancel(String appName, String id) {
|
||||
URI uri = UriComponentsBuilder.fromUriString(serviceUrl)
|
||||
.path("apps/{appName}/{id}")
|
||||
.buildAndExpand(appName, id)
|
||||
.toUri();
|
||||
String urlPath = serviceUrl + "apps/" + appName + '/' + id;
|
||||
|
||||
ResponseEntity<Void> response = restTemplate.exchange(uri, HttpMethod.DELETE, null, Void.class);
|
||||
ResponseEntity<Void> response = restTemplate.exchange(urlPath, HttpMethod.DELETE, null, Void.class);
|
||||
|
||||
return anEurekaHttpResponse(response.getStatusCode().value()).headers(headersOf(response)).build();
|
||||
}
|
||||
@@ -105,22 +92,15 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> sendHeartBeat(String appName, String id, InstanceInfo info,
|
||||
InstanceStatus overriddenStatus) {
|
||||
UriComponentsBuilder uriBuilder = UriComponentsBuilder.fromUriString(serviceUrl)
|
||||
.path("apps/{appName}/{id}")
|
||||
.queryParam("status", info.getStatus().toString())
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString());
|
||||
String urlPath = serviceUrl + "apps/" + appName + '/' + id + "?status=" + info.getStatus().toString()
|
||||
+ "&lastDirtyTimestamp=" + info.getLastDirtyTimestamp().toString()
|
||||
+ (overriddenStatus != null ? "&overriddenstatus=" + overriddenStatus.name() : "");
|
||||
|
||||
if (overriddenStatus != null) {
|
||||
uriBuilder = uriBuilder.queryParam("overriddenstatus", overriddenStatus.name());
|
||||
}
|
||||
|
||||
URI uri = uriBuilder.buildAndExpand(appName, id).toUri();
|
||||
|
||||
ResponseEntity<InstanceInfo> response = restTemplate.exchange(uri, HttpMethod.PUT, null, InstanceInfo.class);
|
||||
ResponseEntity<InstanceInfo> response = restTemplate.exchange(urlPath, HttpMethod.PUT, null,
|
||||
InstanceInfo.class);
|
||||
|
||||
EurekaHttpResponseBuilder<InstanceInfo> eurekaResponseBuilder = anEurekaHttpResponse(
|
||||
response.getStatusCode().value(), InstanceInfo.class)
|
||||
.headers(headersOf(response));
|
||||
response.getStatusCode().value(), InstanceInfo.class).headers(headersOf(response));
|
||||
|
||||
if (response.hasBody()) {
|
||||
eurekaResponseBuilder.entity(response.getBody());
|
||||
@@ -132,27 +112,20 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> statusUpdate(String appName, String id, InstanceStatus newStatus,
|
||||
InstanceInfo info) {
|
||||
URI uri = UriComponentsBuilder.fromUriString(serviceUrl)
|
||||
.path("apps/{appName}/{id}/status")
|
||||
.queryParam("value", newStatus.name())
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.buildAndExpand(appName, id)
|
||||
.toUri();
|
||||
String urlPath = serviceUrl + "apps/" + appName + '/' + id + "/status?value=" + newStatus.name()
|
||||
+ "&lastDirtyTimestamp=" + info.getLastDirtyTimestamp().toString();
|
||||
|
||||
ResponseEntity<Void> response = restTemplate.exchange(uri, HttpMethod.PUT, null, Void.class);
|
||||
ResponseEntity<Void> response = restTemplate.exchange(urlPath, HttpMethod.PUT, null, Void.class);
|
||||
|
||||
return anEurekaHttpResponse(response.getStatusCode().value()).headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> deleteStatusOverride(String appName, String id, InstanceInfo info) {
|
||||
URI uri = UriComponentsBuilder.fromUriString(serviceUrl)
|
||||
.path("apps/{appName}/{id}/status")
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.buildAndExpand(appName, id)
|
||||
.toUri();
|
||||
String urlPath = serviceUrl + "apps/" + appName + '/' + id + "/status?lastDirtyTimestamp="
|
||||
+ info.getLastDirtyTimestamp().toString();
|
||||
|
||||
ResponseEntity<Void> response = restTemplate.exchange(uri, HttpMethod.DELETE, null, Void.class);
|
||||
ResponseEntity<Void> response = restTemplate.exchange(urlPath, HttpMethod.DELETE, null, Void.class);
|
||||
|
||||
return anEurekaHttpResponse(response.getStatusCode().value()).headers(headersOf(response)).build();
|
||||
}
|
||||
@@ -163,22 +136,18 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
}
|
||||
|
||||
private EurekaHttpResponse<Applications> getApplicationsInternal(String urlPath, String[] regions) {
|
||||
UriComponentsBuilder uriBuilder = UriComponentsBuilder.fromUriString(serviceUrl).path(urlPath);
|
||||
String url = serviceUrl + urlPath;
|
||||
|
||||
if (regions != null && regions.length > 0) {
|
||||
uriBuilder = uriBuilder.queryParam("regions", StringUtil.join(regions));
|
||||
url = url + (urlPath.contains("?") ? "&" : "?") + "regions=" + StringUtil.join(regions);
|
||||
}
|
||||
|
||||
URI uri = uriBuilder.build().toUri();
|
||||
|
||||
ResponseEntity<EurekaApplications> response = restTemplate.exchange(uri, HttpMethod.GET, null,
|
||||
ResponseEntity<EurekaApplications> response = restTemplate.exchange(url, HttpMethod.GET, null,
|
||||
EurekaApplications.class);
|
||||
|
||||
return anEurekaHttpResponse(response.getStatusCode().value(),
|
||||
response.getStatusCode().value() == HttpStatus.OK.value() && response.hasBody()
|
||||
? (Applications) response.getBody() : null)
|
||||
.headers(headersOf(response))
|
||||
.build();
|
||||
? (Applications) response.getBody() : null).headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -198,9 +167,9 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Application> getApplication(String appName) {
|
||||
URI uri = UriComponentsBuilder.fromUriString(serviceUrl).path("apps/{appName}").buildAndExpand(appName).toUri();
|
||||
String urlPath = serviceUrl + "apps/" + appName;
|
||||
|
||||
ResponseEntity<Application> response = restTemplate.exchange(uri, HttpMethod.GET, null, Application.class);
|
||||
ResponseEntity<Application> response = restTemplate.exchange(urlPath, HttpMethod.GET, null, Application.class);
|
||||
|
||||
Application application = response.getStatusCode().value() == HttpStatus.OK.value() && response.hasBody()
|
||||
? response.getBody() : null;
|
||||
@@ -210,24 +179,23 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> getInstance(String appName, String id) {
|
||||
return getInstanceInternal("apps", appName, id);
|
||||
return getInstanceInternal("apps/" + appName + '/' + id);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> getInstance(String id) {
|
||||
return getInstanceInternal("instances", id);
|
||||
return getInstanceInternal("instances/" + id);
|
||||
}
|
||||
|
||||
private EurekaHttpResponse<InstanceInfo> getInstanceInternal(String... pathSegments) {
|
||||
URI uri = UriComponentsBuilder.fromUriString(serviceUrl).pathSegment(pathSegments).build().toUri();
|
||||
private EurekaHttpResponse<InstanceInfo> getInstanceInternal(String urlPath) {
|
||||
urlPath = serviceUrl + urlPath;
|
||||
|
||||
ResponseEntity<InstanceInfo> response = restTemplate.exchange(uri, HttpMethod.GET, null, InstanceInfo.class);
|
||||
ResponseEntity<InstanceInfo> response = restTemplate.exchange(urlPath, HttpMethod.GET, null,
|
||||
InstanceInfo.class);
|
||||
|
||||
return anEurekaHttpResponse(response.getStatusCode().value(),
|
||||
response.getStatusCode().value() == HttpStatus.OK.value() && response.hasBody() ? response.getBody()
|
||||
: null)
|
||||
.headers(headersOf(response))
|
||||
.build();
|
||||
: null).headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -241,7 +209,7 @@ public class RestTemplateEurekaHttpClient implements EurekaHttpClient {
|
||||
return Collections.emptyMap();
|
||||
}
|
||||
Map<String, String> headers = new HashMap<>();
|
||||
for (Entry<String, List<String>> entry : httpHeaders.headerSet()) {
|
||||
for (Entry<String, List<String>> entry : httpHeaders.entrySet()) {
|
||||
if (!entry.getValue().isEmpty()) {
|
||||
headers.put(entry.getKey(), entry.getValue().get(0));
|
||||
}
|
||||
|
||||
+5
-12
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -27,16 +27,9 @@ import com.netflix.discovery.EurekaClientConfig;
|
||||
import com.netflix.discovery.shared.transport.TransportClientFactory;
|
||||
import com.netflix.discovery.shared.transport.jersey.TransportClientFactories;
|
||||
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
* @author Armin Krezovic
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
public class RestTemplateTransportClientFactories implements TransportClientFactories<Void> {
|
||||
|
||||
private final RestTemplateDiscoveryClientOptionalArgs args;
|
||||
@@ -48,16 +41,16 @@ public class RestTemplateTransportClientFactories implements TransportClientFact
|
||||
@Override
|
||||
public TransportClientFactory newTransportClientFactory(EurekaClientConfig clientConfig,
|
||||
Collection<Void> additionalFilters, InstanceInfo myInstanceInfo) {
|
||||
return new RestTemplateTransportClientFactory(args.getSSLContext(), args.getHostnameVerifier(),
|
||||
args.eurekaClientHttpRequestFactorySupplier, args.restTemplateBuilderSupplier);
|
||||
return new RestTemplateTransportClientFactory(this.args.getSSLContext(), this.args.getHostnameVerifier(),
|
||||
this.args.eurekaClientHttpRequestFactorySupplier);
|
||||
}
|
||||
|
||||
@Override
|
||||
public TransportClientFactory newTransportClientFactory(final EurekaClientConfig clientConfig,
|
||||
final Collection<Void> additionalFilters, final InstanceInfo myInstanceInfo,
|
||||
final Optional<SSLContext> sslContext, final Optional<HostnameVerifier> hostnameVerifier) {
|
||||
return new RestTemplateTransportClientFactory(args.getSSLContext(), args.getHostnameVerifier(),
|
||||
args.eurekaClientHttpRequestFactorySupplier, args.restTemplateBuilderSupplier);
|
||||
return new RestTemplateTransportClientFactory(this.args.getSSLContext(), this.args.getHostnameVerifier(),
|
||||
this.args.eurekaClientHttpRequestFactorySupplier);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+143
-62
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,45 +16,54 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.util.Optional;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.SSLContext;
|
||||
|
||||
import com.fasterxml.jackson.databind.BeanDescription;
|
||||
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.PropertyNamingStrategies;
|
||||
import com.fasterxml.jackson.databind.SerializationConfig;
|
||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||
import com.fasterxml.jackson.databind.module.SimpleModule;
|
||||
import com.fasterxml.jackson.databind.ser.BeanSerializerModifier;
|
||||
import com.fasterxml.jackson.databind.ser.std.BeanSerializerBase;
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.discovery.converters.jackson.mixin.ApplicationsJsonMixIn;
|
||||
import com.netflix.discovery.converters.jackson.mixin.InstanceInfoJsonMixIn;
|
||||
import com.netflix.discovery.converters.jackson.serializer.InstanceInfoJsonBeanSerializer;
|
||||
import com.netflix.discovery.shared.Applications;
|
||||
import com.netflix.discovery.shared.resolver.EurekaEndpoint;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
import com.netflix.discovery.shared.transport.TransportClientFactory;
|
||||
|
||||
import org.springframework.boot.restclient.RestTemplateBuilder;
|
||||
import org.springframework.cloud.configuration.SSLContextFactory;
|
||||
import org.springframework.cloud.configuration.TlsProperties;
|
||||
import org.springframework.http.HttpHeaders;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.HttpStatusCode;
|
||||
import org.springframework.http.client.ClientHttpRequestFactory;
|
||||
import org.springframework.http.client.ClientHttpResponse;
|
||||
import org.springframework.http.client.support.BasicAuthenticationInterceptor;
|
||||
import org.springframework.http.converter.json.MappingJackson2HttpMessageConverter;
|
||||
import org.springframework.web.client.DefaultResponseErrorHandler;
|
||||
import org.springframework.web.client.RestClient;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.util.UriComponentsBuilder;
|
||||
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.context;
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.extractUserInfo;
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.mappingJacksonHttpMessageConverter;
|
||||
|
||||
/**
|
||||
* Provides the custom {@link RestTemplate} required by the
|
||||
* {@link RestTemplateEurekaHttpClient}. Relies on Jackson for serialization and
|
||||
* deserialization.
|
||||
*
|
||||
* @author Daniel Lavoie
|
||||
* @author Armin Krezovic
|
||||
* @author Wonchul Heo
|
||||
* @author Olga Maciaszek-Sharma
|
||||
* @deprecated {@link RestTemplate}-based implementation to be removed in favour of
|
||||
* {@link RestClient}-based implementation.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
public class RestTemplateTransportClientFactory implements TransportClientFactory {
|
||||
|
||||
private final Optional<SSLContext> sslContext;
|
||||
@@ -63,44 +72,37 @@ public class RestTemplateTransportClientFactory implements TransportClientFactor
|
||||
|
||||
private final EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier;
|
||||
|
||||
private final Supplier<RestTemplateBuilder> restTemplateBuilderSupplier;
|
||||
public RestTemplateTransportClientFactory(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
this.sslContext = context(tlsProperties);
|
||||
this.hostnameVerifier = Optional.empty();
|
||||
this.eurekaClientHttpRequestFactorySupplier = eurekaClientHttpRequestFactorySupplier;
|
||||
}
|
||||
|
||||
private Optional<SSLContext> context(TlsProperties properties) {
|
||||
if (properties == null || !properties.isEnabled()) {
|
||||
return Optional.empty();
|
||||
}
|
||||
try {
|
||||
return Optional.of(new SSLContextFactory(properties).createSSLContext());
|
||||
}
|
||||
catch (Exception e) {
|
||||
throw new IllegalStateException(e);
|
||||
}
|
||||
}
|
||||
|
||||
public RestTemplateTransportClientFactory(Optional<SSLContext> sslContext,
|
||||
Optional<HostnameVerifier> hostnameVerifier,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
Supplier<RestTemplateBuilder> restTemplateBuilderSupplier) {
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
this.sslContext = sslContext;
|
||||
this.hostnameVerifier = hostnameVerifier;
|
||||
this.eurekaClientHttpRequestFactorySupplier = eurekaClientHttpRequestFactorySupplier;
|
||||
this.restTemplateBuilderSupplier = restTemplateBuilderSupplier;
|
||||
}
|
||||
|
||||
public RestTemplateTransportClientFactory(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier,
|
||||
Supplier<RestTemplateBuilder> restTemplateBuilderSupplier) {
|
||||
this(context(tlsProperties), Optional.empty(), eurekaClientHttpRequestFactorySupplier,
|
||||
restTemplateBuilderSupplier);
|
||||
}
|
||||
|
||||
public RestTemplateTransportClientFactory(TlsProperties tlsProperties,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
this(tlsProperties, eurekaClientHttpRequestFactorySupplier, RestTemplateBuilder::new);
|
||||
}
|
||||
|
||||
public RestTemplateTransportClientFactory(Optional<SSLContext> sslContext,
|
||||
Optional<HostnameVerifier> hostnameVerifier,
|
||||
EurekaClientHttpRequestFactorySupplier eurekaClientHttpRequestFactorySupplier) {
|
||||
|
||||
this(sslContext, hostnameVerifier, eurekaClientHttpRequestFactorySupplier, RestTemplateBuilder::new);
|
||||
}
|
||||
|
||||
// Visible for testing
|
||||
/**
|
||||
* @deprecated pass the default values while initialising object in test classes.
|
||||
*/
|
||||
@Deprecated(forRemoval = true)
|
||||
public RestTemplateTransportClientFactory() {
|
||||
this(Optional.empty(), Optional.empty(), new DefaultEurekaClientHttpRequestFactorySupplier());
|
||||
this.sslContext = Optional.empty();
|
||||
this.hostnameVerifier = Optional.empty();
|
||||
this.eurekaClientHttpRequestFactorySupplier = new DefaultEurekaClientHttpRequestFactorySupplier();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -117,25 +119,21 @@ public class RestTemplateTransportClientFactory implements TransportClientFactor
|
||||
|
||||
private RestTemplate restTemplate(String serviceUrl) {
|
||||
ClientHttpRequestFactory requestFactory = this.eurekaClientHttpRequestFactorySupplier
|
||||
.get(this.sslContext.orElse(null), this.hostnameVerifier.orElse(null));
|
||||
.get(this.sslContext.orElse(null), this.hostnameVerifier.orElse(null));
|
||||
RestTemplate restTemplate = new RestTemplate(requestFactory);
|
||||
|
||||
RestTemplate restTemplate;
|
||||
|
||||
if (restTemplateBuilderSupplier != null && restTemplateBuilderSupplier.get() != null) {
|
||||
// Avoid using RestTemplateBuilder.requestFactory(() -> requestFactory)
|
||||
// when we have a concrete type, the reflective builder can throw errors if
|
||||
// there is custom configuration (ie Redirects.DONT_FOLLOW) gh-4423
|
||||
restTemplate = restTemplateBuilderSupplier.get().build();
|
||||
restTemplate.setRequestFactory(requestFactory);
|
||||
}
|
||||
else {
|
||||
restTemplate = new RestTemplate(requestFactory);
|
||||
try {
|
||||
URI serviceURI = new URI(serviceUrl);
|
||||
if (serviceURI.getUserInfo() != null) {
|
||||
String[] credentials = serviceURI.getUserInfo().split(":");
|
||||
if (credentials.length == 2) {
|
||||
restTemplate.getInterceptors()
|
||||
.add(new BasicAuthenticationInterceptor(credentials[0], credentials[1]));
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (URISyntaxException ignore) {
|
||||
|
||||
final EurekaHttpClientUtils.UserInfo userInfo = extractUserInfo(serviceUrl);
|
||||
if (userInfo != null) {
|
||||
restTemplate.getInterceptors()
|
||||
.add(new BasicAuthenticationInterceptor(userInfo.username(), userInfo.password()));
|
||||
}
|
||||
|
||||
restTemplate.getMessageConverters().add(0, mappingJacksonHttpMessageConverter());
|
||||
@@ -152,19 +150,102 @@ public class RestTemplateTransportClientFactory implements TransportClientFactor
|
||||
return restTemplate;
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides the serialization configurations required by the Eureka Server. JSON
|
||||
* content exchanged with eureka requires a root node matching the entity being
|
||||
* serialized or deserialized. Achived with
|
||||
* {@link SerializationFeature#WRAP_ROOT_VALUE} and
|
||||
* {@link DeserializationFeature#UNWRAP_ROOT_VALUE}.
|
||||
* {@link PropertyNamingStrategies.SnakeCaseStrategy} is applied to the underlying
|
||||
* {@link ObjectMapper}.
|
||||
* @return a {@link MappingJackson2HttpMessageConverter} object
|
||||
*/
|
||||
public MappingJackson2HttpMessageConverter mappingJacksonHttpMessageConverter() {
|
||||
MappingJackson2HttpMessageConverter converter = new MappingJackson2HttpMessageConverter();
|
||||
converter.setObjectMapper(new ObjectMapper().setPropertyNamingStrategy(PropertyNamingStrategies.SNAKE_CASE));
|
||||
|
||||
SimpleModule jsonModule = new SimpleModule();
|
||||
jsonModule.setSerializerModifier(createJsonSerializerModifier());
|
||||
converter.getObjectMapper().registerModule(jsonModule);
|
||||
|
||||
converter.getObjectMapper().configure(SerializationFeature.WRAP_ROOT_VALUE, true);
|
||||
converter.getObjectMapper().configure(DeserializationFeature.UNWRAP_ROOT_VALUE, true);
|
||||
converter.getObjectMapper().addMixIn(Applications.class, ApplicationsJsonMixIn.class);
|
||||
converter.getObjectMapper().addMixIn(InstanceInfo.class, InstanceInfoJsonMixIn.class);
|
||||
|
||||
return converter;
|
||||
}
|
||||
|
||||
public static BeanSerializerModifier createJsonSerializerModifier() {
|
||||
return new BeanSerializerModifier() {
|
||||
@Override
|
||||
public JsonSerializer<?> modifySerializer(SerializationConfig config, BeanDescription beanDesc,
|
||||
JsonSerializer<?> serializer) {
|
||||
if (beanDesc.getBeanClass().isAssignableFrom(InstanceInfo.class)) {
|
||||
return new InstanceInfoJsonBeanSerializer((BeanSerializerBase) serializer, false);
|
||||
}
|
||||
return serializer;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Override
|
||||
public void shutdown() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Response that ignores body, specifically for 404 errors.
|
||||
*/
|
||||
private static class NotFoundHttpResponse implements ClientHttpResponse {
|
||||
|
||||
private final ClientHttpResponse response;
|
||||
|
||||
NotFoundHttpResponse(ClientHttpResponse response) {
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
@Override
|
||||
public HttpStatusCode getStatusCode() throws IOException {
|
||||
return response.getStatusCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getRawStatusCode() throws IOException {
|
||||
return response.getRawStatusCode();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getStatusText() throws IOException {
|
||||
return response.getStatusText();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void close() {
|
||||
response.close();
|
||||
}
|
||||
|
||||
@Override
|
||||
public InputStream getBody() throws IOException {
|
||||
// ignore body on 404 for heartbeat, see gh-4145
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public HttpHeaders getHeaders() {
|
||||
return response.getHeaders();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class ErrorHandler extends DefaultResponseErrorHandler {
|
||||
|
||||
@Override
|
||||
protected boolean hasError(HttpStatusCode statusCode) {
|
||||
/**
|
||||
* When the Eureka server restarts and a client tries to send a heartbeat the
|
||||
* server will respond with a 404. By default, RestTemplate will throw an
|
||||
* When the Eureka server restarts and a client tries to sent a heartbeat the
|
||||
* server will respond with a 404. By default RestTemplate will throw an
|
||||
* exception in this case. What we want is to return the 404 to the upstream
|
||||
* code, so it will send another registration request to the server.
|
||||
* code so it will send another registration request to the server.
|
||||
*/
|
||||
if (statusCode.is4xxClientError()) {
|
||||
return false;
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+49
-85
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -17,7 +17,6 @@
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.appinfo.InstanceInfo.InstanceStatus;
|
||||
@@ -43,7 +42,6 @@ import static com.netflix.discovery.shared.transport.EurekaHttpResponse.anEureka
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
* @author Haytham Mohamed
|
||||
* @author Václav Plic
|
||||
*/
|
||||
public class WebClientEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@@ -55,48 +53,34 @@ public class WebClientEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> register(InstanceInfo info) {
|
||||
return webClient.post()
|
||||
.uri(uriBuilder -> uriBuilder.path("apps/{appName}").build(info.getAppName()))
|
||||
.body(BodyInserters.fromValue(info))
|
||||
.header(HttpHeaders.ACCEPT_ENCODING, "gzip")
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toBodilessEntity()
|
||||
.map(this::eurekaHttpResponse)
|
||||
.block();
|
||||
return webClient.post().uri("apps/" + info.getAppName()).body(BodyInserters.fromValue(info))
|
||||
.header(HttpHeaders.ACCEPT_ENCODING, "gzip")
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE).retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError).toBodilessEntity().map(this::eurekaHttpResponse)
|
||||
.block();
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> cancel(String appName, String id) {
|
||||
return webClient.delete()
|
||||
.uri(uriBuilder -> uriBuilder.path("apps/{appName}/{id}").build(appName, id))
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toBodilessEntity()
|
||||
.map(this::eurekaHttpResponse)
|
||||
.block();
|
||||
return webClient.delete().uri("apps/" + appName + '/' + id).retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError).toBodilessEntity().map(this::eurekaHttpResponse)
|
||||
.block();
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> sendHeartBeat(String appName, String id, InstanceInfo info,
|
||||
InstanceStatus overriddenStatus) {
|
||||
String urlPath = "apps/" + appName + '/' + id + "?status=" + info.getStatus().toString()
|
||||
+ "&lastDirtyTimestamp=" + info.getLastDirtyTimestamp().toString()
|
||||
+ (overriddenStatus != null ? "&overriddenstatus=" + overriddenStatus.name() : "");
|
||||
|
||||
ResponseEntity<InstanceInfo> response = webClient.put()
|
||||
.uri(uriBuilder -> uriBuilder.path("apps/{appName}/{id}")
|
||||
.queryParam("status", info.getStatus().toString())
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.build(appName, id))
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toEntity(InstanceInfo.class)
|
||||
.block();
|
||||
ResponseEntity<InstanceInfo> response = webClient.put().uri(urlPath)
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError).toEntity(InstanceInfo.class).block();
|
||||
|
||||
EurekaHttpResponseBuilder<InstanceInfo> builder = anEurekaHttpResponse(statusCodeValueOf(response),
|
||||
InstanceInfo.class)
|
||||
.headers(headersOf(response));
|
||||
InstanceInfo.class).headers(headersOf(response));
|
||||
|
||||
InstanceInfo entity = response.getBody();
|
||||
|
||||
@@ -111,31 +95,22 @@ public class WebClientEurekaHttpClient implements EurekaHttpClient {
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> statusUpdate(String appName, String id, InstanceStatus newStatus,
|
||||
InstanceInfo info) {
|
||||
return webClient.put()
|
||||
.uri(uriBuilder -> uriBuilder.path("apps/{appName}/{id}/status")
|
||||
.queryParam("value", newStatus.name())
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.build(appName, id))
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toBodilessEntity()
|
||||
.map(this::eurekaHttpResponse)
|
||||
.block();
|
||||
String urlPath = "apps/" + appName + '/' + id + "/status?value=" + newStatus.name() + "&lastDirtyTimestamp="
|
||||
+ info.getLastDirtyTimestamp().toString();
|
||||
|
||||
return webClient.put().uri(urlPath).header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve().onStatus(HttpStatusCode::isError, this::ignoreError).toBodilessEntity()
|
||||
.map(this::eurekaHttpResponse).block();
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<Void> deleteStatusOverride(String appName, String id, InstanceInfo info) {
|
||||
return webClient.delete()
|
||||
.uri(uriBuilder -> uriBuilder.path("apps/{appName}/{id}/status")
|
||||
.queryParam("lastDirtyTimestamp", info.getLastDirtyTimestamp().toString())
|
||||
.build(appName, id))
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toBodilessEntity()
|
||||
.map(this::eurekaHttpResponse)
|
||||
.block();
|
||||
String urlPath = "apps/" + appName + '/' + id + "/status?lastDirtyTimestamp="
|
||||
+ info.getLastDirtyTimestamp().toString();
|
||||
|
||||
return webClient.delete().uri(urlPath).header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve().onStatus(HttpStatusCode::isError, this::ignoreError).toBodilessEntity()
|
||||
.map(this::eurekaHttpResponse).block();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -144,25 +119,23 @@ public class WebClientEurekaHttpClient implements EurekaHttpClient {
|
||||
}
|
||||
|
||||
private EurekaHttpResponse<Applications> getApplicationsInternal(String urlPath, String[] regions) {
|
||||
Optional<String> regionsParam = (regions != null && regions.length > 0) ? Optional.of(StringUtil.join(regions))
|
||||
: Optional.empty();
|
||||
String url = urlPath;
|
||||
|
||||
ResponseEntity<Applications> response = webClient.get()
|
||||
.uri(uriBuilder -> uriBuilder.path(urlPath).queryParamIfPresent("regions", regionsParam).build())
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toEntity(Applications.class)
|
||||
.block();
|
||||
if (regions != null && regions.length > 0) {
|
||||
url = url + (urlPath.contains("?") ? "&" : "?") + "regions=" + StringUtil.join(regions);
|
||||
}
|
||||
|
||||
ResponseEntity<Applications> response = webClient.get().uri(url)
|
||||
.header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError).toEntity(Applications.class).block();
|
||||
|
||||
int statusCode = statusCodeValueOf(response);
|
||||
|
||||
Applications body = response.getBody();
|
||||
|
||||
return anEurekaHttpResponse(statusCode, statusCode == HttpStatus.OK.value() && body != null ? body : null)
|
||||
.headers(headersOf(response))
|
||||
.build();
|
||||
.headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -183,13 +156,9 @@ public class WebClientEurekaHttpClient implements EurekaHttpClient {
|
||||
@Override
|
||||
public EurekaHttpResponse<Application> getApplication(String appName) {
|
||||
|
||||
ResponseEntity<Application> response = webClient.get()
|
||||
.uri(uriBuilder -> uriBuilder.path("apps/{appName}").build(appName))
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toEntity(Application.class)
|
||||
.block();
|
||||
ResponseEntity<Application> response = webClient.get().uri("apps/" + appName)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError).toEntity(Application.class).block();
|
||||
|
||||
int statusCode = statusCodeValueOf(response);
|
||||
Application body = response.getBody();
|
||||
@@ -201,29 +170,24 @@ public class WebClientEurekaHttpClient implements EurekaHttpClient {
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> getInstance(String appName, String id) {
|
||||
return getInstanceInternal("apps", appName, id);
|
||||
return getInstanceInternal("apps/" + appName + '/' + id);
|
||||
}
|
||||
|
||||
@Override
|
||||
public EurekaHttpResponse<InstanceInfo> getInstance(String id) {
|
||||
return getInstanceInternal("instances", id);
|
||||
return getInstanceInternal("instances/" + id);
|
||||
}
|
||||
|
||||
private EurekaHttpResponse<InstanceInfo> getInstanceInternal(String... pathSegments) {
|
||||
ResponseEntity<InstanceInfo> response = webClient.get()
|
||||
.uri(uriBuilder -> uriBuilder.pathSegment(pathSegments).build())
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE)
|
||||
.retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError)
|
||||
.toEntity(InstanceInfo.class)
|
||||
.block();
|
||||
private EurekaHttpResponse<InstanceInfo> getInstanceInternal(String urlPath) {
|
||||
ResponseEntity<InstanceInfo> response = webClient.get().uri(urlPath)
|
||||
.header(HttpHeaders.ACCEPT, MediaType.APPLICATION_JSON_VALUE).retrieve()
|
||||
.onStatus(HttpStatusCode::isError, this::ignoreError).toEntity(InstanceInfo.class).block();
|
||||
|
||||
int statusCode = statusCodeValueOf(response);
|
||||
InstanceInfo body = response.getBody();
|
||||
|
||||
return anEurekaHttpResponse(statusCode, statusCode == HttpStatus.OK.value() && body != null ? body : null)
|
||||
.headers(headersOf(response))
|
||||
.build();
|
||||
.headers(headersOf(response)).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+71
-17
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -16,9 +16,25 @@
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.http;
|
||||
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import com.fasterxml.jackson.databind.BeanDescription;
|
||||
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||
import com.fasterxml.jackson.databind.JsonSerializer;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.PropertyNamingStrategies;
|
||||
import com.fasterxml.jackson.databind.SerializationConfig;
|
||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||
import com.fasterxml.jackson.databind.module.SimpleModule;
|
||||
import com.fasterxml.jackson.databind.ser.BeanSerializerModifier;
|
||||
import com.fasterxml.jackson.databind.ser.std.BeanSerializerBase;
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import com.netflix.discovery.converters.jackson.mixin.ApplicationsJsonMixIn;
|
||||
import com.netflix.discovery.converters.jackson.mixin.InstanceInfoJsonMixIn;
|
||||
import com.netflix.discovery.converters.jackson.serializer.InstanceInfoJsonBeanSerializer;
|
||||
import com.netflix.discovery.shared.Applications;
|
||||
import com.netflix.discovery.shared.resolver.EurekaEndpoint;
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
import com.netflix.discovery.shared.transport.TransportClientFactory;
|
||||
@@ -34,10 +50,6 @@ import org.springframework.web.reactive.function.client.ClientResponse;
|
||||
import org.springframework.web.reactive.function.client.ExchangeFilterFunction;
|
||||
import org.springframework.web.reactive.function.client.ExchangeFilterFunctions;
|
||||
import org.springframework.web.reactive.function.client.WebClient;
|
||||
import org.springframework.web.util.UriComponentsBuilder;
|
||||
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.extractUserInfo;
|
||||
import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtils.objectMapper;
|
||||
|
||||
/**
|
||||
* Provides the custom {@link WebClient.Builder} required by the
|
||||
@@ -46,8 +58,6 @@ import static org.springframework.cloud.netflix.eureka.http.EurekaHttpClientUtil
|
||||
*
|
||||
* @author Daniel Lavoie
|
||||
* @author Haytham Mohamed
|
||||
* @author Armin Krezovic
|
||||
* @author Wonchul Heo
|
||||
*/
|
||||
public class WebClientTransportClientFactory implements TransportClientFactory {
|
||||
|
||||
@@ -68,15 +78,35 @@ public class WebClientTransportClientFactory implements TransportClientFactory {
|
||||
}
|
||||
|
||||
private WebClient.Builder setUrl(WebClient.Builder builder, String serviceUrl) {
|
||||
String url = UriComponentsBuilder.fromUriString(serviceUrl).userInfo(null).toUriString();
|
||||
|
||||
final EurekaHttpClientUtils.UserInfo userInfo = extractUserInfo(serviceUrl);
|
||||
if (userInfo != null) {
|
||||
builder.filter(ExchangeFilterFunctions.basicAuthentication(userInfo.username(), userInfo.password()));
|
||||
String url = serviceUrl;
|
||||
try {
|
||||
URI serviceURI = new URI(serviceUrl);
|
||||
if (serviceURI.getUserInfo() != null) {
|
||||
String[] credentials = serviceURI.getUserInfo().split(":");
|
||||
if (credentials.length == 2) {
|
||||
builder.filter(ExchangeFilterFunctions.basicAuthentication(credentials[0], credentials[1]));
|
||||
url = serviceUrl.replace(credentials[0] + ":" + credentials[1] + "@", "");
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (URISyntaxException ignore) {
|
||||
}
|
||||
return builder.baseUrl(url);
|
||||
}
|
||||
|
||||
private static BeanSerializerModifier createJsonSerializerModifier() {
|
||||
return new BeanSerializerModifier() {
|
||||
@Override
|
||||
public JsonSerializer<?> modifySerializer(SerializationConfig config, BeanDescription beanDesc,
|
||||
JsonSerializer<?> serializer) {
|
||||
if (beanDesc.getBeanClass().isAssignableFrom(InstanceInfo.class)) {
|
||||
return new InstanceInfoJsonBeanSerializer((BeanSerializerBase) serializer, false);
|
||||
}
|
||||
return serializer;
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private void setCodecs(WebClient.Builder builder) {
|
||||
ObjectMapper objectMapper = objectMapper();
|
||||
builder.codecs(configurer -> {
|
||||
@@ -87,6 +117,32 @@ public class WebClientTransportClientFactory implements TransportClientFactory {
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides the serialization configurations required by the Eureka Server. JSON
|
||||
* content exchanged with eureka requires a root node matching the entity being
|
||||
* serialized or deserialized. Achieved with
|
||||
* {@link SerializationFeature#WRAP_ROOT_VALUE} and
|
||||
* {@link DeserializationFeature#UNWRAP_ROOT_VALUE}.
|
||||
* {@link PropertyNamingStrategies.SnakeCaseStrategy} is applied to the underlying
|
||||
* {@link ObjectMapper}.
|
||||
* @return a {@link ObjectMapper} object
|
||||
*/
|
||||
private ObjectMapper objectMapper() {
|
||||
ObjectMapper objectMapper = new ObjectMapper();
|
||||
objectMapper.setPropertyNamingStrategy(PropertyNamingStrategies.SNAKE_CASE);
|
||||
|
||||
SimpleModule jsonModule = new SimpleModule();
|
||||
jsonModule.setSerializerModifier(createJsonSerializerModifier());
|
||||
objectMapper.registerModule(jsonModule);
|
||||
|
||||
objectMapper.configure(SerializationFeature.WRAP_ROOT_VALUE, true);
|
||||
objectMapper.configure(DeserializationFeature.UNWRAP_ROOT_VALUE, true);
|
||||
objectMapper.addMixIn(Applications.class, ApplicationsJsonMixIn.class);
|
||||
objectMapper.addMixIn(InstanceInfo.class, InstanceInfoJsonMixIn.class);
|
||||
|
||||
return objectMapper;
|
||||
}
|
||||
|
||||
// Skip over 4xx http errors
|
||||
private ExchangeFilterFunction http4XxErrorExchangeFilterFunction() {
|
||||
return ExchangeFilterFunction.ofResponseProcessor(clientResponse -> {
|
||||
@@ -97,11 +153,9 @@ public class WebClientTransportClientFactory implements TransportClientFactory {
|
||||
return Mono.just(newResponse);
|
||||
}
|
||||
if (clientResponse.statusCode().equals(HttpStatus.NOT_FOUND)) {
|
||||
ClientResponse newResponse = clientResponse.mutate()
|
||||
.statusCode(clientResponse.statusCode())
|
||||
// ignore body on 404 for heartbeat, see gh-4145
|
||||
.body(Flux.empty())
|
||||
.build();
|
||||
ClientResponse newResponse = clientResponse.mutate().statusCode(clientResponse.statusCode())
|
||||
// ignore body on 404 for heartbeat, see gh-4145
|
||||
.body(Flux.empty()).build();
|
||||
return Mono.just(newResponse);
|
||||
}
|
||||
return Mono.just(clientResponse);
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2012-present the original author or authors.
|
||||
* Copyright 2012-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+5
-6
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2019-present the original author or authors.
|
||||
* Copyright 2019-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -52,16 +52,15 @@ public class EurekaReactiveDiscoveryClient implements ReactiveDiscoveryClient {
|
||||
@Override
|
||||
public Flux<ServiceInstance> getInstances(String serviceId) {
|
||||
return Flux.defer(() -> Flux.fromIterable(eurekaClient.getInstancesByVipAddress(serviceId, false)))
|
||||
.map(EurekaServiceInstance::new);
|
||||
.map(EurekaServiceInstance::new);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Flux<String> getServices() {
|
||||
return Flux.defer(() -> Mono.justOrEmpty(eurekaClient.getApplications()))
|
||||
.flatMapIterable(Applications::getRegisteredApplications)
|
||||
.filter(application -> !application.getInstances().isEmpty())
|
||||
.map(Application::getName)
|
||||
.map(String::toLowerCase);
|
||||
.flatMapIterable(Applications::getRegisteredApplications)
|
||||
.filter(application -> !application.getInstances().isEmpty()).map(Application::getName)
|
||||
.map(String::toLowerCase);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
+2
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2019-present the original author or authors.
|
||||
* Copyright 2019-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -61,7 +61,7 @@ public class EurekaReactiveDiscoveryClientConfiguration {
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnClass(name = "org.springframework.boot.health.contributor.ReactiveHealthIndicator")
|
||||
@ConditionalOnClass(name = "org.springframework.boot.actuate.health.ReactiveHealthIndicator")
|
||||
@ConditionalOnDiscoveryHealthIndicatorEnabled
|
||||
public ReactiveDiscoveryClientHealthIndicator eurekaReactiveDiscoveryClientHealthIndicator(
|
||||
EurekaReactiveDiscoveryClient client, DiscoveryClientHealthIndicatorProperties properties) {
|
||||
|
||||
+2
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2023 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -22,7 +22,7 @@ import java.util.concurrent.atomic.AtomicInteger;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.boot.web.server.context.WebServerInitializedEvent;
|
||||
import org.springframework.boot.web.context.WebServerInitializedEvent;
|
||||
import org.springframework.cloud.client.discovery.event.InstancePreRegisteredEvent;
|
||||
import org.springframework.cloud.client.discovery.event.InstanceRegisteredEvent;
|
||||
import org.springframework.cloud.client.serviceregistry.AutoServiceRegistration;
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+3
-32
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -17,54 +17,25 @@
|
||||
package org.springframework.cloud.netflix.eureka.serviceregistry;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
|
||||
import com.netflix.appinfo.InstanceInfo;
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
|
||||
import org.springframework.cloud.client.serviceregistry.ServiceRegistry;
|
||||
import org.springframework.cloud.netflix.eureka.EurekaInstanceConfigBean;
|
||||
|
||||
import static com.netflix.appinfo.InstanceInfo.InstanceStatus.UNKNOWN;
|
||||
|
||||
/**
|
||||
* @author Spencer Gibb
|
||||
* @author Robert Bleyl
|
||||
*/
|
||||
public class EurekaServiceRegistry implements ServiceRegistry<EurekaRegistration> {
|
||||
|
||||
private static final Log log = LogFactory.getLog(EurekaServiceRegistry.class);
|
||||
|
||||
private EurekaInstanceConfigBean eurekaInstanceConfigBean;
|
||||
|
||||
public EurekaServiceRegistry() {
|
||||
|
||||
}
|
||||
|
||||
public EurekaServiceRegistry(EurekaInstanceConfigBean eurekaInstanceConfigBean) {
|
||||
this.eurekaInstanceConfigBean = eurekaInstanceConfigBean;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void register(EurekaRegistration reg) {
|
||||
if (eurekaInstanceConfigBean != null && eurekaInstanceConfigBean.isAsyncClientInitialization()) {
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Initializing client asynchronously...");
|
||||
}
|
||||
|
||||
ExecutorService executorService = Executors.newSingleThreadExecutor();
|
||||
executorService.submit(() -> {
|
||||
maybeInitializeClient(reg);
|
||||
if (log.isDebugEnabled()) {
|
||||
log.debug("Asynchronous client initialization done.");
|
||||
}
|
||||
});
|
||||
}
|
||||
else {
|
||||
maybeInitializeClient(reg);
|
||||
}
|
||||
maybeInitializeClient(reg);
|
||||
|
||||
if (log.isInfoEnabled()) {
|
||||
log.info("Registering application " + reg.getApplicationInfoManager().getInfo().getAppName()
|
||||
@@ -74,7 +45,7 @@ public class EurekaServiceRegistry implements ServiceRegistry<EurekaRegistration
|
||||
reg.getApplicationInfoManager().setInstanceStatus(reg.getInstanceConfig().getInitialStatus());
|
||||
|
||||
reg.getHealthCheckHandler()
|
||||
.ifAvailable(healthCheckHandler -> reg.getEurekaClient().registerHealthCheck(healthCheckHandler));
|
||||
.ifAvailable(healthCheckHandler -> reg.getEurekaClient().registerHealthCheck(healthCheckHandler));
|
||||
}
|
||||
|
||||
private void maybeInitializeClient(EurekaRegistration reg) {
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
-12
@@ -12,24 +12,12 @@
|
||||
"description": "Determines whether the EurekaClient instance can be refreshed or not(If disabled none of the Eureka client properties will be refreshable).",
|
||||
"type": "java.lang.Boolean"
|
||||
},
|
||||
{
|
||||
"defaultValue": false,
|
||||
"name": "eureka.client.restclient.enabled",
|
||||
"description": "Enables the use of RestClient for Eureka HTTP Client.",
|
||||
"type": "java.lang.Boolean"
|
||||
},
|
||||
{
|
||||
"defaultValue": false,
|
||||
"name": "eureka.client.webclient.enabled",
|
||||
"description": "Enables the use of WebClient for Eureka HTTP Client.",
|
||||
"type": "java.lang.Boolean"
|
||||
},
|
||||
{
|
||||
"defaultValue": true,
|
||||
"name": "eureka.client.jersey.enabled",
|
||||
"description": "Enables the use of JerseyClient for Eureka HTTP Client.",
|
||||
"type": "java.lang.Boolean"
|
||||
},
|
||||
{
|
||||
"defaultValue": 1,
|
||||
"name": "eureka.instance.metadata-map.weight",
|
||||
|
||||
+14
-18
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2015-present the original author or authors.
|
||||
* Copyright 2015-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -37,23 +37,20 @@ class ConditionalOnRefreshScopeTests {
|
||||
@Test
|
||||
void refreshScopeIncluded() {
|
||||
new ApplicationContextRunner().withConfiguration(AutoConfigurations.of(RefreshAutoConfiguration.class))
|
||||
.withUserConfiguration(Beans.class)
|
||||
.run(c -> {
|
||||
assertThat(c).hasSingleBean(org.springframework.cloud.context.scope.refresh.RefreshScope.class);
|
||||
assertThat(c.getBean("foo")).isEqualTo("foo");
|
||||
});
|
||||
.withUserConfiguration(Beans.class).run(c -> {
|
||||
assertThat(c).hasSingleBean(org.springframework.cloud.context.scope.refresh.RefreshScope.class);
|
||||
assertThat(c.getBean("foo")).isEqualTo("foo");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void refreshScopeIncludedAndPropertyDisabled() {
|
||||
new ApplicationContextRunner().withConfiguration(AutoConfigurations.of(RefreshAutoConfiguration.class))
|
||||
.withPropertyValues("eureka.client.refresh.enable=false")
|
||||
.withUserConfiguration(Beans.class)
|
||||
.run(c -> {
|
||||
assertThat(c).hasSingleBean(org.springframework.cloud.context.scope.refresh.RefreshScope.class);
|
||||
assertThat(c).doesNotHaveBean("foo");
|
||||
assertThat(c.getBean("bar")).isEqualTo("bar");
|
||||
});
|
||||
.withPropertyValues("eureka.client.refresh.enable=false").withUserConfiguration(Beans.class).run(c -> {
|
||||
assertThat(c).hasSingleBean(org.springframework.cloud.context.scope.refresh.RefreshScope.class);
|
||||
assertThat(c).doesNotHaveBean("foo");
|
||||
assertThat(c.getBean("bar")).isEqualTo("bar");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -64,11 +61,10 @@ class ConditionalOnRefreshScopeTests {
|
||||
});
|
||||
|
||||
new ApplicationContextRunner().withUserConfiguration(Beans.class)
|
||||
.withPropertyValues("eureka.client.refresh.enable=false")
|
||||
.run(c -> {
|
||||
assertThat(c).doesNotHaveBean("foo");
|
||||
assertThat(c.getBean("bar")).isEqualTo("bar");
|
||||
});
|
||||
.withPropertyValues("eureka.client.refresh.enable=false").run(c -> {
|
||||
assertThat(c).doesNotHaveBean("foo");
|
||||
assertThat(c.getBean("bar")).isEqualTo("bar");
|
||||
});
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+88
-132
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -118,7 +118,7 @@ class EurekaClientAutoConfigurationTests {
|
||||
@Test
|
||||
void shouldSetManagementAndJmxPortsInMetadataMap() {
|
||||
TestPropertyValues.of("management.server.port=9999", "com.sun.management.jmxremote.port=6789")
|
||||
.applyTo(this.context);
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
@@ -128,10 +128,8 @@ class EurekaClientAutoConfigurationTests {
|
||||
|
||||
@Test
|
||||
void shouldNotResetManagementAndJmxPortsInMetadataMap() {
|
||||
TestPropertyValues
|
||||
.of("management.server.port=9999", "eureka.instance.metadata-map.jmx.port=9898",
|
||||
"eureka.instance.metadata-map.management.port=7878")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("management.server.port=9999", "eureka.instance.metadata-map.jmx.port=9898",
|
||||
"eureka.instance.metadata-map.management.port=7878").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
@@ -180,128 +178,112 @@ class EurekaClientAutoConfigurationTests {
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().contains("9999")).as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlPathAndManagementPort() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "eureka.instance.statusPageUrlPath=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999",
|
||||
"eureka.instance.statusPageUrlPath=/myStatusPage").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().contains("/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathAndManagementPort() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "eureka.instance.healthCheckUrlPath=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999",
|
||||
"eureka.instance.healthCheckUrlPath=/myHealthCheck").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().contains("/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrl_and_healthCheckUrl_do_not_contain_server_context_path() {
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "server.contextPath=/service")
|
||||
.applyTo(this.context);
|
||||
.applyTo(this.context);
|
||||
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":9999/actuator/info"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":9999/actuator/health"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrl_and_healthCheckUrl_contain_management_context_path() {
|
||||
TestPropertyValues.of("server.port=8989", "management.server.servlet.context-path=/management")
|
||||
.applyTo(this.context);
|
||||
.applyTo(this.context);
|
||||
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":8989/management/actuator/info"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":8989/management/actuator/health"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrl_and_healthCheckUrl_contain_management_context_path_random_port() {
|
||||
TestPropertyValues.of("server.port=0", "management.server.servlet.context-path=/management")
|
||||
.applyTo(this.context);
|
||||
.applyTo(this.context);
|
||||
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrlPath().equals("/management/actuator/info"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrlPath())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrlPath()).isTrue();
|
||||
assertThat(instance.getHealthCheckUrlPath().equals("/management/actuator/health"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrlPath())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrlPath()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlPathAndManagementPortAndContextPath() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.servlet.context-path=/manage",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999",
|
||||
"management.server.servlet.context-path=/manage", "eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":9999/manage/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathAndManagementPortAndContextPath() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.servlet.context-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.servlet.context-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":9999/manage/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlPathAndManagementPortAndContextPathKebobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.servlet.context-path=/manage",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999",
|
||||
"management.server.servlet.context-path=/manage", "eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":9999/manage/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathAndManagementPortAndContextPathKebobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.servlet.context-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.servlet.context-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":9999/manage/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -311,11 +293,9 @@ class EurekaClientAutoConfigurationTests {
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":8989/management/actuator/info"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":8989/management/actuator/health"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -325,132 +305,111 @@ class EurekaClientAutoConfigurationTests {
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrlPath().equals("/management/actuator/info"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrlPath())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrlPath()).isTrue();
|
||||
assertThat(instance.getHealthCheckUrlPath().equals("/management/actuator/health"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrlPath())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrlPath()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlPathAndManagementPortAndBasePath() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":9999/manage/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathAndManagementPortAndBasePath() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":9999/manage/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlPathAndManagementPortAndBasePathKebobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().endsWith(":9999/manage/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathAndManagementPortAndBasePathKebobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "management.server.base-path=/manage",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().endsWith(":9999/manage/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathWithServerPortAndContextPathKebobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "server.servlet.context-path=/servletContextPath",
|
||||
"eureka.instance.health-check-url-path=${server.servlet.context-path:}/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
.of("server.port=8989", "server.servlet.context-path=/servletContextPath",
|
||||
"eureka.instance.health-check-url-path=${server.servlet.context-path:}/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl()).as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.endsWith(":8989/servletContextPath/myHealthCheck");
|
||||
.endsWith(":8989/servletContextPath/myHealthCheck");
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlPathAndManagementPortKabobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "eureka.instance.status-page-url-path=/myStatusPage")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999",
|
||||
"eureka.instance.status-page-url-path=/myStatusPage").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().contains("/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageUrlAndPreferIpAddress() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "eureka.instance.hostname=foo",
|
||||
"eureka.instance.prefer-ip-address:true")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "eureka.instance.hostname=foo",
|
||||
"eureka.instance.prefer-ip-address:true").applyTo(this.context);
|
||||
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
|
||||
assertThat(instance.getStatusPageUrl()).as("statusPageUrl is wrong")
|
||||
.isEqualTo("http://" + instance.getIpAddress() + ":9999/actuator/info");
|
||||
.isEqualTo("http://" + instance.getIpAddress() + ":9999/actuator/info");
|
||||
assertThat(instance.getHealthCheckUrl()).as("healthCheckUrl is wrong")
|
||||
.isEqualTo("http://" + instance.getIpAddress() + ":9999/actuator/health");
|
||||
.isEqualTo("http://" + instance.getIpAddress() + ":9999/actuator/health");
|
||||
}
|
||||
|
||||
@Test
|
||||
void statusPageAndHealthCheckUrlsShouldSetUserDefinedIpAddress() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999", "eureka.instance.hostname=foo",
|
||||
"eureka.instance.ip-address:192.168.13.90", "eureka.instance.prefer-ip-address:true")
|
||||
.applyTo(this.context);
|
||||
.of("server.port=8989", "management.server.port=9999", "eureka.instance.hostname=foo",
|
||||
"eureka.instance.ip-address:192.168.13.90", "eureka.instance.prefer-ip-address:true")
|
||||
.applyTo(this.context);
|
||||
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
|
||||
assertThat(instance.getStatusPageUrl()).as("statusPageUrl is wrong")
|
||||
.isEqualTo("http://192.168.13.90:9999/actuator/info");
|
||||
.isEqualTo("http://192.168.13.90:9999/actuator/info");
|
||||
assertThat(instance.getHealthCheckUrl()).as("healthCheckUrl is wrong")
|
||||
.isEqualTo("http://192.168.13.90:9999/actuator/health");
|
||||
.isEqualTo("http://192.168.13.90:9999/actuator/health");
|
||||
}
|
||||
|
||||
@Test
|
||||
void healthCheckUrlPathAndManagementPortKabobCase() {
|
||||
TestPropertyValues
|
||||
.of("server.port=8989", "management.server.port=9999",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999",
|
||||
"eureka.instance.health-check-url-path=/myHealthCheck").applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().contains("/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -460,8 +419,7 @@ class EurekaClientAutoConfigurationTests {
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().contains("/myStatusPage"))
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.as("Wrong status page: " + instance.getStatusPageUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -471,36 +429,35 @@ class EurekaClientAutoConfigurationTests {
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getHealthCheckUrl().contains("/myHealthCheck"))
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl())
|
||||
.isTrue();
|
||||
.as("Wrong health check: " + instance.getHealthCheckUrl()).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void hostname() {
|
||||
TestPropertyValues.of("server.port=8989", "management.server.port=9999", "eureka.instance.hostname=foo")
|
||||
.applyTo(this.context);
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
EurekaInstanceConfigBean instance = this.context.getBean(EurekaInstanceConfigBean.class);
|
||||
assertThat(instance.getStatusPageUrl().contains("foo")).as("Wrong status page: " + instance.getStatusPageUrl())
|
||||
.isTrue();
|
||||
.isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
void refreshScopedBeans() {
|
||||
setupContext(RefreshAutoConfiguration.class);
|
||||
assertThat(this.context.getBeanDefinition("eurekaClient").getBeanClassName())
|
||||
.startsWith(GenericScope.class.getName() + "$LockedScopedProxyFactoryBean");
|
||||
.startsWith(GenericScope.class.getName() + "$LockedScopedProxyFactoryBean");
|
||||
assertThat(this.context.getBeanDefinition("eurekaApplicationInfoManager").getBeanClassName())
|
||||
.startsWith(GenericScope.class.getName() + "$LockedScopedProxyFactoryBean");
|
||||
.startsWith(GenericScope.class.getName() + "$LockedScopedProxyFactoryBean");
|
||||
}
|
||||
|
||||
@SuppressWarnings({ "unchecked", "rawtypes" })
|
||||
@Test
|
||||
void shouldReregisterHealthCheckHandlerAfterRefresh() throws Exception {
|
||||
TestPropertyValues
|
||||
.of("eureka.client.healthcheck.enabled=true", "spring.cloud.config.import-check.enabled=false",
|
||||
"spring.cloud.refresh.additionalPropertySourcesToRetain=test")
|
||||
.applyTo(this.context);
|
||||
.of("eureka.client.healthcheck.enabled=true", "spring.cloud.config.import-check.enabled=false",
|
||||
"spring.cloud.refresh.additionalPropertySourcesToRetain=test")
|
||||
.applyTo(this.context);
|
||||
setupContext(RefreshAutoConfiguration.class, AutoServiceRegistrationConfiguration.class);
|
||||
|
||||
EurekaClient oldEurekaClient = getLazyInitEurekaClient();
|
||||
@@ -640,14 +597,13 @@ class EurekaClientAutoConfigurationTests {
|
||||
@Test
|
||||
void shouldNotHaveDiscoveryClientWhenBlockingDiscoveryDisabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(
|
||||
AutoConfigurations.of(UtilAutoConfiguration.class, DiscoveryClientOptionalArgsConfiguration.class,
|
||||
EurekaClientAutoConfiguration.class, EurekaDiscoveryClientConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.discovery.blocking.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).doesNotHaveBean(DiscoveryClient.class);
|
||||
assertThat(context).doesNotHaveBean(DiscoveryClientHealthIndicator.class);
|
||||
});
|
||||
.withConfiguration(AutoConfigurations.of(UtilAutoConfiguration.class,
|
||||
DiscoveryClientOptionalArgsConfiguration.class, EurekaClientAutoConfiguration.class,
|
||||
EurekaDiscoveryClientConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.discovery.blocking.enabled=false").run(context -> {
|
||||
assertThat(context).doesNotHaveBean(DiscoveryClient.class);
|
||||
assertThat(context).doesNotHaveBean(DiscoveryClientHealthIndicator.class);
|
||||
});
|
||||
}
|
||||
|
||||
@SuppressWarnings({ "unchecked", "rawtypes" })
|
||||
@@ -685,7 +641,7 @@ class EurekaClientAutoConfigurationTests {
|
||||
|
||||
private EurekaClient getLazyInitEurekaClient() throws Exception {
|
||||
return (EurekaClient) ((Advised) this.context.getBean("eurekaClient", EurekaClient.class)).getTargetSource()
|
||||
.getTarget();
|
||||
.getTarget();
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
|
||||
+2
-2
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -59,7 +59,7 @@ class EurekaClientConfigBeanTests {
|
||||
this.context.register(PropertyPlaceholderAutoConfiguration.class, TestConfiguration.class);
|
||||
this.context.refresh();
|
||||
assertThat(this.context.getBean(EurekaClientConfigBean.class).getServiceUrl().toString())
|
||||
.isEqualTo("{defaultZone=https://example.com}");
|
||||
.isEqualTo("{defaultZone=https://example.com}");
|
||||
assertThat(getEurekaServiceUrlsForDefaultZone()).isEqualTo("[https://example.com/]");
|
||||
}
|
||||
|
||||
|
||||
+26
-14
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -17,24 +17,24 @@
|
||||
package org.springframework.cloud.netflix.eureka;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import com.netflix.appinfo.InstanceInfo.InstanceStatus;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
import org.springframework.boot.actuate.health.AbstractHealthIndicator;
|
||||
import org.springframework.boot.actuate.health.AbstractReactiveHealthIndicator;
|
||||
import org.springframework.boot.actuate.health.CompositeHealthContributor;
|
||||
import org.springframework.boot.actuate.health.Health;
|
||||
import org.springframework.boot.actuate.health.HealthContributor;
|
||||
import org.springframework.boot.actuate.health.HealthIndicator;
|
||||
import org.springframework.boot.actuate.health.NamedContributor;
|
||||
import org.springframework.boot.actuate.health.ReactiveHealthIndicator;
|
||||
import org.springframework.boot.actuate.health.SimpleStatusAggregator;
|
||||
import org.springframework.boot.health.contributor.AbstractHealthIndicator;
|
||||
import org.springframework.boot.health.contributor.AbstractReactiveHealthIndicator;
|
||||
import org.springframework.boot.health.contributor.CompositeHealthContributor;
|
||||
import org.springframework.boot.health.contributor.Health;
|
||||
import org.springframework.boot.health.contributor.HealthContributor;
|
||||
import org.springframework.boot.health.contributor.HealthContributors;
|
||||
import org.springframework.boot.health.contributor.HealthIndicator;
|
||||
import org.springframework.boot.health.contributor.ReactiveHealthIndicator;
|
||||
import org.springframework.cloud.client.discovery.health.DiscoveryClientHealthIndicator;
|
||||
import org.springframework.cloud.client.discovery.health.DiscoveryCompositeHealthContributor;
|
||||
import org.springframework.cloud.client.discovery.health.DiscoveryHealthIndicator;
|
||||
@@ -319,10 +319,22 @@ class EurekaHealthCheckHandlerTests {
|
||||
}
|
||||
|
||||
@Override
|
||||
public Stream<HealthContributors.Entry> stream() {
|
||||
return contributorMap.entrySet()
|
||||
.stream()
|
||||
.map((entry) -> new HealthContributors.Entry(entry.getKey(), entry.getValue()));
|
||||
public Iterator<NamedContributor<HealthContributor>> iterator() {
|
||||
Iterator<Map.Entry<String, HealthContributor>> iterator = contributorMap.entrySet().iterator();
|
||||
return new Iterator<>() {
|
||||
|
||||
@Override
|
||||
public boolean hasNext() {
|
||||
return iterator.hasNext();
|
||||
}
|
||||
|
||||
@Override
|
||||
public NamedContributor<HealthContributor> next() {
|
||||
Map.Entry<String, HealthContributor> entry = iterator.next();
|
||||
return NamedContributor.of(entry.getKey(), entry.getValue());
|
||||
}
|
||||
|
||||
};
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+7
-10
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -169,8 +169,7 @@ class EurekaInstanceConfigBeanTests {
|
||||
setupContext();
|
||||
EurekaInstanceConfigBean instance = getInstanceConfig();
|
||||
assertThat(getInstanceConfig().getHostname().equals(instance.getIpAddress()))
|
||||
.as("Wrong hostname: " + instance.getHostname())
|
||||
.isTrue();
|
||||
.as("Wrong hostname: " + instance.getHostname()).isTrue();
|
||||
|
||||
}
|
||||
|
||||
@@ -185,14 +184,12 @@ class EurekaInstanceConfigBeanTests {
|
||||
|
||||
@Test
|
||||
void testCustomVirtualHostName() {
|
||||
TestPropertyValues
|
||||
.of("spring.application.name:myapp", "eureka.instance.virtualHostName=myvirthost",
|
||||
"eureka.instance.secureVirtualHostName=mysecurevirthost")
|
||||
.applyTo(this.context);
|
||||
TestPropertyValues.of("spring.application.name:myapp", "eureka.instance.virtualHostName=myvirthost",
|
||||
"eureka.instance.secureVirtualHostName=mysecurevirthost").applyTo(this.context);
|
||||
setupContext();
|
||||
assertThat(getInstanceConfig().getVirtualHostName()).as("virtualHostName wrong").isEqualTo("myvirthost");
|
||||
assertThat(getInstanceConfig().getSecureVirtualHostName()).as("secureVirtualHostName wrong")
|
||||
.isEqualTo("mysecurevirthost");
|
||||
.isEqualTo("mysecurevirthost");
|
||||
|
||||
}
|
||||
|
||||
@@ -201,9 +198,9 @@ class EurekaInstanceConfigBeanTests {
|
||||
setupContext();
|
||||
assertThat(getInstanceConfig().getAppname()).as("default app name is wrong").isEqualTo("unknown");
|
||||
assertThat(getInstanceConfig().getVirtualHostName()).as("default virtual hostname is wrong")
|
||||
.isEqualTo("unknown");
|
||||
.isEqualTo("unknown");
|
||||
assertThat(getInstanceConfig().getSecureVirtualHostName()).as("default secure virtual hostname is wrong")
|
||||
.isEqualTo("unknown");
|
||||
.isEqualTo("unknown");
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
+3
-6
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -24,11 +24,8 @@ class EurekaServiceInstanceTests {
|
||||
|
||||
@Test
|
||||
void getSchemeReturnsNonNull() {
|
||||
InstanceInfo instanceInfo = InstanceInfo.Builder.newBuilder()
|
||||
.setAppName("test")
|
||||
.setHostName("myhost")
|
||||
.setPort(8080)
|
||||
.build();
|
||||
InstanceInfo instanceInfo = InstanceInfo.Builder.newBuilder().setAppName("test").setHostName("myhost")
|
||||
.setPort(8080).build();
|
||||
EurekaServiceInstance instance = new EurekaServiceInstance(instanceInfo);
|
||||
Assertions.assertThat(instance.getScheme()).isEqualTo("http");
|
||||
}
|
||||
|
||||
+1
-1
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
|
||||
+2
-6
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -31,7 +31,6 @@ import static org.springframework.boot.test.context.SpringBootTest.WebEnvironmen
|
||||
|
||||
/**
|
||||
* @author Ryan Baxter
|
||||
* @author Kaiyao Ke
|
||||
*/
|
||||
@SpringBootTest(webEnvironment = RANDOM_PORT, classes = RefreshEurekaSampleApplication.class)
|
||||
class ConfigRefreshTests {
|
||||
@@ -43,8 +42,6 @@ class ConfigRefreshTests {
|
||||
// Mocked in RefreshEurekaSampleApplication
|
||||
private EurekaClient client;
|
||||
|
||||
private static boolean isFirstRun = true;
|
||||
|
||||
@Test
|
||||
// This test is used to verify that getApplications is called the correct number of
|
||||
// times when a refresh event is fired. The getApplications call in
|
||||
@@ -52,9 +49,8 @@ class ConfigRefreshTests {
|
||||
// ensures that the EurekaClient bean is recreated after a refresh event and that we
|
||||
// reregister the client with the server
|
||||
void verifyGetApplications() {
|
||||
if (publisher != null && isFirstRun) {
|
||||
if (publisher != null) {
|
||||
publisher.publishEvent(new RefreshScopeRefreshedEvent());
|
||||
isFirstRun = false;
|
||||
}
|
||||
verify(client, times(3)).getApplications();
|
||||
}
|
||||
|
||||
+18
-20
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -36,35 +36,33 @@ class EurekaClientConfigServerAutoConfigurationTests {
|
||||
@Test
|
||||
void offByDefault() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaClientConfigServerAutoConfiguration.class))
|
||||
.run(c -> assertThat(c.getBeanNamesForType(EurekaInstanceConfigBean.class).length).isEqualTo(0));
|
||||
.withConfiguration(AutoConfigurations.of(EurekaClientConfigServerAutoConfiguration.class))
|
||||
.run(c -> assertThat(c.getBeanNamesForType(EurekaInstanceConfigBean.class).length).isEqualTo(0));
|
||||
}
|
||||
|
||||
@Test
|
||||
void onWhenRequested() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaClientConfigServerAutoConfiguration.class,
|
||||
UtilAutoConfiguration.class, ConfigServerProperties.class, EurekaInstanceConfigBean.class))
|
||||
.withPropertyValues("spring.cloud.config.server.prefix=/config")
|
||||
.run(c -> {
|
||||
assertThat(c.getBeanNamesForType(EurekaInstanceConfig.class).length).isEqualTo(1);
|
||||
EurekaInstanceConfig instance = c.getBean(EurekaInstanceConfig.class);
|
||||
assertThat(instance.getMetadataMap().get("configPath")).isEqualTo("/config");
|
||||
});
|
||||
.withConfiguration(AutoConfigurations.of(EurekaClientConfigServerAutoConfiguration.class,
|
||||
UtilAutoConfiguration.class, ConfigServerProperties.class, EurekaInstanceConfigBean.class))
|
||||
.withPropertyValues("spring.cloud.config.server.prefix=/config").run(c -> {
|
||||
assertThat(c.getBeanNamesForType(EurekaInstanceConfig.class).length).isEqualTo(1);
|
||||
EurekaInstanceConfig instance = c.getBean(EurekaInstanceConfig.class);
|
||||
assertThat(instance.getMetadataMap().get("configPath")).isEqualTo("/config");
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void notOverridingMetamapSettings() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaClientConfigServerAutoConfiguration.class,
|
||||
UtilAutoConfiguration.class, ConfigServerProperties.class, EurekaInstanceConfigBean.class))
|
||||
.withPropertyValues("spring.cloud.config.server.prefix=/config")
|
||||
.withPropertyValues("eureka.instance.metadataMap.configPath=/differentpath")
|
||||
.run(c -> {
|
||||
assertThat(c.getBeanNamesForType(EurekaInstanceConfig.class).length).isEqualTo(1);
|
||||
EurekaInstanceConfig instance = c.getBean(EurekaInstanceConfig.class);
|
||||
assertThat(instance.getMetadataMap().get("configPath")).isEqualTo("/differentpath");
|
||||
});
|
||||
.withConfiguration(AutoConfigurations.of(EurekaClientConfigServerAutoConfiguration.class,
|
||||
UtilAutoConfiguration.class, ConfigServerProperties.class, EurekaInstanceConfigBean.class))
|
||||
.withPropertyValues("spring.cloud.config.server.prefix=/config")
|
||||
.withPropertyValues("eureka.instance.metadataMap.configPath=/differentpath").run(c -> {
|
||||
assertThat(c.getBeanNamesForType(EurekaInstanceConfig.class).length).isEqualTo(1);
|
||||
EurekaInstanceConfig instance = c.getBean(EurekaInstanceConfig.class);
|
||||
assertThat(instance.getMetadataMap().get("configPath")).isEqualTo("/differentpath");
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
-131
@@ -1,131 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import com.netflix.discovery.shared.transport.EurekaHttpClient;
|
||||
import org.junit.jupiter.api.Nested;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
|
||||
import org.springframework.boot.autoconfigure.AutoConfigurations;
|
||||
import org.springframework.boot.test.context.runner.ApplicationContextRunner;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientEurekaHttpClient;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateEurekaHttpClient;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientEurekaHttpClient;
|
||||
import org.springframework.cloud.test.ClassPathExclusions;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatThrownBy;
|
||||
|
||||
/**
|
||||
* @author Wonchul Heo
|
||||
*/
|
||||
class EurekaConfigServerBootstrapConfigurationClientTests {
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenRestTemplateEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.withPropertyValues("eureka.client.restclient.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientEurekaHttpClient.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenRestClientEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.withPropertyValues("eureka.client.restclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestClientEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientEurekaHttpClient.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenWebClientEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.withPropertyValues("eureka.client.webclient.enabled=true")
|
||||
.run(context -> {
|
||||
final EurekaHttpClient bean = context.getBean(EurekaHttpClient.class);
|
||||
System.out.println(bean);
|
||||
assertThat(context).hasSingleBean(WebClientEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientEurekaHttpClient.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Nested
|
||||
@ClassPathExclusions({ "spring-webflux-*" })
|
||||
static class NoWebFlux {
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenRestTemplateEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.withPropertyValues("eureka.client.restclient.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientEurekaHttpClient.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenRestClientEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.withPropertyValues("eureka.client.restclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestClientEurekaHttpClient.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientEurekaHttpClient.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenWebClientEnabledThenFailed() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.withPropertyValues("eureka.client.webclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThatThrownBy(() -> context.getBean(WebClientEurekaHttpClient.class))
|
||||
.hasRootCauseInstanceOf(NoSuchBeanDefinitionException.class)
|
||||
.hasRootCauseMessage(
|
||||
"No qualifying bean of type 'com.netflix.discovery.shared.transport.EurekaHttpClient' available: "
|
||||
+ "expected at least 1 bean which qualifies as autowire candidate. "
|
||||
+ "Dependency annotations: {}");
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
-87
@@ -1,87 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.boot.web.server.test.LocalServerPort;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientEurekaHttpClient;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
|
||||
import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer;
|
||||
import org.springframework.security.web.SecurityFilterChain;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import org.springframework.web.client.RestClient;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.boot.test.context.SpringBootTest.WebEnvironment.RANDOM_PORT;
|
||||
|
||||
/**
|
||||
* @author Wonchul Heo
|
||||
*/
|
||||
@SpringBootTest(
|
||||
properties = { "spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"spring.config.use-legacy-processing=true", "eureka.client.restclient.enabled=true" },
|
||||
webEnvironment = RANDOM_PORT)
|
||||
class EurekaConfigServerBootstrapConfigurationRestClientIntegrationTests {
|
||||
|
||||
@LocalServerPort
|
||||
private int port;
|
||||
|
||||
@Autowired
|
||||
private RestClientEurekaHttpClient eurekaHttpClient;
|
||||
|
||||
@Test
|
||||
void restClientRespectsCodecProperties() {
|
||||
RestClient restClient = eurekaHttpClient.getRestClient();
|
||||
ResponseEntity<String> response = restClient.get()
|
||||
.uri("http://localhost:" + port)
|
||||
.retrieve()
|
||||
.toEntity(String.class);
|
||||
|
||||
assertThat(response).isNotNull();
|
||||
assertThat(response.getStatusCode()).isEqualTo(HttpStatus.OK);
|
||||
assertThat(response.getBody()).isEqualTo("rest-client");
|
||||
}
|
||||
|
||||
@SpringBootConfiguration(proxyBeanMethods = false)
|
||||
@EnableAutoConfiguration
|
||||
@RestController
|
||||
static class RestClientController {
|
||||
|
||||
@GetMapping("/")
|
||||
public String hello() {
|
||||
return "rest-client";
|
||||
}
|
||||
|
||||
@Bean
|
||||
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
|
||||
return http.authorizeHttpRequests(auth -> auth.anyRequest().permitAll())
|
||||
.csrf(AbstractHttpConfigurer::disable)
|
||||
.build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
-62
@@ -1,62 +0,0 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.boot.autoconfigure.AutoConfigurations;
|
||||
import org.springframework.boot.test.context.runner.ApplicationContextRunner;
|
||||
import org.springframework.cloud.config.client.ConfigServerInstanceProvider;
|
||||
import org.springframework.cloud.netflix.eureka.EurekaClientConfigBean;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientEurekaHttpClient;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateEurekaHttpClient;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
/**
|
||||
* @author Wonchul Heo
|
||||
*/
|
||||
class EurekaConfigServerBootstrapConfigurationRestClientTests {
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"eureka.client.restclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(EurekaClientConfigBean.class);
|
||||
assertThat(context).hasSingleBean(RestClientEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(ConfigServerInstanceProvider.Function.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenEnabledRestClientDisabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"eureka.client.restclient.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(EurekaClientConfigBean.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(RestTemplateEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(ConfigServerInstanceProvider.Function.class);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
+43
-81
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -51,9 +51,7 @@ import static org.mockito.Mockito.when;
|
||||
|
||||
/**
|
||||
* @author Spencer Gibb
|
||||
* @author Tang Xiong
|
||||
*/
|
||||
@SuppressWarnings("removal")
|
||||
@RunWith(ModifiedClassPathRunner.class)
|
||||
@ClassPathExclusions("spring-webflux-*")
|
||||
public class EurekaConfigServerBootstrapConfigurationTests {
|
||||
@@ -64,100 +62,96 @@ public class EurekaConfigServerBootstrapConfigurationTests {
|
||||
@Test
|
||||
public void offByDefault() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void properBeansCreatedWhenDiscoveryEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true")
|
||||
.run(this::assertEurekaBeansPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true").run(this::assertEurekaBeansPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenDiscoveryNotEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenDiscoveryDisabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.disabled")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.disabled").run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenEurekaClientEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("eureka.client.enabled=true")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("eureka.client.enabled=true").run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenEurekaClientNotEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("eureka.client.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("eureka.client.enabled=false").run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenEurekaClientDisabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("eureka.client.disabled")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("eureka.client.disabled").run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void properBeansCreatedWhenDiscoveryEnabled_EurekaEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true")
|
||||
.run(this::assertEurekaBeansPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true")
|
||||
.run(this::assertEurekaBeansPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenDiscoveryEnabled_EurekaNotEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenDiscoveryNotEnabled_EurekaEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=false", "eureka.client.enabled=true")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=false", "eureka.client.enabled=true")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void beansNotCreatedWhenDiscoveryNotEnabled_EurekaNotEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=false", "eureka.client.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=false", "eureka.client.enabled=false")
|
||||
.run(this::assertEurekaBeansNotPresent);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void eurekaDnsConfigurationWorks() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"eureka.instance.hostname=eurekaclient1", "eureka.client.use-dns-for-fetching-service-urls=true",
|
||||
"eureka.client.eureka-server-d-n-s-name=myeurekahost",
|
||||
"eureka.client.eureka-server-u-r-l-context=eureka", "eureka.client.eureka-server-port=30000")
|
||||
.run(context -> assertThat(output)
|
||||
.contains("Cannot get cnames bound to the region:txt.us-east-1.myeurekahost"));
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"eureka.instance.hostname=eurekaclient1",
|
||||
"eureka.client.use-dns-for-fetching-service-urls=true",
|
||||
"eureka.client.eureka-server-d-n-s-name=myeurekahost",
|
||||
"eureka.client.eureka-server-u-r-l-context=eureka", "eureka.client.eureka-server-port=30000")
|
||||
.run(context -> assertThat(output)
|
||||
.contains("Cannot get cnames bound to the region:txt.us-east-1.myeurekahost"));
|
||||
}
|
||||
|
||||
@Test
|
||||
@@ -165,43 +159,13 @@ public class EurekaConfigServerBootstrapConfigurationTests {
|
||||
// FIXME: why do I need to do this? (fails in maven build without it.
|
||||
TomcatURLStreamHandlerFactory.disable();
|
||||
new SpringApplicationBuilder(TestConfigDiscoveryConfiguration.class)
|
||||
.properties("spring.config.use-legacy-processing=true", "spring.cloud.config.discovery.enabled=true",
|
||||
"eureka.client.enabled=true",
|
||||
"spring.main.sources=" + TestConfigDiscoveryBootstrapConfiguration.class.getName(),
|
||||
"logging.level.org.springframework.cloud.netflix.eureka.config=DEBUG")
|
||||
.run()
|
||||
.close();
|
||||
.properties("spring.config.use-legacy-processing=true", "spring.cloud.config.discovery.enabled=true",
|
||||
"eureka.client.enabled=true",
|
||||
"spring.main.sources=" + TestConfigDiscoveryBootstrapConfiguration.class.getName(),
|
||||
"logging.level.org.springframework.cloud.netflix.eureka.config=DEBUG")
|
||||
.run();
|
||||
assertThat(output).contains("eurekaConfigServerInstanceProvider finding instances for configserver")
|
||||
.contains("eurekaConfigServerInstanceProvider found 1 instance(s) for configserver");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void eurekaConfigServerInstanceProviderCalledWithRemoteRegions() {
|
||||
TomcatURLStreamHandlerFactory.disable();
|
||||
new SpringApplicationBuilder(TestConfigDiscoveryConfiguration.class)
|
||||
.properties("spring.config.use-legacy-processing=true", "spring.cloud.config.discovery.enabled=true",
|
||||
"eureka.client.enabled=true", "eureka.client.fetchRemoteRegionsRegistry=us-east-1,us-east-2",
|
||||
"spring.main.sources=" + TestConfigDiscoveryBootstrapConfiguration.class.getName(),
|
||||
"logging.level.org.springframework.cloud.netflix.eureka.config=DEBUG")
|
||||
.run()
|
||||
.close();
|
||||
assertThat(output).contains("eurekaConfigServerInstanceProvider finding instances for configserver")
|
||||
.contains("eurekaConfigServerInstanceProvider found 1 instance(s) for configserver");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void eurekaConfigServerInstanceProviderCalledWithVipAddress() {
|
||||
TomcatURLStreamHandlerFactory.disable();
|
||||
new SpringApplicationBuilder(TestConfigDiscoveryConfiguration.class)
|
||||
.properties("spring.config.use-legacy-processing=true", "spring.cloud.config.discovery.enabled=true",
|
||||
"eureka.client.enabled=true", "eureka.client.registryRefreshSingleVipAddress=vip1",
|
||||
"eureka.client.fetchRemoteRegionsRegistry=us-east-1,us-east-2",
|
||||
"spring.main.sources=" + TestConfigDiscoveryBootstrapConfiguration.class.getName(),
|
||||
"logging.level.org.springframework.cloud.netflix.eureka.config=DEBUG")
|
||||
.run()
|
||||
.close();
|
||||
assertThat(output).contains("eurekaConfigServerInstanceProvider finding instances for configserver")
|
||||
.contains("eurekaConfigServerInstanceProvider found 1 instance(s) for configserver");
|
||||
.contains("eurekaConfigServerInstanceProvider found 1 instance(s) for configserver");
|
||||
}
|
||||
|
||||
private void assertEurekaBeansPresent(AssertableApplicationContext context) {
|
||||
@@ -244,9 +208,7 @@ public class EurekaConfigServerBootstrapConfigurationTests {
|
||||
when(response.getEntity()).thenReturn(applications);
|
||||
|
||||
EurekaHttpClient client = mock(EurekaHttpClient.class);
|
||||
when(client.getApplications("us-east-1", "us-east-2")).thenReturn(response);
|
||||
when(client.getApplications((String) null)).thenReturn(response);
|
||||
when(client.getVip("vip1", "us-east-1", "us-east-2")).thenReturn(response);
|
||||
when(client.getApplications("us-east-1")).thenReturn(response);
|
||||
return client;
|
||||
}
|
||||
|
||||
|
||||
+9
-16
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -22,16 +22,15 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.SpringBootConfiguration;
|
||||
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.boot.web.server.test.LocalServerPort;
|
||||
import org.springframework.boot.test.web.server.LocalServerPort;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientEurekaHttpClient;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
|
||||
import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer;
|
||||
import org.springframework.security.web.SecurityFilterChain;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
import org.springframework.web.reactive.function.client.ClientResponse;
|
||||
import org.springframework.web.reactive.function.client.WebClient;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
@@ -42,7 +41,7 @@ import static org.springframework.boot.test.context.SpringBootTest.WebEnvironmen
|
||||
*/
|
||||
@SpringBootTest(properties = { "spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"spring.config.use-legacy-processing=true", "eureka.client.webclient.enabled=true",
|
||||
"spring.http.codecs.max-in-memory-size=310000" }, webEnvironment = RANDOM_PORT)
|
||||
"spring.codec.max-in-memory-size=310000" }, webEnvironment = RANDOM_PORT)
|
||||
class EurekaConfigServerBootstrapConfigurationWebClientIntegrationTests {
|
||||
|
||||
@LocalServerPort
|
||||
@@ -54,15 +53,10 @@ class EurekaConfigServerBootstrapConfigurationWebClientIntegrationTests {
|
||||
@Test
|
||||
void webClientRespectsCodecProperties() {
|
||||
WebClient webClient = eurekaHttpClient.getWebClient();
|
||||
ResponseEntity<String> response = webClient.get()
|
||||
.uri("http://localhost:" + port)
|
||||
.retrieve()
|
||||
.toEntity(String.class)
|
||||
.block();
|
||||
|
||||
ClientResponse response = webClient.get().uri("http://localhost:" + port).exchange().block();
|
||||
assertThat(response).isNotNull();
|
||||
assertThat(response.getStatusCode()).isEqualTo(HttpStatus.OK);
|
||||
assertThat(response.getBody()).startsWith("....").hasSize(300000);
|
||||
assertThat(response.statusCode()).isEqualTo(HttpStatus.OK);
|
||||
assertThat(response.bodyToMono(String.class).block()).startsWith("....").hasSize(300000);
|
||||
}
|
||||
|
||||
@SpringBootConfiguration
|
||||
@@ -77,9 +71,8 @@ class EurekaConfigServerBootstrapConfigurationWebClientIntegrationTests {
|
||||
|
||||
@Bean
|
||||
public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {
|
||||
return http.authorizeHttpRequests(auth -> auth.anyRequest().permitAll())
|
||||
.csrf(AbstractHttpConfigurer::disable)
|
||||
.build();
|
||||
http.authorizeHttpRequests().anyRequest().permitAll().and().csrf().disable();
|
||||
return http.build();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+17
-18
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -30,33 +30,32 @@ import static org.assertj.core.api.Assertions.assertThat;
|
||||
/**
|
||||
* @author Spencer Gibb
|
||||
*/
|
||||
@SuppressWarnings("removal")
|
||||
class EurekaConfigServerBootstrapConfigurationWebClientTests {
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenEnabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"eureka.client.webclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(EurekaClientConfigBean.class);
|
||||
assertThat(context).hasSingleBean(WebClientEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(ConfigServerInstanceProvider.Function.class);
|
||||
});
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true",
|
||||
"eureka.client.webclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(EurekaClientConfigBean.class);
|
||||
assertThat(context).hasSingleBean(WebClientEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(ConfigServerInstanceProvider.Function.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
void properBeansCreatedWhenEnabledWebClientDisabled() {
|
||||
new ApplicationContextRunner()
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(EurekaClientConfigBean.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(RestTemplateEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(ConfigServerInstanceProvider.Function.class);
|
||||
});
|
||||
.withConfiguration(AutoConfigurations.of(EurekaConfigServerBootstrapConfiguration.class))
|
||||
.withPropertyValues("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(EurekaClientConfigBean.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(RestTemplateEurekaHttpClient.class);
|
||||
assertThat(context).hasSingleBean(ConfigServerInstanceProvider.Function.class);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
+13
-17
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2023 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -59,10 +59,10 @@ import static org.mockserver.model.HttpResponse.response;
|
||||
* @author Ryan Baxter
|
||||
*/
|
||||
@Testcontainers
|
||||
public class EurekaConfigServerBootstrapperIntegrationTests {
|
||||
public class EurekaConfigServerBootstrapperIT {
|
||||
|
||||
public static final DockerImageName MOCKSERVER_IMAGE = DockerImageName.parse("mockserver/mockserver")
|
||||
.withTag("mockserver-" + MockServerClient.class.getPackage().getImplementationVersion());
|
||||
.withTag("mockserver-" + MockServerClient.class.getPackage().getImplementationVersion());
|
||||
|
||||
@Container
|
||||
static MockServerContainer mockServer = new MockServerContainer(MOCKSERVER_IMAGE);
|
||||
@@ -93,25 +93,21 @@ public class EurekaConfigServerBootstrapperIntegrationTests {
|
||||
try (MockServerClient mockServerClient = new MockServerClient(mockServer.getHost(),
|
||||
mockServer.getMappedPort(MockServerContainer.PORT))) {
|
||||
mockServerClient.when(request().withPath("/application/default"))
|
||||
.respond(response().withBody(objectMapper.writeValueAsString(environment))
|
||||
.withHeader("content-type", "application/json"));
|
||||
.respond(response().withBody(objectMapper.writeValueAsString(environment))
|
||||
.withHeader("content-type", "application/json"));
|
||||
InstanceInfo configServerInstanceInfo = InstanceInfo.Builder.newBuilder()
|
||||
.setVIPAddress("eureka-configserver")
|
||||
.setInstanceId("eureka-configserver")
|
||||
.setAppName("eureka-configserver")
|
||||
.setStatus(InstanceInfo.InstanceStatus.UP)
|
||||
.enablePort(InstanceInfo.PortType.UNSECURE, true)
|
||||
.setHostName("localhost")
|
||||
.setPort(mockServer.getMappedPort(MockServerContainer.PORT))
|
||||
.build();
|
||||
.setVIPAddress("eureka-configserver").setInstanceId("eureka-configserver")
|
||||
.setAppName("eureka-configserver").setStatus(InstanceInfo.InstanceStatus.UP)
|
||||
.enablePort(InstanceInfo.PortType.UNSECURE, true).setHostName("localhost")
|
||||
.setPort(mockServer.getMappedPort(MockServerContainer.PORT)).build();
|
||||
Application configServer = new Application("eureka-configserver",
|
||||
Collections.singletonList(configServerInstanceInfo));
|
||||
EurekaApplications eurekaApplications = new EurekaApplications("hashcode", 0L,
|
||||
Collections.singletonList(configServer));
|
||||
mockServerClient.when(request().withPath("/apps/"))
|
||||
.respond(response()
|
||||
.withBody("{\"applications\":" + objectMapper.writeValueAsString(eurekaApplications) + "}")
|
||||
.withHeader("content-type", "application/json"));
|
||||
.respond(response()
|
||||
.withBody("{\"applications\":" + objectMapper.writeValueAsString(eurekaApplications) + "}")
|
||||
.withHeader("content-type", "application/json"));
|
||||
this.context = setup().run();
|
||||
assertThat(this.context.getEnvironment().getProperty("hello")).isEqualTo("world");
|
||||
}
|
||||
@@ -133,7 +129,7 @@ public class EurekaConfigServerBootstrapperIntegrationTests {
|
||||
|
||||
SpringApplicationBuilder setup(String... env) {
|
||||
SpringApplicationBuilder builder = new SpringApplicationBuilder(TestConfig.class)
|
||||
.properties(addDefaultEnv(env));
|
||||
.properties(addDefaultEnv(env));
|
||||
return builder;
|
||||
}
|
||||
|
||||
+39
-47
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2013-present the original author or authors.
|
||||
* Copyright 2013-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -37,67 +37,59 @@ class EurekaConfigServerBootstrapperTests {
|
||||
@Test
|
||||
void notEnabledReturnsEmptyList() {
|
||||
new SpringApplicationBuilder(TestConfig.class)
|
||||
.properties("spring.cloud.service-registry.auto-registration.enabled=false")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
assertThat(providerFn.apply("id")).as("Should return empty list").isEmpty();
|
||||
}))
|
||||
.run()
|
||||
.close();
|
||||
.properties("spring.cloud.service-registry.auto-registration.enabled=false")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
assertThat(providerFn.apply("id")).as("Should return empty list").isEmpty();
|
||||
})).run().close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void discoveryClientNotEnabledProvidesEmptyList() {
|
||||
new SpringApplicationBuilder(TestConfig.class)
|
||||
.properties("spring.cloud.config.discovery.enabled=true", "spring.cloud.discovery.enabled=false",
|
||||
"spring.cloud.service-registry.auto-registration.enabled=false")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
Binder binder = event.getBootstrapContext().get(Binder.class);
|
||||
BindHandler bindHandler = event.getBootstrapContext().get(BindHandler.class);
|
||||
assertThat(providerFn.apply("id", binder, bindHandler, mock(Log.class))).as("Should return empty list")
|
||||
.isEmpty();
|
||||
}))
|
||||
.run()
|
||||
.close();
|
||||
.properties("spring.cloud.config.discovery.enabled=true", "spring.cloud.discovery.enabled=false",
|
||||
"spring.cloud.service-registry.auto-registration.enabled=false")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
Binder binder = event.getBootstrapContext().get(Binder.class);
|
||||
BindHandler bindHandler = event.getBootstrapContext().get(BindHandler.class);
|
||||
assertThat(providerFn.apply("id", binder, bindHandler, mock(Log.class)))
|
||||
.as("Should return empty list").isEmpty();
|
||||
})).run().close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void eurekaClientNotEnabledProvidesEmptyList() {
|
||||
new SpringApplicationBuilder(TestConfig.class)
|
||||
.properties("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=false",
|
||||
"spring.cloud.service-registry.auto-registration.enabled=false")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
Binder binder = event.getBootstrapContext().get(Binder.class);
|
||||
BindHandler bindHandler = event.getBootstrapContext().get(BindHandler.class);
|
||||
assertThat(providerFn.apply("id", binder, bindHandler, mock(Log.class))).as("Should return empty list")
|
||||
.isEmpty();
|
||||
}))
|
||||
.run()
|
||||
.close();
|
||||
.properties("spring.cloud.config.discovery.enabled=true", "eureka.client.enabled=false",
|
||||
"spring.cloud.service-registry.auto-registration.enabled=false")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
Binder binder = event.getBootstrapContext().get(Binder.class);
|
||||
BindHandler bindHandler = event.getBootstrapContext().get(BindHandler.class);
|
||||
assertThat(providerFn.apply("id", binder, bindHandler, mock(Log.class)))
|
||||
.as("Should return empty list").isEmpty();
|
||||
})).run().close();
|
||||
}
|
||||
|
||||
@Test
|
||||
void enabledAddsInstanceProviderFn() {
|
||||
new SpringApplicationBuilder(TestConfig.class)
|
||||
.properties("spring.config.import: classpath:bootstrapper.yaml",
|
||||
ConfigClientProperties.PREFIX + ".enabled=true")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
Binder binder = event.getBootstrapContext().get(Binder.class);
|
||||
BindHandler bindHandler = event.getBootstrapContext().get(BindHandler.class);
|
||||
assertThatThrownBy(() -> providerFn.apply("id", binder, bindHandler, mock(Log.class)))
|
||||
.isInstanceOf(ResourceAccessException.class)
|
||||
.hasMessageContaining("I/O error on GET request for \"http://localhost:8761/eureka/apps/\"")
|
||||
.as("Should have tried to connect to Eureka to fetch instances.");
|
||||
}))
|
||||
.run()
|
||||
.close();
|
||||
.properties("spring.config.import: classpath:bootstrapper.yaml",
|
||||
ConfigClientProperties.PREFIX + ".enabled=true")
|
||||
.addBootstrapRegistryInitializer(registry -> registry.addCloseListener(event -> {
|
||||
ConfigServerInstanceProvider.Function providerFn = event.getBootstrapContext()
|
||||
.get(ConfigServerInstanceProvider.Function.class);
|
||||
Binder binder = event.getBootstrapContext().get(Binder.class);
|
||||
BindHandler bindHandler = event.getBootstrapContext().get(BindHandler.class);
|
||||
assertThatThrownBy(() -> providerFn.apply("id", binder, bindHandler, mock(Log.class)))
|
||||
.isInstanceOf(ResourceAccessException.class)
|
||||
.hasMessageContaining("I/O error on GET request for \"http://localhost:8761/eureka/apps/\"")
|
||||
.as("Should have tried to connect to Eureka to fetch instances.");
|
||||
})).run().close();
|
||||
}
|
||||
|
||||
@SpringBootConfiguration
|
||||
|
||||
+3
-4
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -37,7 +37,7 @@ import static org.assertj.core.api.AssertionsForInterfaceTypes.assertThat;
|
||||
@RunWith(ModifiedClassPathRunner.class)
|
||||
@ClassPathExclusions({ "jersey-client-*", "jersey-core-*", "jersey-apache-client4-*", "spring-webflux-*" })
|
||||
@SpringBootTest(classes = EurekaSampleApplication.class, webEnvironment = WebEnvironment.RANDOM_PORT)
|
||||
public class EurekaHttpClientsOptionalArgsConfigurationNoWebFluxTests {
|
||||
public class EurekaHttpClientsOptionalArgsConfigurationNoWebfluxTest {
|
||||
|
||||
@Test
|
||||
public void contextFailsWithoutWebClient() {
|
||||
@@ -46,8 +46,7 @@ public class EurekaHttpClientsOptionalArgsConfigurationNoWebFluxTests {
|
||||
try {
|
||||
TomcatURLStreamHandlerFactory.disable();
|
||||
ctx = new SpringApplicationBuilder(EurekaSampleApplication.class)
|
||||
.properties("eureka.client.webclient.enabled=true")
|
||||
.run();
|
||||
.properties("eureka.client.webclient.enabled=true").run();
|
||||
fail("exception not thrown");
|
||||
}
|
||||
catch (Exception e) {
|
||||
+67
@@ -0,0 +1,67 @@
|
||||
/*
|
||||
* Copyright 2017-2022 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
|
||||
import org.springframework.boot.test.context.runner.WebApplicationContextRunner;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.sample.EurekaSampleApplication;
|
||||
import org.springframework.cloud.test.ClassPathExclusions;
|
||||
import org.springframework.cloud.test.ModifiedClassPathRunner;
|
||||
|
||||
import static org.assertj.core.api.AssertionsForInterfaceTypes.assertThat;
|
||||
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
*/
|
||||
@RunWith(ModifiedClassPathRunner.class)
|
||||
@ClassPathExclusions({ "jersey-client-*", "jersey-core-*", "jersey-apache-client4-*" })
|
||||
@SpringBootTest(classes = EurekaSampleApplication.class, webEnvironment = WebEnvironment.RANDOM_PORT)
|
||||
public class EurekaHttpClientsOptionalArgsConfigurationTest {
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithRestTemplate() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.webclient.enabled=false").run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithWebClient() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.webclient.enabled=true").run(context -> {
|
||||
assertThat(context).doesNotHaveBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).hasSingleBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithRestTemplateAsDefault() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class).run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
-99
@@ -1,99 +0,0 @@
|
||||
/*
|
||||
* Copyright 2017-present the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.netflix.eureka.config;
|
||||
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
import org.springframework.boot.test.context.SpringBootTest;
|
||||
import org.springframework.boot.test.context.SpringBootTest.WebEnvironment;
|
||||
import org.springframework.boot.test.context.runner.WebApplicationContextRunner;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestClientDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.RestTemplateDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.http.WebClientDiscoveryClientOptionalArgs;
|
||||
import org.springframework.cloud.netflix.eureka.sample.EurekaSampleApplication;
|
||||
import org.springframework.cloud.test.ClassPathExclusions;
|
||||
import org.springframework.cloud.test.ModifiedClassPathRunner;
|
||||
|
||||
import static org.assertj.core.api.AssertionsForInterfaceTypes.assertThat;
|
||||
|
||||
/**
|
||||
* @author Daniel Lavoie
|
||||
* @author Wonchul Heo
|
||||
*/
|
||||
@RunWith(ModifiedClassPathRunner.class)
|
||||
@ClassPathExclusions({ "jersey-client-*", "jersey-core-*", "jersey-apache-client4-*" })
|
||||
@SpringBootTest(classes = EurekaSampleApplication.class, webEnvironment = WebEnvironment.RANDOM_PORT)
|
||||
public class EurekaHttpClientsOptionalArgsConfigurationTests {
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithRestTemplateWhenWebClientDisabled() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.webclient.enabled=false")
|
||||
.withPropertyValues("eureka.client.restclient.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithRestTemplateWhenRestClientDisabled() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.restclient.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithWebClient() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.webclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).doesNotHaveBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).hasSingleBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithRestClient() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.restclient.enabled=true")
|
||||
.run(context -> {
|
||||
assertThat(context).doesNotHaveBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).hasSingleBean(RestClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
@Test
|
||||
public void contextLoadsWithRestTemplateAsDefault() {
|
||||
new WebApplicationContextRunner().withUserConfiguration(EurekaSampleApplication.class)
|
||||
.withPropertyValues("eureka.client.restclient.enabled=false")
|
||||
.run(context -> {
|
||||
assertThat(context).hasSingleBean(RestTemplateDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(WebClientDiscoveryClientOptionalArgs.class);
|
||||
assertThat(context).doesNotHaveBean(RestClientDiscoveryClientOptionalArgs.class);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user