首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何从java应用程序导出Prometheus格式的度量(由DropWizard收集)?

如何从java应用程序导出Prometheus格式的度量(由DropWizard收集)?
EN

Stack Overflow用户
提问于 2022-06-29 11:43:32
回答 3查看 719关注 0票数 1

My aim -创建spring引导应用程序,使用DropWizard收集度量,并为Prometheus公开端点以使用应用程序度量:

我的代码:

代码语言:javascript
复制
@SpringBootApplication
@EnableMetrics(proxyTargetClass = true)
public class DemoApplication {

    public static void main(String[] args) {

        SpringApplication.run(DemoApplication.class, args);
    }

}
代码语言:javascript
复制
package com.example.demo;

import com.codahale.metrics.Counter;
import com.codahale.metrics.MetricRegistry;
import com.codahale.metrics.annotation.Timed;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.PostConstruct;
import java.util.concurrent.atomic.AtomicLong;

@RestController
public class HelloController {
    private AtomicLong atomicLong = new AtomicLong();
    private Counter counter;

    @Autowired
    private MetricRegistry metricRegistry;

    @PostConstruct
    public void init() {
        counter = metricRegistry.counter("counter");
    }

    @GetMapping("/hello")
    @Timed(name = "my-index")
    public String index() {
        counter.inc();

        return "Greetings from Spring Boot!. count=" + atomicLong.incrementAndGet();
    }

}
代码语言:javascript
复制
package com.example.demo;

import com.codahale.metrics.ConsoleReporter;
import com.codahale.metrics.MetricRegistry;
import com.codahale.metrics.jvm.FileDescriptorRatioGauge;
import com.codahale.metrics.jvm.GarbageCollectorMetricSet;
import com.codahale.metrics.jvm.MemoryUsageGaugeSet;
import com.codahale.metrics.jvm.ThreadStatesGaugeSet;
import com.codahale.metrics.servlets.AdminServlet;
import com.codahale.metrics.servlets.CpuProfileServlet;
import com.codahale.metrics.servlets.MetricsServlet;
import com.ryantenney.metrics.spring.config.annotation.EnableMetrics;
import com.ryantenney.metrics.spring.config.annotation.MetricsConfigurerAdapter;
import io.prometheus.client.dropwizard.DropwizardExports;
import org.springframework.boot.web.servlet.ServletRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.concurrent.TimeUnit;

@Configuration
public class Config /*extends MetricsConfigurerAdapter*/ {
    //@Override
            //public void configureReporters(MetricRegistry metricRegistry) {
        //    // registerReporter allows the MetricsConfigurerAdapter to
        //    // shut down the reporter when the Spring context is closed
        //   // registerReporter(ConsoleReporter
        //   //         .forRegistry(metricRegistry)
        //   //         .build())
        //   //         .start(1, TimeUnit.MINUTES);


        //    new DropwizardExports(metricRegistry).register();
        //}

   @Bean
   public DropwizardExports dropwizardExports(MetricRegistry metricRegistry){
       DropwizardExports dropwizardExports = new DropwizardExports(metricRegistry);
       dropwizardExports.register();
       return dropwizardExports;
   }

    @Bean
    public MetricRegistry metricRegistry() {
        MetricRegistry metricRegistry = new MetricRegistry();
        metricRegistry.registerAll(new GarbageCollectorMetricSet());
        metricRegistry.registerAll(new MemoryUsageGaugeSet());
        metricRegistry.registerAll(new ThreadStatesGaugeSet());
        return metricRegistry;
    }

    @Bean
    public ConsoleReporter consoleReporter(MetricRegistry metricRegistry) {
        ConsoleReporter reporter = ConsoleReporter.forRegistry(metricRegistry).build();
        reporter.start(5, TimeUnit.SECONDS);
        reporter.report();
        return reporter;
    }

    @Bean
    public ServletRegistrationBean<MetricsServlet> registerMetricsServlet(MetricRegistry metricRegistry) {
        return new ServletRegistrationBean<>(new MetricsServlet(metricRegistry), "/metrics/*");
    }

    @Bean
    public ServletRegistrationBean<CpuProfileServlet> registerCpuServlet() {
        return new ServletRegistrationBean<>(new CpuProfileServlet(), "/cpu/*");
    }
}

build.gradle:

代码语言:javascript
复制
plugins {
    id 'org.springframework.boot' version '2.7.1'
    id 'io.spring.dependency-management' version '1.0.11.RELEASE'
    id 'java'
}

group = 'com.example'
version = '0.0.1-SNAPSHOT'
sourceCompatibility = '17'

repositories {
    mavenCentral()
}

