From 5a5e60d3719fba1063a5447f1e87bf00b59d42e5 Mon Sep 17 00:00:00 2001 From: sunxien <1025488853@qq.com> Date: Thu, 25 Dec 2025 11:41:08 +0800 Subject: [PATCH] =?UTF-8?q?feat(canal/adapter):=20adapter=E6=94=AF?= =?UTF-8?q?=E6=8C=81prometheus=E6=9A=B4=E9=9C=B2jvm=E6=8C=87=E6=A0=87=20(#?= =?UTF-8?q?5549)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - adapter 默认提供prometheus暴露JVM指标 - 指定 maven-antrun-plugin 未指定版本号,默认是 3.0.0,但是配置中使用 标签,编译报错。 - 降级版本号,显式指定 1.8 版本 - 或者把配置中的 标签改成 --- client-adapter/launcher/pom.xml | 13 ++- .../launcher/CanalAdapterApplication.java | 1 + .../prometheus/CanalAdapterExports.java | 33 +++++++ .../prometheus/PrometheusService.java | 98 +++++++++++++++++++ 4 files changed, 144 insertions(+), 1 deletion(-) create mode 100644 client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/CanalAdapterExports.java create mode 100644 client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/PrometheusService.java diff --git a/client-adapter/launcher/pom.xml b/client-adapter/launcher/pom.xml index 3f8cd836..34246b91 100644 --- a/client-adapter/launcher/pom.xml +++ b/client-adapter/launcher/pom.xml @@ -68,7 +68,6 @@ com.microsoft.sqlserver mssql-jdbc - org.apache.hbase hbase-shaded-client @@ -79,6 +78,18 @@ clickhouse-jdbc + + + io.prometheus + simpleclient_hotspot + 0.4.0 + + + io.prometheus + simpleclient_httpserver + 0.4.0 + + com.alibaba.otter diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java index 2e3501dd..990af7fa 100644 --- a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/CanalAdapterApplication.java @@ -13,6 +13,7 @@ import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration; */ @SpringBootApplication(exclude= { DataSourceAutoConfiguration.class}) public class CanalAdapterApplication { + public static void main(String[] args) { // 支持rocketmq client 配置日志路径 System.setProperty("rocketmq.client.logUseSlf4j","true"); diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/CanalAdapterExports.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/CanalAdapterExports.java new file mode 100644 index 00000000..7dd100bc --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/CanalAdapterExports.java @@ -0,0 +1,33 @@ +package com.alibaba.otter.canal.adapter.launcher.prometheus; + +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +/** + * @author sunxien + * @date 2025/5/19 + * @since 1.0.0-SNAPSHOT + */ +public class CanalAdapterExports { + + private static final Logger logger = LoggerFactory.getLogger(CanalAdapterExports.class); + + private CanalAdapterExports() { + } + + private static class SingletonHolder { + private static final CanalAdapterExports SINGLETON = new CanalAdapterExports(); + } + + public static CanalAdapterExports instance() { + return SingletonHolder.SINGLETON; + } + + public void initialize() { + // TODO + } + + public void terminate() { + // TODO + } +} diff --git a/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/PrometheusService.java b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/PrometheusService.java new file mode 100644 index 00000000..76fcf8c8 --- /dev/null +++ b/client-adapter/launcher/src/main/java/com/alibaba/otter/canal/adapter/launcher/prometheus/PrometheusService.java @@ -0,0 +1,98 @@ +package com.alibaba.otter.canal.adapter.launcher.prometheus; + +import io.prometheus.client.exporter.HTTPServer; +import io.prometheus.client.hotspot.DefaultExports; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.springframework.beans.factory.DisposableBean; +import org.springframework.beans.factory.InitializingBean; +import org.springframework.stereotype.Component; + +import java.io.IOException; + +/** + * @author sunxien + * @date 2025/5/19 + * @since 1.0.0-SNAPSHOT + */ +@Component +public class PrometheusService implements InitializingBean, DisposableBean { + + private static final Logger logger = LoggerFactory.getLogger(PrometheusService.class); + + private final CanalAdapterExports adapterExports; + private volatile boolean running = false; + + /** + *
+     * Canal Server admin port: 11112
+     * Canal Server tcp port: 11111
+     * Canal Adapter metric port: 11113
+     * 
+ */ + private int port = 11113; + private HTTPServer httpServer; + + private PrometheusService() { + this.adapterExports = CanalAdapterExports.instance(); + } + + private static class SingletonHolder { + private static final PrometheusService SINGLETON = new PrometheusService(); + } + + public static PrometheusService getInstance() { + return SingletonHolder.SINGLETON; + } + + @Override + public void afterPropertiesSet() throws Exception { + PrometheusService.getInstance().initialize(); + } + + @Override + public void destroy() throws Exception { + PrometheusService.getInstance().terminate(); + } + + public void initialize() { + try { + logger.info("Starting prometheus HTTPServer on port {}....", port); + // TODO 2.Https? + httpServer = new HTTPServer(port); + logger.info("Start prometheus HTTPServer on port {} success", port); + } catch (IOException e) { + logger.error("Unable to start prometheus HTTPServer on port {}.", port, e); + return; + } + try { + // JVM exports + DefaultExports.initialize(); + // adapterExports.initialize(); + this.running = true; + } catch (Throwable t) { + logger.error("Unable to initialize adapter exports. (Register the default Hotspot collectors)", t); + } + } + + public void terminate() { + try { + this.running = false; + adapterExports.terminate(); + if (httpServer != null) { + httpServer.stop(); + logger.info("Stop prometheus HTTPServer on port {} success", port); + } + } catch (Throwable t) { + logger.error("Something happened while terminating prometheus HTTPServer.", t); + } + } + + public boolean isRunning() { + return running; + } + + public void setServerPort(int port) { + this.port = port; + } +}