Skip to content

Commit

Permalink
JMX Metric Insight
Browse files Browse the repository at this point in the history
Solving  #6131 (JMX Support).
  • Loading branch information
PeterF778 committed Sep 22, 2022
1 parent 3371d93 commit d496304
Show file tree
Hide file tree
Showing 39 changed files with 3,365 additions and 12 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@
import io.opentelemetry.instrumentation.runtimemetrics.GarbageCollector;
import io.opentelemetry.instrumentation.runtimemetrics.MemoryPools;
import io.opentelemetry.instrumentation.runtimemetrics.Threads;
import io.opentelemetry.instrumentation.runtimemetrics.jmx.MetricService;
import io.opentelemetry.javaagent.extension.AgentListener;
import io.opentelemetry.sdk.autoconfigure.AutoConfiguredOpenTelemetrySdk;
import io.opentelemetry.sdk.autoconfigure.spi.ConfigProperties;
Expand All @@ -27,21 +28,25 @@ public void afterAgent(AutoConfiguredOpenTelemetrySdk autoConfiguredSdk) {
ConfigProperties config = autoConfiguredSdk.getConfig();

boolean defaultEnabled = config.getBoolean("otel.instrumentation.common.default-enabled", true);
if (!config.getBoolean("otel.instrumentation.runtime-metrics.enabled", defaultEnabled)) {
return;
}
if (config.getBoolean("otel.instrumentation.runtime-metrics.enabled", defaultEnabled)) {

OpenTelemetry openTelemetry = GlobalOpenTelemetry.get();

OpenTelemetry openTelemetry = GlobalOpenTelemetry.get();
BufferPools.registerObservers(openTelemetry);
Classes.registerObservers(openTelemetry);
Cpu.registerObservers(openTelemetry);
MemoryPools.registerObservers(openTelemetry);
Threads.registerObservers(openTelemetry);

BufferPools.registerObservers(openTelemetry);
Classes.registerObservers(openTelemetry);
Cpu.registerObservers(openTelemetry);
MemoryPools.registerObservers(openTelemetry);
Threads.registerObservers(openTelemetry);
if (config.getBoolean(
"otel.instrumentation.runtime-metrics.experimental-metrics.enabled", false)) {
GarbageCollector.registerObservers(openTelemetry);
}
}

if (config.getBoolean(
"otel.instrumentation.runtime-metrics.experimental-metrics.enabled", false)) {
GarbageCollector.registerObservers(openTelemetry);
if (config.getBoolean("otel.jmx.enabled", true)) {
MetricService service = new MetricService(GlobalOpenTelemetry.get(), config);
service.start();
}
}
}
270 changes: 270 additions & 0 deletions instrumentation/runtime-metrics/library/README.md

Large diffs are not rendered by default.

17 changes: 17 additions & 0 deletions instrumentation/runtime-metrics/library/activemq.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# ActiveMQ Metrics

Here is the list of metrics based on MBeans exposed by ActiveMQ.

| Metric Name | Type | Attributes | Description |
| ---------------- | --------------- | ---------------- | --------------- |
| activemq.ProducerCount | UpDownCounter | destination, broker | The number of producers attached to this destination |
| activemq.ConsumerCount | UpDownCounter | destination, broker | The number of consumers subscribed to this destination |
| activemq.memory.MemoryPercentUsage | Gauge | destination, broker | The percentage of configured memory used |
| activemq.message.QueueSize | UpDownCounter | destination, broker | The current number of messages waiting to be consumed |
| activemq.message.ExpiredCount | Counter | destination, broker | The number of messages not delivered because they expired |
| activemq.message.EnqueueCount | Counter | destination, broker | The number of messages sent to this destination |
| activemq.message.DequeueCount | Counter | destination, broker | The number of messages acknowledged and removed from this destination |
| activemq.message.AverageEnqueueTime | Gauge | destination, broker | The average time a message was held on this destination |
| activemq.connections.CurrentConnectionsCount | UpDownCounter | | The total number of current connections |
| activemq.disc.StorePercentUsage | Gauge | | The percentage of configured disk used for persistent messages |
| activemq.disc.TempPercentUsage | Gauge | | The percentage of configured disk used for non-persistent messages |
4 changes: 4 additions & 0 deletions instrumentation/runtime-metrics/library/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,10 @@ plugins {
}

dependencies {
implementation("org.yaml:snakeyaml:1.30")

compileOnly("io.opentelemetry:opentelemetry-sdk-extension-autoconfigure")

testImplementation("io.opentelemetry:opentelemetry-sdk-metrics")
testImplementation(project(":testing-common"))
}
15 changes: 15 additions & 0 deletions instrumentation/runtime-metrics/library/hadoop.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Hadoop Metrics

Here is the list of metrics based on MBeans exposed by Hadoop.