dependencies {
    implementation 'org.springframework.boot:spring-boot-starter-web'
    implementation "org.springframework.boot:spring-boot-starter-actuator"
    // Minimum required for metrics.
    implementation ('com.ryantenney.metrics:metrics-spring:3.1.3') {
        exclude group: 'com.codahale.metrics'
        exclude group: 'org.springframework'
    }
    implementation 'io.dropwizard.metrics:metrics-core:4.2.9'
    implementation 'io.dropwizard.metrics:metrics-annotation:4.2.9'
    implementation 'io.dropwizard.metrics:metrics-servlets:4.2.9'

    implementation 'io.prometheus:simpleclient_dropwizard:0.15.0'
    implementation 'io.prometheus:simpleclient_servlet:0.15.0'
    implementation 'io.dropwizard:dropwizard-core:2.1.0'

    implementation 'com.ryantenney.metrics:metrics-spring:3.1.3'
    implementation 'io.prometheus:simpleclient_common:0.16.0'

    testImplementation 'org.springframework.boot:spring-boot-starter-test'
}

tasks.named('test') {
    useJUnitPlatform()
}

我访问localhost:8080/metrics并收到以下响应:

代码语言:javascript
复制
{
  "version": "4.0.0",
  "gauges": {
    "G1-Old-Generation.count": {
      "value": 0
    },
    "G1-Old-Generation.time": {
      "value": 0
    },
    "G1-Young-Generation.count": {
      "value": 7
    },
    "G1-Young-Generation.time": {
      "value": 31
    },
    "blocked.count": {
      "value": 0
    },
    "count": {
      "value": 26
    },
    "daemon.count": {
      "value": 22
    },
    "deadlock.count": {
      "value": 0
    },
    "deadlocks": {
      "value": []
    },
    "heap.committed": {
      "value": 301989888
    },
    "heap.init": {
      "value": 532676608
    },
    "heap.max": {
      "value": 8518631424
    },
    "heap.usage": {
      "value": 0.008041180864688155
    },
    "heap.used": {
      "value": 68499856
    },
    "new.count": {
      "value": 0
    },
    "non-heap.committed": {
      "value": 51707904
    },
    "non-heap.init": {
      "value": 2555904
    },
    "non-heap.max": {
      "value": -1
    },
    "non-heap.usage": {
      "value": -5.0738536E7
    },
    "non-heap.used": {
      "value": 50738536
    },
    "peak.count": {
      "value": 32
    },
    "pools.CodeCache.committed": {
      "value": 10551296
    },
    "pools.CodeCache.init": {
      "value": 2555904
    },
    "pools.CodeCache.max": {
      "value": 50331648
    },
    "pools.CodeCache.usage": {
      "value": 0.2039642333984375
    },
    "pools.CodeCache.used": {
      "value": 10265856
    },
    "pools.Compressed-Class-Space.committed": {
      "value": 5177344
    },
    "pools.Compressed-Class-Space.init": {
      "value": 0
    },
    "pools.Compressed-Class-Space.max": {
      "value": 1073741824
    },
    "pools.Compressed-Class-Space.usage": {
      "value": 0.004625104367733002
    },
    "pools.Compressed-Class-Space.used": {
      "value": 4966168
    },
    "pools.G1-Eden-Space.committed": {
      "value": 188743680
    },
    "pools.G1-Eden-Space.init": {
      "value": 29360128
    },
    "pools.G1-Eden-Space.max": {
      "value": -1
    },
    "pools.G1-Eden-Space.usage": {
      "value": 0.26666666666666666
    },
    "pools.G1-Eden-Space.used": {
      "value": 50331648
    },
    "pools.G1-Eden-Space.used-after-gc": {
      "value": 0
    },
    "pools.G1-Old-Gen.committed": {
      "value": 109051904
    },
    "pools.G1-Old-Gen.init": {
      "value": 503316480
    },
    "pools.G1-Old-Gen.max": {
      "value": 8518631424
    },
    "pools.G1-Old-Gen.usage": {
      "value": 0.0017806278080379123
    },
    "pools.G1-Old-Gen.used": {
      "value": 15168512
    },
    "pools.G1-Old-Gen.used-after-gc": {
      "value": 15168512
    },
    "pools.G1-Survivor-Space.committed": {
      "value": 4194304
    },
    "pools.G1-Survivor-Space.init": {
      "value": 0
    },
    "pools.G1-Survivor-Space.max": {
      "value": -1
    },
    "pools.G1-Survivor-Space.usage": {
      "value": 0.7151832580566406
    },
    "pools.G1-Survivor-Space.used": {
      "value": 2999696
    },
    "pools.G1-Survivor-Space.used-after-gc": {
      "value": 2999696
    },
    "pools.Metaspace.committed": {
      "value": 35979264
    },
    "pools.Metaspace.init": {
      "value": 0
    },
    "pools.Metaspace.max": {
      "value": -1
    },
    "pools.Metaspace.usage": {
      "value": 0.9868604316086066
    },
    "pools.Metaspace.used": {
      "value": 35506512
    },
    "runnable.count": {
      "value": 10
    },
    "terminated.count": {
      "value": 0
    },
    "timed_waiting.count": {
      "value": 5
    },
    "total.committed": {
      "value": 353697792
    },
    "total.init": {
      "value": 535232512
    },
    "total.max": {
      "value": 8518631423
    },
    "total.used": {
      "value": 119238392
    },
    "total_started.count": {
      "value": 47
    },
    "waiting.count": {
      "value": 11
    }
  },
  "counters": {
    "counter": {
      "count": 9
    }
  },
  "histograms": {},
  "meters": {},
  "timers": {}
}

