1. Einleitung

Prometheus ist ein Open-Source-Tool zur Überwachung von Systemen und Anwendungen. Es sammelt regelmäßig Messwerte (Metriken), etwa zur CPU-Auslastung, Anzahl von Anfragen oder Speichernutzung.

Diese Daten speichert Prometheus in einer Zeitreihendatenbank. So kann man sehen, wie sich bestimmte Werte im Zeitverlauf verändern. Mit der eigenen Abfragesprache PromQL lassen sich die Daten gezielt auswerten.

1.1. Welches Problem löst Prometheus?

Moderne Software-Systeme bestehen oft aus vielen kleinen Diensten (Microservices), die dynamisch in Containern laufen. In dieser komplexen Umgebung wird es schwierig, den Überblick über den Zustand der Systeme zu behalten:

  • Läuft alles wie erwartet?

  • Warum ist die Anwendung plötzlich langsam?

  • Gibt es Fehlermuster, bevor ein Absturz passiert?

Prometheus löst genau dieses Problem: Es sammelt regelmäßig präzise Messdaten über den Zustand und das Verhalten einer Anwendung. So kann man Fehler früh erkennen, Engpässe analysieren und Systeme effizienter betreiben.

2. Warum Prometheus?

Prometheus ist besonders beliebt, weil es einige wichtige Vorteile mitbringt:

  • Einfach zu integrieren: Man muss nur einen Endpoint bereitstellen, an dem Prometheus regelmäßig Messwerte abfragen kann.

  • Eigene Abfragesprache (PromQL): Ermöglicht sehr gezielte Auswertungen.

  • Gute Visualisierung mit Grafana: Daten können übersichtlich in Dashboards dargestellt werden.

3. Architektur von Prometheus

architecture
Figure 1. Prometheus Architektur
  • Prometheus-Server: Fragt regelmäßig Metriken ab und speichert sie.

  • Exporters / Jobs: Stellen Metriken unter /metrics bereit.

  • Pushgateway: Unterstützt kurzlebige Jobs, die Metriken einmalig senden.

  • Service Discovery: Erkennt automatisch neue Dienste (z. B. in Kubernetes).

  • Alertmanager: Versendet Warnungen auf Basis definierter Regeln.

  • Grafana: Visualisiert Metriken in Dashboards.

  • Web UI: Interface für direkte PromQL-Abfragen.

4. Prometheus vs. Micrometer

Prometheus und Micrometer haben unterschiedliche Rollen im Monitoring-Stack, auch wenn sie oft zusammen verwendet werden:

Aspekt Beschreibung

Prometheus

Monitoring-System zur Erfassung, Speicherung und Analyse von Metriken. Es holt sich die Daten (Pull-Prinzip) regelmäßig von Endpunkten wie /metrics oder /q/metrics.

Micrometer

Bibliothek für Anwendungen zur Erzeugung von Metriken. Sie abstrahiert verschiedene Monitoring-Systeme (z. B. Prometheus, InfluxDB, Datadog) und bietet eine einheitliche API.

Zusammenarbeit

Micrometer erzeugt die Metriken innerhalb einer Anwendung (z. B. Quarkus-App). Prometheus sammelt diese Metriken dann regelmäßig ein.

Micrometer ist also ein Produzent, während Prometheus ein Sammler und Analysator ist.

5. Weitere Monitoring-Alternativen (kurzer Überblick)

Tool Kurzbeschreibung

Grafana Cloud

Gehostete Monitoring-Lösung, integriert Prometheus, Loki und Tempo. Eher für schnelle Setups oder SaaS-Szenarien.

Datadog

Kommerzielle Lösung mit starker Integration in Cloud-Umgebungen, bietet Metriken, Logs und Tracing.

InfluxDB

Zeitreihendatenbank mit eigener Query-Sprache (Flux). Eignet sich für Metriken und Events.

Zabbix

Klassisches Monitoring-Tool mit Fokus auf Infrastrukturüberwachung, eher agentenbasiert.

New Relic

Komplettlösung für Application Performance Monitoring (APM), eher für größere Enterprise-Setups gedacht.

OpenTelemetry

Standard zur Sammlung von Logs, Metriken und Traces – ersetzt langfristig viele eigene APIs (wie Micrometer) und ist stark im Kommen.

6. Prometheus in Quarkus

