Метрики для системних компонентів Kubernetes

Метрики для системних компонентів Kubernetes

Метрики системних компонентів дають змогу краще зрозуміти, що відбувається всередині них. Метрики особливо корисні для побудови dashboards та сповіщень.

Компоненти Kubernetes надають метрики у форматі Prometheus. Цей формат — структурований звичайний текст, який можуть читати як люди, так і машини.

Метрики в Kubernetes

У більшості випадків метрики доступні в точці доступу /metrics HTTP-сервера. Для компонентів, які стандартно не відкривають цю точку доступу, її можна ввімкнути за допомогою прапорця --bind-address.

Приклади таких компонентів:

У промисловому середовищі варто налаштувати Prometheus Server або інший збирач метрик, щоб періодично збирати ці метрики й робити їх доступними в базі даних часових рядів.

Зверніть увагу, що kubelet також надає метрики через точки доступу /metrics/cadvisor, /metrics/resource та /metrics/probes. Ці метрики мають інший життєвий цикл.

Якщо ваш кластер використовує RBAC, для читання метрик потрібна авторизація через користувача, групу або ServiceAccount з ClusterRole, що дозволяє доступ до /metrics. Наприклад:

apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
  name: prometheus
rules:
  - nonResourceURLs:
      - "/metrics"
    verbs:
      - get

Життєвий цикл метрик

Альфа-метрика → Бета-метрика → Стабільна метрика → Застаріла метрика → Прихована метрика → Видалена метрика

Альфа-метрики не мають гарантій стабільності. Ці метрики можуть бути змінені або видалені в будь-який момент.

Бета-метрики дотримуються менш суворого контракту API, ніж стабільні. Із бета-метрик не можна вилучати мітки протягом їх життєвого циклу, однак мітки можна додавати, поки метрика перебуває на стадії бета.

Стабільні метрики гарантовано не змінюються. Це означає:

  • Стабільну метрику без ознаки застарілості не буде видалено чи перейменовано
  • Тип стабільної метрики не буде змінено

Застарілі метрики заплановано до видалення, але вони все ще доступні для використання. Ці метрики містять анотацію з версією, у якій вони стали застарілими.

Наприклад:

  • Перед застаріванням

    # HELP some_counter this counts things
    # TYPE some_counter counter
    some_counter 0
    
  • Після застарівання

    # HELP some_counter (Deprecated since 1.15.0) this counts things
    # TYPE some_counter counter
    some_counter 0
    

Приховані метрики більше не публікуються для збирання, але все ще доступні для використання. Застаріла метрика стає прихованою через певний час, залежно від її рівня стабільності:

  • STABLE метрики стають прихованими щонайменше через 3 випуски або 9 місяців, залежно від того, що довше.
  • BETA метрики стають прихованими щонайменше через 1 випуск або 4 місяці, залежно від того, що довше.
  • ALPHA метрики можуть бути приховані або видалені в тому самому випуску, в якому вони стали застарілими.

Щоб використовувати приховану метрику, її потрібно ввімкнути. Докладніше дивіться в розділі Показ прихованих метрик.

Видалені метрики більше не публікуються і не можуть бути використані.

Показ прихованих метрик

Як описано вище, адміністратори можуть увімкнути приховані метрики через прапорець командного рядка конкретного бінарного файлу. Це запасний варіант для адміністраторів, які пропустили міграцію з метрик, що стали застарілими в останньому випуску.

Прапорець show-hidden-metrics-for-version приймає версію, для якої потрібно показати метрики, що стали застарілими в цьому випуску. Версія зазначається як x.y, де x — мажорна версія, y — мінорна версія. Патч-версія не потрібна: хоча метрика може стати застарілою в патч-випуску, політика застарівання метрик працює на рівні мінорних випусків.

Прапорець може приймати лише попередню мінорну версію. Якщо ви хочете показати всі метрики, приховані в попередньому випуску, встановіть прапорець show-hidden-metrics-for-version на попередню версію. Використання надто старої версії не дозволено, оскільки це порушує політику застарівання метрик.

Наприклад, припустімо, що метрика A стала застарілою в 1.29. Версія, в якій метрика A стає прихованою, залежить від її рівня стабільності:

  • Якщо метрика A є ALPHA, вона може бути прихована в 1.29.
  • Якщо метрика A є BETA, вона буде прихована не раніше ніж у 1.30. Якщо ви оновлюєтесь до 1.30 і все ще потребуєте A, ви повинні використовувати прапорець командного рядка --show-hidden-metrics-for-version=1.29.
  • Якщо метрика A є STABLE, вона буде прихована не раніше ніж у 1.32. Якщо ви оновлюєтесь до 1.32 і все ще потребуєте A, ви повинні використовувати прапорець командного рядка --show-hidden-metrics-for-version=1.31.

Метрики компонентів

Метрики kube-controller-manager

Метрики менеджера контролерів дають важливе уявлення про продуктивність і справність менеджера контролерів. До цих метрик належать поширені метрики середовища виконання мови Go, такі як кількість go_routine, та специфічні для контролерів метрики, такі як затримки запитів до etcd або затримки API Cloudprovider (AWS, GCE, OpenStack), які можна використовувати для оцінки справності кластера.

Починаючи з Kubernetes 1.7, для операцій зі сховищем у GCE, AWS, Vsphere та OpenStack доступні докладні метрики Cloudprovider. Ці метрики можна використовувати для моніторингу справності операцій із постійними томами.

Наприклад, для GCE ці метрики називаються:

cloudprovider_gce_api_request_duration_seconds { request = "instance_list"}
cloudprovider_gce_api_request_duration_seconds { request = "disk_insert"}
cloudprovider_gce_api_request_duration_seconds { request = "disk_delete"}
cloudprovider_gce_api_request_duration_seconds { request = "attach_disk"}
cloudprovider_gce_api_request_duration_seconds { request = "detach_disk"}
cloudprovider_gce_api_request_duration_seconds { request = "list_disk"}

Метрики kube-scheduler

СТАН ФУНКЦІОНАЛУ: Beta since Kubernetes v1.21

Планувальник надає необовʼязкові метрики, які повідомляють про запитані ресурси та бажані обмеження всіх запущених Podʼів. Ці метрики можна використовувати для побудови dashboards планування місткості, оцінки поточних або історичних обмежень планування, швидкого виявлення робочих навантажень, які не можуть бути заплановані через брак ресурсів, і порівняння фактичного використання із запитом Podʼа.

kube-scheduler визначає запити та обмеження ресурсів, налаштовані для кожного Podʼа; коли запит або обмеження не дорівнює нулю, kube-scheduler повідомляє часовий ряд метрик. Часовий ряд має такі мітки:

  • простір імен
  • назва Podʼа
  • вузол, на який заплановано Pod, або порожній рядок, якщо його ще не заплановано
  • пріоритет
  • призначений планувальник для цього Podʼа
  • назва ресурсу (наприклад, cpu)
  • одиниця ресурсу, якщо відома (наприклад, cores)

Щойно Pod завершує роботу (має restartPolicy зі значенням Never або OnFailure і перебуває у фазі Succeeded або Failed, або його видалено, і всі контейнери перебувають у стані завершення), часовий ряд більше не повідомляється, оскільки тепер планувальник може запланувати запуск інших Podʼів. Ці дві метрики називаються kube_pod_resource_request та kube_pod_resource_limit.

Метрики доступні через HTTP-точку доступу /metrics/resources. Для них потрібна авторизація для точки доступу /metrics/resources, яку зазвичай надає ClusterRole з дієсловом get для URL /metrics/resources, що не є ресурсом.

У Kubernetes 1.21 потрібно використовувати прапорець --show-hidden-metrics-for-version=1.20, щоб показати ці альфа-метрики.

Метрики kubelet Pressure Stall Information (PSI)

СТАН ФУНКЦІОНАЛУ: GA since Kubernetes v1.36
More information about this feature

This is a stable feature in Kubernetes, and has been since version v1.36. It was first available in the v1.33 release. You can no longer disable or opt out of this feature or behavior (it is locked); if you explicitly set a value for the associated feature gate KubeletPSI, Kubernetes ignores it but does not report any error.

Якщо в ядрі ввімкнено PSI (версія 4.20 або новіша), kubelet збирає Pressure Stall Information (PSI) щодо використання CPU, памʼяті та вводу-виводу. Інформація збирається на рівні вузла, Podʼа та контейнера.

Метрики Prometheus: надаються через точку доступу /metrics/cadvisor у вигляді кумулятивних лічильників (totals), що відображають загальний час затримки в секундах. Метрики доступні через цю точку доступу під такими назвами:

container_pressure_cpu_stalled_seconds_total
container_pressure_cpu_waiting_seconds_total
container_pressure_memory_stalled_seconds_total
container_pressure_memory_waiting_seconds_total
container_pressure_io_stalled_seconds_total
container_pressure_io_waiting_seconds_total

Summary API: надається через точку доступу /stats/summary, повертаючи як кумулятивні totals, так і ковзні середні (avg10, avg60, avg300) у форматі JSON. Ці середні значення показують відсоток часу, протягом якого завдання були затримані на ресурсі за відповідні інтервали 10 секунд, 60 секунд і 5 хвилин.

Ці метрики також нативно експортуються через відповідний файл вузла в /proc/pressure/ — cpu, memory та io — у такому форматі:

some avg10=0.00 avg60=0.00 avg300=0.00 total=0
full avg10=0.00 avg60=0.00 avg300=0.00 total=0

Як можна інтерпретувати ці метрики разом? Візьмемо, наприклад, такий запит до Summary API:
kubectl get --raw "/api/v1/nodes/$(kubectl get nodes -o jsonpath='{.items[0].metadata.name}')/proxy/stats/summary" | jq '.pods[].containers[] | select(.name=="<CONTAINER_NAME>") | {name, cpu: .cpu.psi, memory: .memory.psi, io: .io.psi}'. Це повертає інформацію у форматі JSON, як показано нижче.

{
  "name": "<CONTAINER_NAME>",
  "cpu": {
    "full": {
      "total": 0,
      "avg10": 0,
      "avg60": 0,
      "avg300": 0
    },
    "some": {
      "total": 35232438,
      "avg10": 0.74,
      "avg60": 0.52,
      "avg300": 0.21,
    },
  },
  "memory": {
    "full": {
      "total": 539105,
      "avg10": 0,
      "avg60": 0,
      "avg300": 0
    },
    "some": {
      "total": 658164,
      "avg10": 0.01,
      "avg60": 0.01,
      "avg300": 0.00,
    },
    }
  },
  "io": {
    "full": {
      "total": 33190987,
      "avg10": 0.31,
      "avg60": 0.22,
      "avg300": 0.05,
    },
    "some": {
      "total": 40809937,
      "avg10": 0.52,
      "avg60": 0.45,
      "avg300": 0.12,
    }
  }
}

Ось простий сценарій сплеску. Значення avg10 для cpu.some, що дорівнює 0.74, означає, що за останні 10 секунд принаймні одне завдання в цьому контейнері було затримано на CPU протягом 0.74% часу (0.0074 секунди або 74 мілісекунди). Оскільки avg10 (0.74) значно перевищує avg300 (0.21) для того самого ресурсу, це свідчить про недавній сплеск конкуренції за ресурси, а не про тривале вузьке місце. Якщо постійно стежити за метриками й avg300 також зростає, можна діагностувати серйознішу, тривалу проблему!

Крім того, зверніть увагу, що в цьому прикладі cpu.some показує тиск, тоді як cpu.full залишається на рівні 0.00. Це означає, що хоча деякі процеси були затримані в очікуванні часу CPU, контейнер загалом продовжував роботу. Ненульове значення full означало б, що всі завдання, які не простоюють, були затримані одночасно, а це набагато серйозніша проблема. Хоча значення total 35232438 не так зручно читати людині, воно показує кумулятивний час затримки в мікросекундах, що дозволяє виявляти сплески затримки, які інакше можуть не проявитися в середніх значеннях. Такі значення також корисні для систем моніторингу, таких як Prometheus, для точного обчислення темпів зростання за певні часові вікна. І наостанок: високий тиск на I/O разом із низьким тиском на памʼять може означати, що застосунок очікує на пропускну здатність диска, а не страждає від браку доступної оперативної памʼяті. Вузол не перевантажений за памʼяттю, тому варто окремо дослідити споживання диска.

Метрики PSI дають надійніший спосіб моніторингу конкуренції за ресурси в реальному часі на всіх рівнях для кожної cgroup, відкриваючи можливість динамічно обробляти робочі навантаження в усій системі. Докладніше про метрики PSI читайте в Understand PSI Metrics.

Вимоги

Pressure Stall Information вимагає:

Вимкнення метрик

Ви можете явно вимкнути метрики за допомогою прапорця командного рядка --disabled-metrics. Це може знадобитися, наприклад, якщо метрика спричиняє проблеми з продуктивністю. Вхідні дані — це список вимкнених метрик (тобто --disabled-metrics=metric1,metric2).

Обмеження кардинальності метрик

Метрики з необмеженими вимірами можуть спричиняти проблеми з памʼяттю в компонентах, які вони інструментують. Щоб обмежити використання ресурсів, ви можете використовувати параметр командного рядка --allow-metric-labels, щоб динамічно налаштувати список дозволених значень міток для метрики.

На стадії альфа цей прапорець може приймати лише серію зіставлень як список дозволених міток метрики. Кожне зіставлення має формат <metric_name>,<label_name>=<allowed_labels>, де <allowed_labels> — розділений комами список допустимих назв міток.

Загальний формат виглядає так:

--allow-metric-labels <metric_name>,<label_name>='<allow_value1>, <allow_value2>...', <metric_name2>,<label_name>='<allow_value1>, <allow_value2>...', ...

Ось приклад:

--allow-metric-labels number_count_metric,odd_number='1,3,5', number_count_metric,even_number='2,4,6', date_gauge_metric,weekend='Saturday,Sunday'

Окрім командного рядка, це можна зробити й у конфігураційному файлі. Шлях до цього файлу можна вказати за допомогою аргументу командного рядка --allow-metric-labels-manifest для компонента. Ось приклад вмісту такого конфігураційного файлу:

"metric1,label2": "v1,v2,v3"
"metric2,label1": "v1,v2,v3"

Крім того, мета-метрика cardinality_enforcement_unexpected_categorizations_total записує кількість неочікуваних категоризацій під час обмеження кардинальності, тобто щоразу, коли трапляється значення мітки, не дозволене обмеженнями списку дозволених значень.

Що далі