У меня есть простое весеннее загрузочное приложение со следующим конфигом (проект доступен здесь на GitHub):

management:
  metrics:
    export:
      simple:
        mode: step
  endpoints:
    web:
      exposure:
        include: "*"

Приведенный выше конфиг создает SimpleMeterRegistry и настраивает его показатели на основе шагов с шагом 60 секунд. У меня есть один сценарий, который отправляет 50-100 запросов в секунду в конечную точку фиктивной службы, а есть другой сценарий, который опрашивает данные из /actuator/metrics/http.server.requests каждые X секунд. Когда я запускаю последний скрипт каждые 60 секунд, все работает как положено , но когда скрипт запускается каждые 120 секунд , ответ всегда содержит нули . для TOTAL_TIME и COUNT метрик.

Кто-нибудь может объяснить такое поведение?

Я прочитал документацию здесь. Картинка ниже введите описание изображения здесь может указывать, что реестр будет пытаться агрегировать данные за предыдущий интервал, только если в течение текущего интервала вызывается pollAsRate. Это объяснит, почему он не работает в течение 120 секунд. Но это только мое предположение, кто-нибудь знает, что на самом деле здесь происходит?

Версия для начальной загрузки: 2.1.7.RELEASE

ОБНОВЛЕНИЕ

Я провел аналогичный тест с management.metrics.export.simple.step=10s, он отлично работает, когда интервал опроса равен 10 с, и не работает, когда он равен 20 с. В течение 15 секунд он работает время от времени. Так что это определенно связано с размером шага и частотой опроса.

0
Marko Vranjkovic 19 Авг 2019 в 16:40

2 ответа

Лучший ответ

Наконец-то разобрался, что происходит.

При каждом запросе к /actuator/metrics MetricsEndpoint собирается объединять меры (см. здесь ). Это делается путем сбора значений для всех счетчиков с помощью measurement.getValue(). StepMeasurement.getValue() не просто вернет значение, но и обновит текущий и предыдущий интервалы и счетчики, а также свернет счетчик (см. здесь и здесь ) .

< Сильный > StepMeasurement.getValue

public double getValue() {
  double absoluteCount = (Double)this.f.get();
  double inc = Math.max(0.0D, absoluteCount - this.lastCount.sum());
  this.lastCount.add(inc);
  this.value.getCurrent().add(inc);
  return this.value.poll();
}

< Сильный > StepDouble.poll

public double poll() {
    rollCount(clock.wallTime());
    return previous;
}

Как это связано с интервалом опроса? Если вы не опросите конечную точку /actuator/metrics, текущий и предыдущий интервалы не будут обновлены, что приведет к тому, что текущий интервал не будет обновлен и метрики будут записаны для «неправильного» интервала.

0
Marko Vranjkovic 20 Авг 2019 в 08:17

MAX, TOTAL_TIME, COUNT является свойством Статистика.

DistributionStatisticConfig имеет .expiry(Duration.ofMinutes(2)), который устанавливает для некоторого измерения значение 0, если нет запроса для последнего 2. минут (120 секунд)

Такие методы, как public TimeWindowMax(Clock clock,...), private void rotate() были написаны для того же самого. Вы можете увидеть реализацию здесь

Более подробный ответ

0
Patel Romil 19 Авг 2019 в 15:12