* initial profile and check * initial istio aware profile impl * adding initial docs * fixing parent * using BootstrapConfiguration for istio profile check * Improve log messages * Add Istio integration tests * Remove unused IstioClient * Remove redundant parent * Revert "Remove redundant parent" This reverts commit c41271fa * Fix startup error * Add name to istio module * Move IstioClient out of bootstrap configuration This is needed because the Kubernetes Config is not a bean in the bootstrap context. Furthermore the IstioClient is not used anywhere in the bootstrap context * Polish * Ensure this IstioClient is actually injected * Fix integration test setup * more refinements * aligning property name * adding headers and small refinements
This commit is contained in:
@@ -72,7 +72,7 @@ jobs:
|
||||
# Allow intra-pod communication
|
||||
sudo iptables -P FORWARD ACCEPT
|
||||
|
||||
/snap/bin/microk8s.enable dns registry
|
||||
echo n |/snap/bin/microk8s.enable dns registry istio
|
||||
|
||||
# wait until the registry is up and running
|
||||
sleep 10
|
||||
@@ -85,6 +85,21 @@ jobs:
|
||||
done
|
||||
|
||||
echo "Kubernetes Container Registry enabled"
|
||||
|
||||
# wait until istio is up and running
|
||||
sleep 10
|
||||
n=0
|
||||
until [ $n -ge 10 ]
|
||||
do
|
||||
(/snap/bin/microk8s.kubectl get pod -l istio=sidecar-injector --namespace=istio-system | grep -z "Running") && break
|
||||
n=$[$n+1]
|
||||
sleep 10
|
||||
done
|
||||
|
||||
echo "Istio enabled"
|
||||
|
||||
# create the namespace where the istio integration test will run
|
||||
/snap/bin/microk8s.kubectl create -f .circleci/istio-test-namespace.yml
|
||||
- run:
|
||||
name: Run integration tests
|
||||
command: |
|
||||
|
||||
6
.circleci/istio-test-namespace.yml
Normal file
6
.circleci/istio-test-namespace.yml
Normal file
@@ -0,0 +1,6 @@
|
||||
apiVersion: v1
|
||||
kind: Namespace
|
||||
metadata:
|
||||
name: istio-test
|
||||
labels:
|
||||
istio-injection: enabled
|
||||
@@ -1,11 +1,11 @@
|
||||
== Kubernetes Awareness
|
||||
== Kubernetes Ecosystem Awareness
|
||||
|
||||
All of the features described above will work equally well regardless of whether your application is running inside
|
||||
Kubernetes or not. This is really helpful for development and troubleshooting.
|
||||
From a development point of view, this is really helpful as you can start your Spring Boot application and debug one
|
||||
of the modules part of this project. It is not required to deploy it in Kubernetes
|
||||
as the code of the project relies on the
|
||||
[Fabric8 Kubernetes Java client](https://github.com/fabric8io/kubernetes-client) which is a fluent DSL able to
|
||||
https://github.com/fabric8io/kubernetes-client[Fabric8 Kubernetes Java client] which is a fluent DSL able to
|
||||
communicate using `http` protocol to the REST API of Kubernetes Server.
|
||||
|
||||
=== Kubernetes Profile Autoconfiguration
|
||||
@@ -13,3 +13,12 @@ communicate using `http` protocol to the REST API of Kubernetes Server.
|
||||
When the application runs as a pod inside Kubernetes a Spring profile named `kubernetes` will automatically get activated.
|
||||
This allows the developer to customize the configuration, to define beans that will be applied when the Spring Boot application is deployed
|
||||
within the Kubernetes platform *(e.g. different dev and prod configuration)*.
|
||||
|
||||
=== Istio Awareness
|
||||
|
||||
When including the **spring-cloud-kubernetes-istio** module into the application classpath a new profile will be added to the application,
|
||||
if the application is running inside a Kubernetes Cluster with http://istio.io[Istio] installed. Then you can use
|
||||
spring **@Profile("istio")** annotations into your Beans and **@Configuration**'s.
|
||||
|
||||
The Istio awareness module uses the **me.snowdrop:istio-client** to interact with Istio APIs enabling us to discover traffic rules, circuit breakers, etc.
|
||||
Making it easy for our Spring Boot applications to consume this data to dynamically configure themselves according the environment.
|
||||
|
||||
3
pom.xml
3
pom.xml
@@ -88,13 +88,14 @@
|
||||
<module>spring-cloud-starter-kubernetes-all</module>
|
||||
<module>spring-cloud-kubernetes-examples</module>
|
||||
<module>spring-cloud-kubernetes-leader</module>
|
||||
<module>spring-cloud-kubernetes-istio</module>
|
||||
<module>spring-cloud-kubernetes-integration-tests</module>
|
||||
<module>docs</module>
|
||||
</modules>
|
||||
|
||||
<dependencyManagement>
|
||||
<dependencies>
|
||||
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-kubernetes-dependencies</artifactId>
|
||||
|
||||
@@ -34,6 +34,7 @@
|
||||
<arquillian.version>1.4.0.Final</arquillian.version>
|
||||
<arquillian-cube.version>1.15.2</arquillian-cube.version>
|
||||
<kubernetes-client.version>4.1.0</kubernetes-client.version>
|
||||
<istio-client.version>1.0.0</istio-client.version>
|
||||
<mockwebserver.version>0.1.0</mockwebserver.version>
|
||||
</properties>
|
||||
<dependencyManagement>
|
||||
@@ -46,6 +47,12 @@
|
||||
<scope>import</scope>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>me.snowdrop</groupId>
|
||||
<artifactId>istio-client</artifactId>
|
||||
<version>${istio-client.version}</version>
|
||||
</dependency>
|
||||
|
||||
<!-- Own dependencies -->
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
@@ -65,6 +72,11 @@
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-kubernetes-istio</artifactId>
|
||||
<version>${project.version}</version>
|
||||
</dependency>
|
||||
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
|
||||
@@ -27,7 +27,7 @@ tests against that microk8s cluster
|
||||
```bash
|
||||
sudo snap install microk8s --classic --channel=1.11/stable
|
||||
sleep 10
|
||||
microk8s.enable dns registry
|
||||
echo n | microk8s.enable dns registry istio
|
||||
```
|
||||
|
||||
Ensure everything is running by inspecting the output of:
|
||||
@@ -66,6 +66,13 @@ Export the kube config file that will be used to access this cluster
|
||||
microk8s.kubectl config view --raw > /tmp/kubeconfig
|
||||
```
|
||||
|
||||
For the istio tests to work, we need a namespace that is properly configured for Istio injection.
|
||||
Such a namespace called `istio-test` can easily be created using:
|
||||
|
||||
```bash
|
||||
microk8s.kubectl create -f .circleci/istio-test-namespace.yml
|
||||
```
|
||||
|
||||
|
||||
## Launch tests
|
||||
|
||||
|
||||
64
spring-cloud-kubernetes-integration-tests/istio/pom.xml
Normal file
64
spring-cloud-kubernetes-integration-tests/istio/pom.xml
Normal file
@@ -0,0 +1,64 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<parent>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-kubernetes-integration-tests</artifactId>
|
||||
<version>1.0.0.BUILD-SNAPSHOT</version>
|
||||
</parent>
|
||||
|
||||
<name>Spring Cloud Kubernetes :: Integration Tests :: Istio</name>
|
||||
<artifactId>istio</artifactId>
|
||||
<packaging>jar</packaging>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-web</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-actuator</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-actuator-autoconfigure</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-kubernetes-istio</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-test</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.arquillian.cube</groupId>
|
||||
<artifactId>arquillian-cube-kubernetes</artifactId>
|
||||
<version>${arquillian-cube.version}</version>
|
||||
<scope>test</scope>
|
||||
<exclusions>
|
||||
<exclusion>
|
||||
<artifactId>undertow-core</artifactId>
|
||||
<groupId>io.undertow</groupId>
|
||||
</exclusion>
|
||||
</exclusions>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.jboss.arquillian.junit</groupId>
|
||||
<artifactId>arquillian-junit-standalone</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>io.rest-assured</groupId>
|
||||
<artifactId>rest-assured</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
</dependencies>
|
||||
|
||||
|
||||
</project>
|
||||
@@ -0,0 +1,10 @@
|
||||
# We need this fragment in order for the kubernetes client to talk to
|
||||
# the Kubernetes API without caring about proper certificates
|
||||
spec:
|
||||
template:
|
||||
spec:
|
||||
containers:
|
||||
- env:
|
||||
- name: KUBERNETES_TRUST_CERTIFICATES
|
||||
value: true
|
||||
|
||||
@@ -0,0 +1,15 @@
|
||||
# we are using an FMP fragment to ensure that NodePort is used correctly
|
||||
kind: Service
|
||||
apiVersion: v1
|
||||
metadata:
|
||||
name: ${project.artifactId}
|
||||
labels:
|
||||
app: ${project.artifactId}
|
||||
spec:
|
||||
selector:
|
||||
app: ${project.artifactId}
|
||||
ports:
|
||||
- protocol: TCP
|
||||
port: 8080
|
||||
nodePort: ${nodeport.value}
|
||||
type: NodePort
|
||||
@@ -0,0 +1,34 @@
|
||||
package org.springframework.cloud.kubernetes.it;
|
||||
|
||||
import me.snowdrop.istio.client.IstioClient;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
@SpringBootApplication
|
||||
@RestController
|
||||
public class IstioApplication {
|
||||
|
||||
@Autowired
|
||||
private Environment environment;
|
||||
|
||||
// used just to ensure that the IstioClient is properly injected into the context
|
||||
@Autowired
|
||||
private IstioClient istioClient;
|
||||
|
||||
@GetMapping("/profiles")
|
||||
public List<String> profiles() {
|
||||
return Arrays.asList(environment.getActiveProfiles());
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
SpringApplication.run(IstioApplication.class, args);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
spring:
|
||||
cloud:
|
||||
istio:
|
||||
client:
|
||||
envoyPort: 15000
|
||||
@@ -0,0 +1,28 @@
|
||||
package org.springframework.cloud.kubernetes.it;
|
||||
|
||||
import static io.restassured.RestAssured.given;
|
||||
|
||||
import org.arquillian.cube.kubernetes.impl.requirement.RequiresKubernetes;
|
||||
import org.hamcrest.core.StringContains;
|
||||
import org.jboss.arquillian.junit.Arquillian;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
|
||||
@RequiresKubernetes
|
||||
@RunWith(Arquillian.class)
|
||||
public class ProfilesIT {
|
||||
|
||||
private static final String HOST = System.getProperty("service.host");
|
||||
private static final Integer PORT = Integer.valueOf(System.getProperty("service.port"));
|
||||
|
||||
@Test
|
||||
public void testProfileEndpoint() {
|
||||
given()
|
||||
.baseUri(String.format("http://%s:%d", HOST, PORT))
|
||||
.get("profiles")
|
||||
.then()
|
||||
.statusCode(200)
|
||||
.body(new StringContains("istio"));
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
<arquillian xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xmlns="http://jboss.org/schema/arquillian"
|
||||
xsi:schemaLocation="http://jboss.org/schema/arquillian http://jboss.org/schema/arquillian/arquillian_1_0.xsd">
|
||||
|
||||
<extension qualifier="kubernetes">
|
||||
<property name="namespace.use.existing">istio-test</property>
|
||||
</extension>
|
||||
|
||||
</arquillian>
|
||||
@@ -128,6 +128,7 @@
|
||||
<modules>
|
||||
<module>simple-core</module>
|
||||
<module>simple-configmap</module>
|
||||
<module>istio</module>
|
||||
<module>discovery</module>
|
||||
</modules>
|
||||
|
||||
|
||||
41
spring-cloud-kubernetes-istio/pom.xml
Normal file
41
spring-cloud-kubernetes-istio/pom.xml
Normal file
@@ -0,0 +1,41 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project xmlns="http://maven.apache.org/POM/4.0.0"
|
||||
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||
<parent>
|
||||
<artifactId>spring-cloud-kubernetes</artifactId>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<version>1.0.0.BUILD-SNAPSHOT</version>
|
||||
</parent>
|
||||
<modelVersion>4.0.0</modelVersion>
|
||||
|
||||
<artifactId>spring-cloud-kubernetes-istio</artifactId>
|
||||
<name>Spring Cloud Kubernetes :: Istio</name>
|
||||
|
||||
<dependencies>
|
||||
<dependency>
|
||||
<groupId>org.springframework.cloud</groupId>
|
||||
<artifactId>spring-cloud-kubernetes-core</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework</groupId>
|
||||
<artifactId>spring-web</artifactId>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>me.snowdrop</groupId>
|
||||
<artifactId>istio-client</artifactId>
|
||||
</dependency>
|
||||
<!-- Testing Dependencies -->
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-test</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-web</artifactId>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
</project>
|
||||
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Copyright 2013-2018 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
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
*/
|
||||
package org.springframework.cloud.kubernetes.istio;
|
||||
|
||||
import io.fabric8.kubernetes.client.Config;
|
||||
import me.snowdrop.istio.client.DefaultIstioClient;
|
||||
import me.snowdrop.istio.client.IstioClient;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
@Configuration
|
||||
@ConditionalOnProperty(value = "spring.cloud.istio.enabled", matchIfMissing = true)
|
||||
public class IstioAutoConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
public IstioClient istioClient(Config config) {
|
||||
return new DefaultIstioClient(config);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
* Copyright 2013-2018 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
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
*/
|
||||
package org.springframework.cloud.kubernetes.istio;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
|
||||
import org.springframework.boot.context.properties.EnableConfigurationProperties;
|
||||
import org.springframework.cloud.kubernetes.istio.utils.MeshUtils;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.core.env.ConfigurableEnvironment;
|
||||
import org.springframework.core.env.Environment;
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.util.Arrays;
|
||||
|
||||
@Configuration
|
||||
@ConditionalOnProperty(value = "spring.cloud.istio.enabled", matchIfMissing = true)
|
||||
@EnableConfigurationProperties(IstioClientProperties.class)
|
||||
public class IstioBootstrapConfiguration {
|
||||
|
||||
private static final Log LOG = LogFactory.getLog(IstioBootstrapConfiguration.class);
|
||||
|
||||
private static final String ISTIO_PROFILE = "istio";
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean
|
||||
public MeshUtils istioMeshUtils(IstioClientProperties istioClientProperties) {
|
||||
return new MeshUtils(istioClientProperties);
|
||||
}
|
||||
|
||||
@EnableConfigurationProperties(IstioClientProperties.class)
|
||||
protected static class IstioDetectionConfiguration {
|
||||
|
||||
private final MeshUtils utils;
|
||||
|
||||
|
||||
private final ConfigurableEnvironment environment;
|
||||
|
||||
public IstioDetectionConfiguration(MeshUtils utils, ConfigurableEnvironment environment) {
|
||||
this.utils = utils;
|
||||
this.environment = environment;
|
||||
}
|
||||
|
||||
@PostConstruct
|
||||
public void detectIstio() {
|
||||
addIstioProfile(environment);
|
||||
}
|
||||
|
||||
void addIstioProfile(ConfigurableEnvironment environment) {
|
||||
if (utils.isIstioEnabled()) {
|
||||
if (hasIstioProfile(environment)) {
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug("'istio' already in list of active profiles");
|
||||
}
|
||||
} else {
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug("Adding 'istio' to list of active profiles");
|
||||
}
|
||||
environment.addActiveProfile(ISTIO_PROFILE);
|
||||
}
|
||||
} else {
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug("Not running inside kubernetes with istio enabled. Skipping 'istio' profile activation.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private boolean hasIstioProfile(Environment environment) {
|
||||
return Arrays.stream(environment.getActiveProfiles()).anyMatch(ISTIO_PROFILE::equalsIgnoreCase);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Copyright 2013-2018 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
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.kubernetes.istio;
|
||||
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
@Configuration
|
||||
@ConfigurationProperties("spring.cloud.istio.client")
|
||||
public class IstioClientProperties {
|
||||
|
||||
private Integer envoyPort = 15090;
|
||||
private String testPath = "stats/prometheus";
|
||||
|
||||
public Integer getEnvoyPort() {
|
||||
return envoyPort;
|
||||
}
|
||||
|
||||
public void setEnvoyPort(Integer envoyPort) {
|
||||
this.envoyPort = envoyPort;
|
||||
}
|
||||
|
||||
public String getTestPath() {
|
||||
return testPath;
|
||||
}
|
||||
|
||||
public void setTestPath(String testPath) {
|
||||
this.testPath = testPath;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,66 @@
|
||||
/*
|
||||
* Copyright 2013-2018 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
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*
|
||||
*/
|
||||
|
||||
package org.springframework.cloud.kubernetes.istio.utils;
|
||||
|
||||
import org.apache.commons.logging.Log;
|
||||
import org.apache.commons.logging.LogFactory;
|
||||
import org.springframework.boot.web.client.RestTemplateBuilder;
|
||||
import org.springframework.cloud.kubernetes.istio.IstioClientProperties;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
public class MeshUtils {
|
||||
|
||||
|
||||
private static final Log LOG = LogFactory.getLog(MeshUtils.class);
|
||||
|
||||
private final IstioClientProperties istioClientProperties;
|
||||
|
||||
private RestTemplate restTemplate = new RestTemplateBuilder().build();
|
||||
|
||||
public MeshUtils(IstioClientProperties istioClientProperties) {
|
||||
this.istioClientProperties = istioClientProperties;
|
||||
}
|
||||
|
||||
public Boolean isIstioEnabled() {
|
||||
return checkIstioServices();
|
||||
}
|
||||
|
||||
private synchronized boolean checkIstioServices() {
|
||||
try {
|
||||
//Check if Istio Envoy proxy is installed. Notice that the check is done to localhost.
|
||||
// TODO: We can improve this initial detection if better methods are found.
|
||||
String resource = "http://localhost:" + istioClientProperties.getEnvoyPort();
|
||||
ResponseEntity<String> response = restTemplate.getForEntity(resource + "/" + istioClientProperties.getTestPath(), String.class);
|
||||
if (response.getStatusCode().is2xxSuccessful()) {
|
||||
LOG.info("Istio Resources Found.");
|
||||
return true;
|
||||
}
|
||||
LOG.warn("Although Envoy proxy did respond at port" + istioClientProperties.getEnvoyPort() +
|
||||
", it did not respond with HTTP 200 to path: " + istioClientProperties.getTestPath() +
|
||||
". You may need to tweak the test path in order to get proper Istio support");
|
||||
return false;
|
||||
} catch (Throwable t) {
|
||||
if (LOG.isDebugEnabled()) {
|
||||
LOG.debug("Envoy proxy could not be located at port: " + istioClientProperties.getEnvoyPort() +
|
||||
". Assuming that the application is not running inside the Istio Service Mesh");
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
|
||||
org.springframework.cloud.kubernetes.istio.IstioAutoConfiguration
|
||||
|
||||
org.springframework.cloud.bootstrap.BootstrapConfiguration=\
|
||||
org.springframework.cloud.kubernetes.istio.IstioBootstrapConfiguration
|
||||
Reference in New Issue
Block a user