Quarkus bietet eine integrierte Unterstützung für Micrometer und Prometheus. Die Metriken werden unter /q/metrics bereitgestellt. Voraussetzung dafür ist die Erweiterung quarkus-micrometer-registry-prometheus.

6.1. Konfiguration in Quarkus

quarkus.micrometer.export.prometheus.enabled=true
quarkus.micrometer.export.prometheus.path=/q/metrics

Beispiel für prometheus.yml:

scrape_configs:
  - job_name: 'quarkus-app'
    static_configs:
      - targets: [ 'quarkus:8080' ]

Mögliche Konfiguration in der docker-compose.yml:

services:
  prometheus:
    image: prom/prometheus:latest
    container_name: prometheus
    volumes:
      - ./prometheus.yml:/etc/prometheus/prometheus.yml
    ports:
      - "9090:9090"
    restart: always
    networks:
      - monitoring

  quarkus:
    build:
      context: ../../../
      dockerfile: ./src/main/docker/Dockerfile.jvm
    container_name: quarkus
    ports:
      - "8080:8080" # Optional, for host access
    restart: always
    networks:
      - monitoring

networks:
  monitoring:
    driver: bridge
Die services müssen im selben Netzwerk sein, damit Prometheus die Metriken abfragen kann.

6.2. Eigene Metriken in Resource-Klassen

Mit dem MeterRegistry lassen sich benutzerdefinierte Metriken erzeugen:

package at.htl.feature;

import io.micrometer.core.instrument.MeterRegistry;
import io.micrometer.core.instrument.Tags;
import io.micrometer.core.instrument.Timer;
import jakarta.enterprise.context.ApplicationScoped;
import jakarta.inject.Inject;
import jakarta.ws.rs.*;
import jakarta.ws.rs.core.MediaType;

import java.util.LinkedList;

@ApplicationScoped
@Path("/person")
@Produces(MediaType.APPLICATION_JSON)
public class PersonResource {

    @Inject
    MeterRegistry registry;

    private LinkedList<String> list = new LinkedList<>();

    @Inject
    PersonRepository personRepository;

    public PersonResource(MeterRegistry registry) {
        this.registry = registry;
        registry.gaugeCollectionSize("person_list_size", Tags.empty(), list);
    }

    // Counter für die Anzahl der Anfragen

    @GET
    @Path("/counter/check/{input}")
    public boolean checkPersonCounter(@PathParam("input") String input) {
        list.add(input);
        registry.counter("person_counter").increment();
        return getPerson(input);
    }

    // Timer für die Zeitmessung

    @GET
    @Path("/timer/check/{input}")
    public boolean checkPersonTimer(@PathParam("input") String input) {
        list.add(input);
        Timer.Sample sample = Timer.start(registry);
        boolean result = getPerson(input);
        sample.stop(registry.timer("person_timer"));
        return result;
    }

    // Method to check if a person exists in the database
    public boolean getPerson(String input) {
        String[] parts = input.split(",");
        if (parts.length != 2 || input.isEmpty()) {
            return false;  // Input format is not correct
        }

        String name = parts[0].trim();
        int age = Integer.parseInt(parts[1].trim());

        // Check if the person exists in the repository
        Person person = (Person) personRepository.find("p_name = ?1 and p_age = ?2", name, age);

        return person != null;  // Return true if person exists, false otherwise
    }

    @DELETE
    @Path("/clear-list")
    public void clearList() {
        list.clear();
    }
}

Diese Metriken erscheinen dann automatisch im /q/metrics-Output.

7. PromQL – Die Abfragesprache von Prometheus

PromQL ist eine leistungsstarke Sprache zur Analyse von Metriken.

7.1. Beispiele

  • Alle Metriken anzeigen

{__name__=~".*"}
  • Durchschnittliche CPU-Auslastung (Beispiel für Systemmetriken)

avg(rate(cpu_usage_seconds_total[5m]))
  • Summe eines eigenen Counters

sum(person_counter)

7.2. PromQL-Beispiele für Quarkus

person_counter
person_timer_count
person_list_size
http_server_requests_seconds_count{job="quarkus-app"}

8. Fazit

Prometheus ist ein leistungsstarkes Tool zur Überwachung moderner Anwendungen. Besonders in Verbindung mit Quarkus ist es einfach zu integrieren und bietet umfangreiche Möglichkeiten zur Analyse und Visualisierung von Metriken.

9. Quellen