This is an automated email from the ASF dual-hosted git repository.

davsclaus pushed a commit to branch ra
in repository https://gitbox.apache.org/repos/asf/camel.git

commit b24ab58dd7b108b2e6b944e4ae085330d8e86a53
Author: Claus Ibsen <claus.ib...@gmail.com>
AuthorDate: Mon May 27 12:12:43 2024 +0200

    CAMEL-20798: Add RemoteAddress to endpoints so they can tell the 
url/hostname etc for the system it connects. This is needed for better 
monitoring, tracing and management. Add this information into camel-tracer as 
tags.
---
 .../camel/component/activemq/ActiveMQEndpoint.java |   5 +
 .../platform/http/PlatformHttpEndpoint.java        |   5 +
 ...onAddress.java => EndpointServiceLocation.java} |  22 ++--
 .../org/apache/camel/dev-console/protocol.json     |  15 +++
 .../services/org/apache/camel/dev-console/protocol |   2 +
 .../org/apache/camel/dev-consoles.properties       |   2 +-
 .../camel/impl/console/ConsumerDevConsole.java     |   3 -
 .../camel/impl/console/EndpointDevConsole.java     |  10 --
 .../camel/impl/console/ProtocolDevConsole.java     | 133 +++++++++++++++++++++
 .../api/management/mbean/ManagedEndpointMBean.java |   9 +-
 .../camel/management/mbean/ManagedEndpoint.java    |  22 ++--
 .../jbang/core/commands/process/ListAddress.java   |   1 +
 .../jbang/core/commands/process/ListService.java   |   2 +
 13 files changed, 200 insertions(+), 31 deletions(-)

diff --git 
a/components/camel-activemq/src/main/java/org/apache/camel/component/activemq/ActiveMQEndpoint.java
 
b/components/camel-activemq/src/main/java/org/apache/camel/component/activemq/ActiveMQEndpoint.java
index 0f2de7b346e..12902718dc1 100644
--- 
a/components/camel-activemq/src/main/java/org/apache/camel/component/activemq/ActiveMQEndpoint.java
+++ 
b/components/camel-activemq/src/main/java/org/apache/camel/component/activemq/ActiveMQEndpoint.java
@@ -72,6 +72,11 @@ public class ActiveMQEndpoint extends JmsEndpoint implements 
EndpointLocationAdd
         return url;
     }
 
+    @Override
+    public String getServiceProtocol() {
+        return "jms";
+    }
+
     @Override
     public Map<String, String> getAddressMetadata() {
         String un = null;
diff --git 
a/components/camel-platform-http/src/main/java/org/apache/camel/component/platform/http/PlatformHttpEndpoint.java
 
b/components/camel-platform-http/src/main/java/org/apache/camel/component/platform/http/PlatformHttpEndpoint.java
index 7ff1eed4f92..e5bc1be80e5 100644
--- 
a/components/camel-platform-http/src/main/java/org/apache/camel/component/platform/http/PlatformHttpEndpoint.java
+++ 
b/components/camel-platform-http/src/main/java/org/apache/camel/component/platform/http/PlatformHttpEndpoint.java
@@ -107,6 +107,11 @@ public class PlatformHttpEndpoint extends DefaultEndpoint
         return server;
     }
 