| Metric Name | Type | Attributes | Description |
|-----------------------------------|---------------|------------------|-------------------------------------------------------|
| hadoop.capacity.CapacityUsed | UpDownCounter | node_name | Current used capacity across all data nodes |
| hadoop.capacity.CapacityTotal | UpDownCounter | node_name | Current raw capacity of data nodes |
| hadoop.block.BlocksTotal | UpDownCounter | node_name | Current number of allocated blocks in the system |
| hadoop.block.MissingBlocks | UpDownCounter | node_name | Current number of missing blocks |
| hadoop.block.CorruptBlocks | UpDownCounter | node_name | Current number of blocks with corrupt replicas |
| hadoop.volume.VolumeFailuresTotal | UpDownCounter | node_name | Total number of volume failures across all data nodes |
| hadoop.file.FilesTotal | UpDownCounter | node_name | Current number of files and directories |
| hadoop.file.TotalLoad | UpDownCounter | node_name | Current number of connection |
| hadoop.datanode.Count | UpDownCounter | node_name, state | The Number of data nodes |
16 changes: 16 additions & 0 deletions instrumentation/runtime-metrics/library/jetty.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
# Jetty Metrics

Here is the list of metrics based on MBeans exposed by Jetty.

| Metric Name | Type | Attributes | Description |
|--------------------------------|---------------|--------------|------------------------------------------------------|
| jetty.session.sessionsCreated | Counter | resource | The number of sessions established in total |
| jetty.session.sessionTimeTotal | UpDownCounter | resource | The total time sessions have been active |
| jetty.session.sessionTimeMax | UpDownCounter | resource | The maximum amount of time a session has been active |
| jetty.session.sessionTimeMean | Gauge | resource | The mean time sessions remain active |
| jetty.threads.busyThreads | UpDownCounter | | The current number of busy threads |
| jetty.threads.idleThreads | UpDownCounter | | The current number of idle threads |
| jetty.threads.maxThreads | UpDownCounter | | The maximum number of threads in the pool |
| jetty.threads.queueSize | UpDownCounter | | The current number of threads in the queue |
| jetty.io.selectCount | Counter | resource, id | The number of select calls |
| jetty.logging.LoggerCount | UpDownCounter | | The number of registered loggers by name |
32 changes: 32 additions & 0 deletions instrumentation/runtime-metrics/library/kafka-broker.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# Kafka Broker Metrics

Here is the list of metrics based on MBeans exposed by Kafka broker. <br /><br />
Broker metrics:

| Metric Name | Type | Attributes | Description |
|------------------------------------|---------------|------------|----------------------------------------------------------------------|
| kafka.message.count | Counter | | The number of messages received by the broker |
| kafka.request.count | Counter | type | The number of requests received by the broker |
| kafka.request.failed | Counter | type | The number of requests to the broker resulting in a failure |
| kafka.request.time.total | Counter | type | The total time the broker has taken to service requests |
| kafka.request.time.50p | Gauge | type | The 50th percentile time the broker has taken to service requests |
| kafka.request.time.99p | Gauge | type | The 99th percentile time the broker has taken to service requests |
| kafka.request.queue | UpDownCounter | | Size of the request queue |
| kafka.network.io | Counter | direction | The bytes received or sent by the broker |
| kafka.purgatory.size | UpDownCounter | type | The number of requests waiting in purgatory |
| kafka.partition.count | UpDownCounter | | The number of partitions on the broker |
| kafka.partition.offline | UpDownCounter | | The number of partitions offline |
| kafka.partition.underReplicated | UpDownCounter | | The number of under replicated partitions |
| kafka.isr.operation.count | UpDownCounter | operation | The number of in-sync replica shrink and expand operations |
| kafka.lag.max | Counter | | The max lag in messages between follower and leader replicas |
| kafka.controller.active.count | UpDownCounter | | The number of controllers active on the broker |
| kafka.leaderElection.count | Counter | | The leader election count |
| kafka.leaderElection.unclean.count | Counter | | Unclean leader election count - increasing indicates broker failures |
<br />
Log metrics:

| Metric Name | Type | Attributes | Description |
|---------------------------|---------|------------|----------------------------------|
| kafka.logs.flush.count | Counter | | Log flush count |
| kafka.logs.flush.time.50p | Gauge | | Log flush time - 50th percentile |
| kafka.logs.flush.time.99p | Gauge | | Log flush time - 99th percentile |
28 changes: 28 additions & 0 deletions instrumentation/runtime-metrics/library/kafka-consumer.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
# Kafka Consumer Metrics

Here is the list of metrics based on MBeans exposed by Kafka consumer. <br /><br />

Consumer metrics:

