diff --git a/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnectionProvider.java b/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnectionProvider.java
index b127f0e86..5ab4357cd 100644
--- a/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnectionProvider.java
+++ b/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnectionProvider.java
@@ -6,14 +6,13 @@
import javax.management.remote.JMXConnector;
import javax.management.remote.JMXConnectorProvider;
import javax.management.remote.JMXServiceURL;
-import org.jolokia.client.jmxadapter.JolokiaJmxConnector;
/**
* This provides support for handling JMX urls over the Jolokia protocol to JVMs running in kubernetes pods
* Syntax examples
*
- * - service:jmx:kubernetes:///api/v1/namespaces/mynamespace/pods/mypodname-.+/actuator/jolokia/
- * - service:jmx:kubernetes:///api/v1/namespaces/mynamespace/services/myservice-.+/actuator/jolokia/
+ * - service:jmx:kubernetes:///namespaces/mynamespace/pods/mypodname-abcd-efgh/actuator/jolokia/
+ * - service:jmx:kubernetes:///namespaces/mynamespace/pods/mypodname-.+/actuator/jolokia/
*
*
* Regular expressions in service url is supported so you can have working URLs across deploys.
@@ -27,7 +26,7 @@
* Example:
* //NB: include trailing slash to jolokia endpoint
* JMXConnector connector = JMXConnectorFactory
- * .connect(new JMXServiceURL("service:jmx:kubernetes:///api/v1/namespaces/mynamespace/pods/mypodname-.+/actuator/jolokia/")));
+ * .connect(new JMXServiceURL("service:jmx:kubernetes:///namespaces/mynamespace/pods/mypodname-.+/actuator/jolokia/")));
* connector.connect();
* connector.getMBeanServerConnection();
*
diff --git a/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnector.java b/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnector.java
index 3a6f27688..f6afbe4de 100644
--- a/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnector.java
+++ b/client/kubernetes/src/main/java/org/jolokia/kubernetes/client/KubernetesJmxConnector.java
@@ -7,9 +7,7 @@
import io.kubernetes.client.Configuration;
import io.kubernetes.client.Pair;
import io.kubernetes.client.apis.CoreV1Api;
-import io.kubernetes.client.models.V1OwnerReference;
import io.kubernetes.client.models.V1Pod;
-import io.kubernetes.client.models.V1Service;
import io.kubernetes.client.util.ClientBuilder;
import io.kubernetes.client.util.KubeConfig;
import java.io.FileReader;
@@ -23,16 +21,13 @@
import javax.management.remote.JMXConnector;
import javax.management.remote.JMXServiceURL;
import org.jolokia.client.J4pClient;
-import org.jolokia.client.J4pClientBuilderFactory;
import org.jolokia.client.jmxadapter.JolokiaJmxConnector;
import org.jolokia.client.jmxadapter.RemoteJmxAdapter;
public class KubernetesJmxConnector extends JolokiaJmxConnector {
private static Pattern POD_PATTERN = Pattern
- .compile("/api/v1/namespaces/([^/]+)/pods/([^/]+)/proxy/(.+)");
- private static Pattern SERVICE_PATTERN = Pattern
- .compile("/api/v1/namespaces/([^/]+)/services/([^/]+)/proxy/(.+)");
+ .compile("/namespaces/([^/]+)/pods/([^/]+)/(.+)");
private static ApiClient apiClient;
public KubernetesJmxConnector(JMXServiceURL serviceURL,
@@ -43,7 +38,9 @@ public KubernetesJmxConnector(JMXServiceURL serviceURL,
@Override
public void connect(Map env) throws IOException {
if (!"kubernetes".equals(this.serviceUrl.getProtocol())) {
- throw new MalformedURLException(String.format("Invalid URL %s : Only protocol \"kubernetes\" is supported (not %s)", serviceUrl, serviceUrl.getProtocol()));
+ throw new MalformedURLException(String
+ .format("Invalid URL %s : Only protocol \"kubernetes\" is supported (not %s)", serviceUrl,
+ serviceUrl.getProtocol()));
}
final Map mergedEnvironment = this.mergedEnvironment(env);
ApiClient client = getApiClient(mergedEnvironment);
@@ -57,7 +54,7 @@ protected RemoteJmxAdapter createAdapter(J4pClient client) throws IOException {
}
public static ApiClient getApiClient(Map env) throws IOException {
- if(apiClient != null){
+ if (apiClient != null) {
return apiClient;
}
return buildApiClient(env);
@@ -80,102 +77,45 @@ public static ApiClient buildApiClient(Map env) throws IOException {
protected J4pClient expandAndProbeUrl(ApiClient client,
Map env) throws MalformedURLException {
Configuration.setDefaultApiClient(client);
-
CoreV1Api api = new CoreV1Api();
String proxyPath = this.serviceUrl.getURLPath();
+ J4pClient connection;
final HashMap headersForProbe = createHeadersForProbe(env);
try {
- if (SERVICE_PATTERN.matcher(proxyPath).matches()) {
- final Matcher matcher = SERVICE_PATTERN.matcher(proxyPath);
- if (matcher.find()) {
- String namespacePattern = matcher.group(1);
- String servicePattern = matcher.group();
- String actualNamespace = null;
- String actualName = null;
- for (final V1Service service : api
- .listServiceForAllNamespaces(null, null, false, null, null, null, null, 5, null)
- .getItems()) {
-
- if (service.getMetadata().getNamespace().matches(namespacePattern) && service
- .getMetadata().getName().matches(servicePattern)) {
- actualNamespace = service.getMetadata().getNamespace();
- actualName = service.getMetadata().getName();
- }
- }
- if (actualName == null || actualNamespace == null) {
- throw new MalformedURLException(
- "Coult not find service in cluster for pattern " + proxyPath);
- }
- if (!actualNamespace.equals(namespacePattern)) {
- proxyPath = proxyPath.replace(namespacePattern, actualNamespace);
- }
- if (!actualName.equals(servicePattern)) {
- proxyPath = proxyPath.replace(servicePattern, actualName);
- }
- //probe a request to this URL via proxy
- try {
- final Response response = probeProxyPath(client, proxyPath,
- headersForProbe);
- response.body().close();
- if (response.isSuccessful()) {
- return new J4pClient(
- proxyPath, new MinimalHttpClientAdapter(client, proxyPath, env));
- }
- } catch (IOException ignore) {
- }
- //try to fall back to finding a pod to see if we are more successful connecting to it, will be picked up from next if block if successful
-
- String path = matcher.group(3);
- proxyPath = findPodPathIfAnyForService(actualName, actualNamespace, path, api);
-
-
- }
- }
if (POD_PATTERN.matcher(proxyPath).matches()) {
final Matcher matcher = POD_PATTERN.matcher(proxyPath);
if (matcher.find()) {
- String namespacePattern = matcher.group(1);
-
+ String namespace = matcher.group(1);
String podPattern = matcher.group(2);
- String actualNamespace = null;
- String actualPodName = null;
- for (final V1Pod pod : api
- .listPodForAllNamespaces(null, null, false, null, null, null, null, 5, null)
- .getItems()) {
-
- if (pod.getMetadata().getNamespace().matches(namespacePattern) && pod.getMetadata()
- .getName().matches(podPattern)) {
- actualNamespace = pod.getMetadata().getNamespace();
- actualPodName = pod.getMetadata().getName();
- break;
- }
- }
- if (actualPodName == null || actualNamespace == null) {
- throw new MalformedURLException(
- "Could not find pod in cluster for pattern " + proxyPath);
- }
- if (!actualNamespace.equals(namespacePattern)) {
- proxyPath = proxyPath.replace(namespacePattern, actualNamespace);
- }
- if (!actualPodName.equals(podPattern)) {
- proxyPath = proxyPath.replace(podPattern, actualPodName);
- }
- //probe a request to this URL via proxy
- try {
- final Response response = probeProxyPath(client, proxyPath,
- headersForProbe);
- response.body().close();
- if (response.isSuccessful()) {
- return new J4pClient(
- proxyPath, new MinimalHttpClientAdapter(client, proxyPath, env));
+ String path = matcher.group(3);
+ //check if podname pans out directly
+ if ((connection = probeProxyPath(env, client, namespace, podPattern, path,
+ headersForProbe)) != null) {
+ return connection;
+ } else { //scan through pods in namespace if podname is a pattern
+ for (final V1Pod pod : api
+ .listNamespacedPod(namespace,
+ false,
+ null,
+ null,
+ null,
+ null,
+ null,
+ null,
+ 10,
+ null)
+ .getItems()) {
+ if (pod.getMetadata().getNamespace().matches(namespace) && pod.getMetadata()
+ .getName().matches(podPattern)) {
+ if ((connection = probeProxyPath(env, client, namespace,
+ pod.getMetadata().getName(), path, headersForProbe)) != null) {
+ return connection;
+ }
+ }
}
-
- } catch (IOException ignore) {
}
}
-
}
-
} catch (ApiException ignore) {
}
throw new MalformedURLException("Unable to connect to proxypath " + proxyPath);
@@ -184,46 +124,35 @@ protected J4pClient expandAndProbeUrl(ApiClient client,
private HashMap createHeadersForProbe(
Map env) {
final HashMap headers = new HashMap();
- String[] credentials= (String[]) env.get(JMXConnector.CREDENTIALS);
- if(credentials != null) {
+ String[] credentials = (String[]) env.get(JMXConnector.CREDENTIALS);
+ if (credentials != null) {
headers.put("Authorization", Credentials.basic(credentials[0], credentials[1]));
}
return headers;
}
/**
- * Find a pod of a service, fail if none
+ * Probe whether we find Jolokia in given namespace, pod and path
*/
- private String findPodPathIfAnyForService(String actualName, String actualNamespace, String path,
- CoreV1Api api) throws MalformedURLException {
+ public static J4pClient probeProxyPath(Map env, ApiClient client,
+ String namespace, String podName, String path,
+ HashMap headers)
+ throws ApiException {
+
+ final String proxyPath = String
+ .format("/api/v1/namespaces/%s/pods/%s/proxy/%s", namespace, podName, path);
try {
- for (V1Pod pod : api
- .listNamespacedPod(actualNamespace, false, null, null, null, null, null, null, 5, false)
- .getItems()) {
- for (V1OwnerReference ref : pod.getMetadata().getOwnerReferences()) {
- //pod that references the service
- if (ref.getName().equals(actualName)) {
- return String
- .format("/api/v1/namespaces/%s/pods/%s/proxy/%s", actualNamespace, actualName,
- path);
- }
- }
+ Response response = MinimalHttpClientAdapter
+ .performRequest(client, proxyPath, Collections.singletonMap("type", "version"),
+ Collections.emptyList(), "POST", headers);
+
+ response.body().close();
+ if (response.isSuccessful()) {
+ return new J4pClient(
+ proxyPath, new MinimalHttpClientAdapter(client, proxyPath, env));
}
- } catch (ApiException ignore) {
+ } catch (IOException ignore) {
}
-
- throw new MalformedURLException(String
- .format("Could not find any pod of service %s in namespace %s with path %s", actualName,
- actualNamespace, path));
- }
-
- /**
- */
- public static Response probeProxyPath(ApiClient client, String proxyPath,
- HashMap headers)
- throws IOException, ApiException {
- return MinimalHttpClientAdapter
- .performRequest(client, proxyPath, Collections.singletonMap("type", "version"),
- Collections.emptyList(), "POST", headers);
+ return null;
}
}
diff --git a/client/kubernetes/src/test/java/org/jolokia/kubernetes/client/ManualTestConnection.java b/client/kubernetes/src/test/java/org/jolokia/kubernetes/client/ManualTestConnection.java
index b1c4e671c..3871a735d 100644
--- a/client/kubernetes/src/test/java/org/jolokia/kubernetes/client/ManualTestConnection.java
+++ b/client/kubernetes/src/test/java/org/jolokia/kubernetes/client/ManualTestConnection.java
@@ -11,7 +11,7 @@ public class ManualTestConnection {
@Test(groups = "manual")
public void testConnect() throws IOException {
final JMXServiceURL jmxServiceURL = new JMXServiceURL(
- "service:jmx:kubernetes:///api/v1/namespaces/che/pods/workspace.+tools-.+-.+/proxy/manage/jolokia/"
+ "service:jmx:kubernetes:///namespaces/che/pods/workspace.+tools-.+-.+/manage/jolokia/"
);
jmxServiceURL.getProtocol();