+    @Override
+    public String getServiceProtocol() {
+        return "http";
+    }
+
     @Override
     public Producer createProducer() throws Exception {
         throw new UnsupportedOperationException("Producer is not supported");
diff --git 
a/core/camel-api/src/main/java/org/apache/camel/spi/EndpointLocationAddress.java
 
b/core/camel-api/src/main/java/org/apache/camel/spi/EndpointServiceLocation.java
similarity index 67%
rename from 
core/camel-api/src/main/java/org/apache/camel/spi/EndpointLocationAddress.java
rename to 
core/camel-api/src/main/java/org/apache/camel/spi/EndpointServiceLocation.java
index e2eafe39113..86a3a119398 100644
--- 
a/core/camel-api/src/main/java/org/apache/camel/spi/EndpointLocationAddress.java
+++ 
b/core/camel-api/src/main/java/org/apache/camel/spi/EndpointServiceLocation.java
@@ -19,29 +19,37 @@ package org.apache.camel.spi;
 import java.util.Map;
 
 /**
- * Used for getting information about (hosted or external) service addresses 
used for connecting to a remote system such
- * as message brokers, databases, or cloud services.
+ * Used for getting information about location to (hosted or external) network 
services.
+ *
+ * An external service such as message brokers, databases, or cloud services.
  *
  * Hosted services are running inside this Camel application such as with 
embedded HTTP server for Rest DSL, or TCP
  * networking with netty etc.
+ *
+ * @see org.apache.camel.Endpoint
  */
-public interface EndpointLocationAddress {
+public interface EndpointServiceLocation {
 
     /**
-     * Gets the remote address such as URL or hostname
+     * Gets the remote address such as URL, hostname, or connection-string 
that are component specific
      *
      * @return the address or null if no address can be determined.
      */
-    String getAddress();
+    String getServiceUrl();
+
+    /**
+     * Get the protocol the service is using such as http, amqp, tcp.
+     */
+    String getServiceProtocol();
 
     /**
-     * Optional additional metadata that is relevant to the address as key 
value pairs. Notice that the metadata is not
+     * Optional metadata that is relevant to the service as key value pairs. 
Notice that the metadata is not
      * supposed to contain sensitive security details such as access token, 
api keys, or passwords. Only share
      * information that can be safely accessed and written to logs.
      *
      * @return optional metadata or null if no data
      */
-    default Map<String, String> getAddressMetadata() {
+    default Map<String, String> getServiceMetadata() {
         return null;
     }
 }
diff --git 
a/core/camel-console/src/generated/resources/META-INF/org/apache/camel/dev-console/protocol.json
 
b/core/camel-console/src/generated/resources/META-INF/org/apache/camel/dev-console/protocol.json
new file mode 100644
index 00000000000..e7a34a208cc
--- /dev/null
+++ 
b/core/camel-console/src/generated/resources/META-INF/org/apache/camel/dev-console/protocol.json
@@ -0,0 +1,15 @@
+{
+  "console": {
+    "kind": "console",
+    "group": "camel",
+    "name": "protocol",
+    "title": "Protocols",
+    "description": "Protocols used for network communication with clients",
+    "deprecated": false,
+    "javaType": "org.apache.camel.impl.console.ProtocolDevConsole",
+    "groupId": "org.apache.camel",
+    "artifactId": "camel-console",
+    "version": "4.7.0-SNAPSHOT"
+  }
+}
+
diff --git 
a/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-console/protocol
 
b/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-console/protocol
new file mode 100644
index 00000000000..0ba65348685
--- /dev/null
+++ 
b/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-console/protocol
@@ -0,0 +1,2 @@
+# Generated by camel build tools - do NOT edit this file!
+class=org.apache.camel.impl.console.ProtocolDevConsole
diff --git 
a/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-consoles.properties
 
b/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-consoles.properties
index c65dacbcf02..923478dde7d 100644
--- 
a/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-consoles.properties
+++ 
b/core/camel-console/src/generated/resources/META-INF/services/org/apache/camel/dev-consoles.properties
@@ -1,5 +1,5 @@
 # Generated by camel build tools - do NOT edit this file!
-dev-consoles=bean blocked circuit-breaker consumer context debug endpoint 
event gc health inflight java-security jvm log memory properties reload route 
route-controller route-dump source startup-recorder thread top trace 
transformers type-converters variables
+dev-consoles=bean blocked circuit-breaker consumer context debug endpoint 
event gc health inflight java-security jvm log memory properties protocol 
reload route route-controller route-dump source startup-recorder thread top 
trace transformers type-converters variables
 groupId=org.apache.camel
 artifactId=camel-console
 version=4.7.0-SNAPSHOT
diff --git 
a/core/camel-console/src/main/java/org/apache/camel/impl/console/ConsumerDevConsole.java
 
b/core/camel-console/src/main/java/org/apache/camel/impl/console/ConsumerDevConsole.java
index 91004eaf753..858edf525a8 100644
--- 
a/core/camel-console/src/main/java/org/apache/camel/impl/console/ConsumerDevConsole.java
+++ 
b/core/camel-console/src/main/java/org/apache/camel/impl/console/ConsumerDevConsole.java
@@ -63,7 +63,6 @@ public class ConsumerDevConsole extends AbstractDevConsole {
                     sb.append(String.format("\n    Uri: %s", 
mc.getEndpointUri()));
                     sb.append(String.format("\n    State: %s", mc.getState()));
                     sb.append(String.format("\n    Class: %s", 
mc.getServiceType()));
-                    sb.append(String.format("\n    Hosted Service: %b", 
mc.isHostedService()));
                     sb.append(String.format("\n    Inflight: %d", inflight));
                     if (mcc instanceof ManagedSchedulePollConsumerMBean mpc) {
                         sb.append(String.format("\n    Polling: %s", 
mpc.isPolling()));
@@ -151,7 +150,6 @@ public class ConsumerDevConsole extends AbstractDevConsole {
                     jo.put("uri", mc.getEndpointUri());
                     jo.put("state", mc.getState());
                     jo.put("class", mc.getServiceType());
-                    jo.put("hostedService", mc.isHostedService());
                     jo.put("inflight", inflight);
                     jo.put("scheduled", false);
                     if (mcc instanceof ManagedSchedulePollConsumerMBean mpc) {
@@ -212,7 +210,6 @@ public class ConsumerDevConsole extends AbstractDevConsole {
                             // ignore
                         }
                     }
-
                     final JsonObject stats = toJsonObject(mr);
                     jo.put("statistics", stats);
 
diff --git 
a/core/camel-console/src/main/java/org/apache/camel/impl/console/EndpointDevConsole.java
 
b/core/camel-console/src/main/java/org/apache/camel/impl/console/EndpointDevConsole.java
index 67cf79047b6..24779c5d724 100644
--- 
a/core/camel-console/src/main/java/org/apache/camel/impl/console/EndpointDevConsole.java
+++ 
b/core/camel-console/src/main/java/org/apache/camel/impl/console/EndpointDevConsole.java
@@ -24,7 +24,6 @@ import java.util.Optional;
 
 import org.apache.camel.Endpoint;
 import org.apache.camel.spi.EndpointRegistry;
-import org.apache.camel.spi.EndpointLocationAddress;
 import org.apache.camel.spi.RuntimeEndpointRegistry;
 import org.apache.camel.spi.annotations.DevConsole;
 import org.apache.camel.support.console.AbstractDevConsole;
@@ -106,15 +105,6 @@ public class EndpointDevConsole extends AbstractDevConsole 
{
                 jo.put("hits", st.getHits());
                 jo.put("routeId", st.getRouteId());
             }
-            if (e instanceof EndpointLocationAddress raa) {
-                JsonObject ro = new JsonObject();
-                ro.put("address", raa.getAddress());
-                var d = raa.getAddressMetadata();
-                if (d != null) {
-                    ro.putAll(d);
-                }
-                jo.put("location", ro);
-            }
             list.add(jo);
         }
 
diff --git 
a/core/camel-console/src/main/java/org/apache/camel/impl/console/ProtocolDevConsole.java
 
b/core/camel-console/src/main/java/org/apache/camel/impl/console/ProtocolDevConsole.java
new file mode 100644
index 00000000000..cd8abb50039
--- /dev/null
+++ 
b/core/camel-console/src/main/java/org/apache/camel/impl/console/ProtocolDevConsole.java
@@ -0,0 +1,133 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You 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.apache.camel.impl.console;
+
+import org.apache.camel.Consumer;
+import org.apache.camel.Endpoint;
+import org.apache.camel.Route;
+import org.apache.camel.spi.EndpointServiceLocation;
+import org.apache.camel.spi.EndpointRegistry;
+import org.apache.camel.spi.RuntimeEndpointRegistry;
+import org.apache.camel.spi.annotations.DevConsole;
+import org.apache.camel.support.DefaultConsumer;
+import org.apache.camel.support.console.AbstractDevConsole;
+
+import java.util.List;
+import java.util.Map;
+import java.util.Optional;
+
+@DevConsole(name = "protocol", displayName = "Protocols", description = 
"Protocols used for network communication with clients")
+public class ProtocolDevConsole extends AbstractDevConsole {
+
+    public ProtocolDevConsole() {
+        super("camel", "protocol", "Protocols", "Protocols used for network 
communication with clients");
+    }
+
+    @Override
+    protected String doCallText(Map<String, Object> options) {
+        StringBuilder sb = new StringBuilder();
+
+        // runtime registry is optional but if enabled we have additional 
statistics to use in output
+        List<RuntimeEndpointRegistry.Statistic> stats = null;
+        RuntimeEndpointRegistry runtimeReg = 
getCamelContext().getRuntimeEndpointRegistry();
+        if (runtimeReg != null) {
+            stats = runtimeReg.getEndpointStatistics();
+        }
+        EndpointRegistry reg = getCamelContext().getEndpointRegistry();
+
+        // find all consumers (IN) direction
+        for (Route route : getCamelContext().getRoutes()) {
+            Consumer consumer = route.getConsumer();
+            Endpoint endpoint = consumer.getEndpoint();
+            if (endpoint instanceof EndpointServiceLocation raa) {
+                String component = endpoint.getComponent().getDefaultName();
+                boolean hosted = false;
+                if (consumer instanceof DefaultConsumer dc) {
+                    hosted = dc.isHostedService();
+                }
+                String adr = raa.getServiceUrl();
+                String protocol = raa.getServiceProtocol();
+                if (adr != null) {
+                    var stat = findStats(stats, endpoint.getEndpointUri(), 
"in");
+                    var uri = endpoint.toString();
+                    printLine(sb, component, stat, "in", hosted, protocol, 
adr, uri);
+                }
+            }
+        }
+
+        // find all endpoint (OUT) direction
+        for (Endpoint endpoint : reg.getReadOnlyValues()) {
+            if (endpoint instanceof EndpointServiceLocation raa) {
+                String component = endpoint.getComponent().getDefaultName();
+                boolean hosted = false;
+                String adr = raa.getServiceUrl();
+                String protocol = raa.getServiceProtocol();
+                if (adr != null) {
+                    var stat = findStats(stats, endpoint.getEndpointUri(), 
"in");
+                    // skip IN as already found via consumer (platform-http is 
only IN)
+                    boolean skip = "platform-http".equals(component) || 
stat.isPresent() && "in".equals(stat.get().getDirection());
+                    if (!skip) {
+                        var uri = endpoint.toString();
+                        printLine(sb, component, stat, "in", hosted, protocol, 
adr, uri);
+                    }
+                }
+            }
+        }
+
+        sb.append("\n");
+
+        return sb.toString();
+    }
+
+    private static void printLine(StringBuilder sb, String component, 
Optional<RuntimeEndpointRegistry.Statistic> stat,
+                                  String dir, boolean hosted, String protocol, 
String adr, String uri) {
+
+        long total = 0;
+        if (stat.isPresent()) {
+            dir = stat.get().getDirection();
+            total = stat.get().getHits();
+        }
+
+        if (!sb.isEmpty()) {
+            sb.append("\n");
+        }
+        sb.append(String.format("\n    Component: %s", component));
+        sb.append(String.format("\n    Direction: %s", dir));
+        sb.append(String.format("\n    Hosted Service: %b", hosted));
+        sb.append(String.format("\n    Usage: %d", total));
+        sb.append(String.format("\n    Protocol: %s", protocol));
+        sb.append(String.format("\n    Service: %s", adr));
+        sb.append(String.format("\n    Endpoint Uri: %s", uri));
+    }
+
+    @Override
+    protected Map<String, Object> doCallJson(Map<String, Object> options) {
+        // TODO:
+        return null;
+    }
+
+    private static Optional<RuntimeEndpointRegistry.Statistic> findStats(
+            List<RuntimeEndpointRegistry.Statistic> stats, String uri, String 
direction) {
+        if (stats == null) {
+            return Optional.empty();
+        }
+        return stats.stream()
+                .filter(s -> uri.equals(s.getUri()) && (direction == null || 
s.getDirection().equals(direction)))
+                .findFirst();
+    }
+
+}
diff --git 
a/core/camel-management-api/src/main/java/org/apache/camel/api/management/mbean/ManagedEndpointMBean.java
 
b/core/camel-management-api/src/main/java/org/apache/camel/api/management/mbean/ManagedEndpointMBean.java
index e3cd0504ad8..79d9956d861 100644
--- 
a/core/camel-management-api/src/main/java/org/apache/camel/api/management/mbean/ManagedEndpointMBean.java
+++ 
b/core/camel-management-api/src/main/java/org/apache/camel/api/management/mbean/ManagedEndpointMBean.java
@@ -40,10 +40,13 @@ public interface ManagedEndpointMBean {
     @ManagedAttribute(description = "Endpoint State")
     String getState();
 
-    @ManagedAttribute(description = "Address (such as URL or hostname) this 
endpoint is connecting (only available for some components)")
-    String getEndpointLocationAddress();
+    @ManagedAttribute(description = "Url used for network connecting to 
service (only available for some components)")
+    String getServiceLocationUrl();
+
+    @ManagedAttribute(description = "Protocol used for service connecting 
(only available for some components)")
+    String getServiceLocationProtocol();
 
     @ManagedAttribute(description = "Additional metadata this endpoint is used 
for connecting (only available for some components)")
-    Map<String, String> getEndpointLocationAddressMetadata();
+    Map<String, String> getServiceLocationMetadata();
 
 }
diff --git 
a/core/camel-management/src/main/java/org/apache/camel/management/mbean/ManagedEndpoint.java
 
b/core/camel-management/src/main/java/org/apache/camel/management/mbean/ManagedEndpoint.java
index 200d9a5066c..df4510213b0 100644
--- 
a/core/camel-management/src/main/java/org/apache/camel/management/mbean/ManagedEndpoint.java
+++ 
b/core/camel-management/src/main/java/org/apache/camel/management/mbean/ManagedEndpoint.java
@@ -24,7 +24,7 @@ import org.apache.camel.StatefulService;
 import org.apache.camel.api.management.ManagedInstance;
 import org.apache.camel.api.management.ManagedResource;
 import org.apache.camel.api.management.mbean.ManagedEndpointMBean;
-import org.apache.camel.spi.EndpointLocationAddress;
+import org.apache.camel.spi.EndpointServiceLocation;
 import org.apache.camel.spi.ManagementStrategy;
 
 @ManagedResource(description = "Managed Endpoint")
@@ -81,17 +81,25 @@ public class ManagedEndpoint implements ManagedInstance, 
ManagedEndpointMBean {
     }
 
     @Override
-    public String getEndpointLocationAddress() {
-        if (endpoint instanceof EndpointLocationAddress raa) {
-            return raa.getAddress();
+    public String getServiceLocationUrl() {
+        if (endpoint instanceof EndpointServiceLocation raa) {
+            return raa.getServiceUrl();
         }
         return null;
     }
 
     @Override
-    public Map<String, String> getEndpointLocationAddressMetadata() {
-        if (endpoint instanceof EndpointLocationAddress raa) {
-            return raa.getAddressMetadata();
+    public String getServiceLocationProtocol() {
+        if (endpoint instanceof EndpointServiceLocation raa) {
+            return raa.getServiceProtocol();
+        }
+        return null;
+    }
+
+    @Override
+    public Map<String, String> getServiceLocationMetadata() {
+        if (endpoint instanceof EndpointServiceLocation raa) {
+            return raa.getServiceMetadata();
         }
         return null;
     }
diff --git 
a/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListAddress.java
 
b/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListAddress.java
index 0058e83e297..d0680e9760e 100644
--- 
a/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListAddress.java
+++ 
b/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListAddress.java
@@ -36,6 +36,7 @@ import picocli.CommandLine;
 import picocli.CommandLine.Command;
 
 @Command(name = "address", description = "Get usage of Camel service addresses 
(hosted and external)", sortOptions = false)
+@Deprecated // TODO: protocol
 public class ListAddress extends ProcessWatchCommand {
 
     @CommandLine.Parameters(description = "Name or pid of running Camel 
integration", arity = "0..1")
diff --git 
a/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListService.java
 
b/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListService.java
index 1e9879f9d31..d5696444ca5 100644
--- 
a/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListService.java
+++ 
b/dsl/camel-jbang/camel-jbang-core/src/main/java/org/apache/camel/dsl/jbang/core/commands/process/ListService.java
@@ -33,6 +33,8 @@ import org.apache.camel.util.json.JsonObject;
 import picocli.CommandLine;
 import picocli.CommandLine.Command;
 
+
+// TODO: protocol
 @Command(name = "service",
          description = "Get services of Camel integrations", sortOptions = 
false)
 public class ListService extends ProcessWatchCommand {

Reply via email to