| Metric Name | Type | Attributes | Description |
|---------------------------------------------------|-------|------------------|--------------------------------------------------------------------------------|
| kafka.consumer.all.rebalance-latency-avg | Gauge | client-id | The average time taken for a group to complete a successful rebalance |
| kafka.consumer.all.rebalance-latency-max | Gauge | client-id | The maximum time taken for a group to complete a successful rebalance |
| kafka.consumer.all.rebalance-latency-total | Gauge | client-id | The total time this consumer has spent in successful rebalances since creation |
| kafka.consumer.all.rebalance-rate-per-hour | Gauge | client-id | The number of successful rebalance events per hour |
| kafka.consumer.all.rebalance-total | Gauge | client-id | The total number of successful rebalance events |
| kafka.consumer.all.last-rebalance-seconds-ago | Gauge | client-id | Number of seconds since the last rebalance event |
| kafka.consumer.all.failed-rebalance-rate-per-hour | Gauge | client-id | Number of failed rebalance events per hour |
| kafka.consumer.all.failed-rebalance-total | Gauge | client-id | Total number of failed rebalance events |
| kafka.consumer.all.commit-latency-avg | Gauge | client-id | The average time taken for a commit request |
| kafka.consumer.all.commit-rate | Gauge | client-id | The number of commit calls per second |
| kafka.consumer.all.fetch-rate | Gauge | client-id | The number of fetch requests for all topics per second |
| kafka.consumer.all.fetch-size-avg | Gauge | client-id | The average number of bytes fetched per request for all topics |
| kafka.consumer.all.fetch-latency-avg | Gauge | client-id | The average time taken for a fetch request |
| kafka.consumer.all.fetch-throttle-time-avg | Gauge | client-id | The average throttle time |
| kafka.consumer.all.records-lag-max | Gauge | client-id | Number of messages the consumer lags behind the producer |
| kafka.consumer.all.records-consumed-rate | Gauge | client-id | The average number of records consumed for all topics per second |
| kafka.consumer.all.bytes-consumed-rate | Gauge | client-id | The average number of bytes consumed for all topics per second |
| kafka.consumer.bytes-consumed-rate | Gauge | client-id, topic | The average number of bytes consumed per second |
| kafka.consumer.fetch-size-avg | Gauge | client-id, topic | The average number of bytes fetched per request |
| kafka.consumer.records-consumed-rate | Gauge | client-id, topic | The average number of records consumed per second |
24 changes: 24 additions & 0 deletions instrumentation/runtime-metrics/library/kafka-producer.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
# Kafka Producer Metrics

Here is the list of metrics based on MBeans exposed by Kafka producer. <br /><br />

Producer metrics:

| Metric Name | Type | Attributes | Description |
|----------------------------------------------|-------|------------------|--------------------------------------------------------------------------------------|
| kafka.producer.all.batch-size-avg | Gauge | client-id | Average number of bytes sent per partition per request |
| kafka.producer.all.bufferpool-wait-ratio | Gauge | client-id | The fraction of time an appender waits for space allocation |
| kafka.producer.all.compression-rate-avg | Gauge | client-id | Average ratio of the compressed batch size to the uncompressed size |
| kafka.producer.all.io-wait-time-ns-avg | Gauge | client-id | The average time the I/O thread spent waiting for a socket ready for reads or writes |
| kafka.producer.all.outgoing-byte-rate | Gauge | client-id | The average number of outgoing bytes sent per second to all servers |
| kafka.producer.all.produce-throttle-time-avg | Gauge | client-id | Average time a request was throttled by a broker |
| kafka.producer.all.record-queue-time-avg | Gauge | client-id | The average time record batches spent in the send buffer |
| kafka.producer.all.record-retry-rate | Gauge | client-id | The average number of retried record sends per second |
| kafka.producer.all.request-latency-avg | Gauge | client-id | The average request latency |
| kafka.producer.all.request-rate | Gauge | client-id | The average number of requests sent per second |
| kafka.producer.all.response-rate | Gauge | client-id | The average number of response sent per second |
| kafka.producer.byte-rate | Gauge | client-id, topic | The average number of bytes sent per second for a topic |
| kafka.producer.compression-rate | Gauge | client-id, topic | The average compression rate of record batches for a topic |
| kafka.producer.record-error-rate | Gauge | client-id, topic | The average per-second number of record sends that resulted in errors for a topic |
| kafka.producer.record-retry-rate | Gauge | client-id, topic | The average per-second number of retried record sends for a topic |
| kafka.producer.record-send-rate | Gauge | client-id, topic | The average number of records sent per second for a topic |
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
/*
* Copyright The OpenTelemetry Authors
* SPDX-License-Identifier: Apache-2.0
*/

package io.opentelemetry.instrumentation.runtimemetrics.jmx;

/**
* A class holding relevant information about an MBean atribute which will be used for collecting
* metric values. The info comes directly from the relevant MBeans.
*/
class AttributeInfo {

private boolean usesDoubles;
private String description;

AttributeInfo(Number sampleValue, String description) {
if (sampleValue instanceof Byte
|| sampleValue instanceof Short
|| sampleValue instanceof Integer
|| sampleValue instanceof Long) {
// will use Long values
usesDoubles = false;
} else {
usesDoubles = true;
}
this.description = description;
}

boolean usesDoubleValues() {
return usesDoubles;
}

String getDescription() {
return description;
}

/**
* It is unlikely, but possible, that among the MBeans matching some ObjectName pattern,
* attributes with the same name but different types exist. In such cases we have to use a metric
* type which will be able to handle all of these attributes.
*
* @param other another AttributeInfo apparently for the same MBean attribute, must not be null
*/
void updateFrom(AttributeInfo other) {
if (other.usesDoubleValues()) {
usesDoubles = true;
}
if (description == null) {
description = other.getDescription();
}
}
}
Loading

0 comments on commit d496304

Please sign in to comment.