显然,这个输出不适用于普罗米修斯(所有的点至少应该用"_“替换)

如何使输出的格式为prometheus做好准备?

附注:

基于文档,我理解io.prometheus.client.dropwizardDropwizardExports类负责生成格式为Prometheus的度量,但我不明白如何生成。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2022-06-29 14:06:19

最后,我找到了一个根本原因:

代码语言:javascript
复制
com.codahale.metrics.servlets.MetricsServlet

应改为

代码语言:javascript
复制
io.prometheus.client.exporter.MetricsServlet
票数 0
EN

Stack Overflow用户

发布于 2022-06-29 12:37:10

我实现了将度量导出到Prometheus的不同方法:

1.1) Pushgateway的自定义实现

我编写了将输出生成到StringBuilder中的代码,并只遵循文档格式/

最后,使用您选择的java HttpClient将该字符串发布到Pushgateway。

1.2)由Prometheus刮除的自定义页面

我编写了一个动态页面(servlet,jsp,.)生成带有纯文本内容类型的输出,并且只遵循文档格式/

配置Prometheus以抓取该动态页面。

  1. 使用现有图书馆

我使用了java,它是Java的官方客户端库。查看自述中关于导出的章节,它非常好,并且涵盖了推送度量和被刮掉的两个方面。

票数 0
EN

Stack Overflow用户

发布于 2022-06-29 13:16:22

我看不出有什么明显的区别,但这是一个有用的例子:

代码语言:javascript
复制
public class JavaDropwizard {
  // Create registry for Dropwizard metrics.
  static final MetricRegistry metrics = new MetricRegistry();
  // Create a Dropwizard counter.
  static final Counter counter = metrics.counter("my.example.counter.total");

  public static void main( String[] args ) throws Exception {
      // Increment the counter.
      counter.inc();

      // Hook the Dropwizard registry into the Prometheus registry
      // via the DropwizardExports collector.
      CollectorRegistry.defaultRegistry.register(new DropwizardExports(metrics));


      // Expose Prometheus metrics.
      Server server = new Server(1234);
      ServletContextHandler context = new ServletContextHandler();
      context.setContextPath("/");
      server.setHandler(context);
      context.addServlet(new ServletHolder(new MetricsServlet()), "/metrics");
      // Add metrics about CPU, JVM memory etc.
      DefaultExports.initialize();
      // Start the webserver.
      server.start();
      server.join();
  }
}

pom.xml

代码语言:javascript
复制
<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/maven-v4_0_0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>io.robustperception.java_examples</groupId>
  <artifactId>java_dropwizard</artifactId>
  <packaging>jar</packaging>
  <version>1.0-SNAPSHOT</version>
  <properties>
    <maven.compiler.source>17</maven.compiler.source>
    <maven.compiler.target>17</maven.compiler.target>
  </properties>
  <name>java_dropwizard</name>
  <url>http://maven.apache.org</url>
  <dependencies>
    <dependency>
      <groupId>io.prometheus</groupId>
      <artifactId>simpleclient</artifactId>
      <version>0.15.0</version>
    </dependency>
    <dependency>
      <groupId>io.prometheus</groupId>
      <artifactId>simpleclient_hotspot</artifactId>
      <version>0.15.0</version>
    </dependency>
    <dependency>
      <groupId>io.prometheus</groupId>
      <artifactId>simpleclient_servlet</artifactId>
      <version>0.15.0</version>
    </dependency>
    <dependency>
      <groupId>io.prometheus</groupId>
      <artifactId>simpleclient_dropwizard</artifactId>
      <version>0.15.0</version>
    </dependency>
    <dependency>
        <groupId>io.dropwizard.metrics</groupId>
        <artifactId>metrics-core</artifactId>
        <version>4.2.9</version>
    </dependency>
    <dependency>
      <groupId>org.eclipse.jetty</groupId>
      <artifactId>jetty-servlet</artifactId>
      <version>8.1.7.v20120910</version>
    </dependency>
  </dependencies>

  <build>
    <plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.1</version>
      </plugin>
      <!-- Build a full jar with dependencies --> 
      <plugin>
        <artifactId>maven-assembly-plugin</artifactId>
        <configuration>
          <archive>
        <manifest>
          <mainClass>io.robustperception.java_examples.JavaDropwizard</mainClass>
        </manifest>
      </archive>
      <descriptorRefs>
        <descriptorRef>jar-with-dependencies</descriptorRef>
      </descriptorRefs>
    </configuration>
    <executions>
      <execution>
        <id>make-assembly</id>
        <phase>package</phase>
        <goals>
          <goal>single</goal>
        </goals>
      </execution>
    </executions>
  </plugin>
</plugins>
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72800851

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档