All Downloads are FREE. Search and download functionalities are using the official Maven repository.

io.micrometer.prometheus.PrometheusNamingConvention Maven / Gradle / Ivy

Go to download

MeterRegistry implementation for Prometheus using io.prometheus:prometheus-metrics-core. If you have compatibility issues with this module, you can go back to io.micrometer:micrometer-registry-prometheus-simpleclient that uses io.prometheus:simpleclient_common.

There is a newer version: 1.14.2
Show newest version
/*
 * Copyright 2017 VMware, Inc.
 *
 * Licensed 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
 *
 * https://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 io.micrometer.prometheus;

import io.micrometer.core.instrument.Meter;
import io.micrometer.core.instrument.config.NamingConvention;
import io.micrometer.core.lang.Nullable;

import java.util.regex.Pattern;

/**
 * See https://prometheus.io/docs/concepts/data_model/#metric-names-and-labels for a
 * specification of the constraints on metric names and labels
 *
 * @author Jon Schneider
 */
public class PrometheusNamingConvention implements NamingConvention {

    private static final Pattern nameChars = Pattern.compile("[^a-zA-Z0-9_:]");

    private static final Pattern tagKeyChars = Pattern.compile("[^a-zA-Z0-9_]");

    private final String timerSuffix;

    public PrometheusNamingConvention() {
        this("");
    }

    public PrometheusNamingConvention(String timerSuffix) {
        this.timerSuffix = timerSuffix;
    }

    /**
     * Names are snake-cased. They contain a base unit suffix when applicable.
     * 

* Names may contain ASCII letters and digits, as well as underscores and colons. They * must match the regex [a-zA-Z_:][a-zA-Z0-9_:]* */ @Override public String name(String name, Meter.Type type, @Nullable String baseUnit) { String conventionName = NamingConvention.snakeCase.name(name, type, baseUnit); switch (type) { case COUNTER: case DISTRIBUTION_SUMMARY: case GAUGE: if (baseUnit != null && !conventionName.endsWith("_" + baseUnit)) conventionName += "_" + baseUnit; break; } switch (type) { case COUNTER: if (!conventionName.endsWith("_total")) conventionName += "_total"; break; case TIMER: case LONG_TASK_TIMER: if (!timerSuffix.isEmpty() && conventionName.endsWith(timerSuffix)) { conventionName += "_seconds"; } else if (!conventionName.endsWith("_seconds")) { conventionName += timerSuffix + "_seconds"; } break; } String sanitized = nameChars.matcher(conventionName).replaceAll("_"); if (!Character.isLetter(sanitized.charAt(0))) { sanitized = "m_" + sanitized; } return sanitized; } /** * Label names may contain ASCII letters, numbers, as well as underscores. They must * match the regex [a-zA-Z_][a-zA-Z0-9_]*. Label names beginning with __ are reserved * for internal use. */ @Override public String tagKey(String key) { String conventionKey = NamingConvention.snakeCase.tagKey(key); String sanitized = tagKeyChars.matcher(conventionKey).replaceAll("_"); if (!Character.isLetter(sanitized.charAt(0))) { sanitized = "m_" + sanitized; } return sanitized; } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy