ELK в Kubernetes: Elasticsearch, APM Server и Kibana
Published: 2026-03-17
ELK-стек используется для двух задач: поиска по логам и мониторинга производительности приложений (APM). Логи приходят от Vector, APM-трейсы — от агента Elastic APM в .NET-приложениях. Kibana объединяет и то и другое.
Развёртывание через FluxCD
Три HelmRelease из Elastic Helm-репозитория:
yaml# elasticsearch
apiVersion: helm.toolkit.fluxcd.io/v2
kind: HelmRelease
metadata:
name: elasticsearch
namespace: elk
spec:
chart:
spec:
chart: elasticsearch
version: "8.x"
sourceRef:
kind: HelmRepository
name: elastic
values:
replicas: 1
minimumMasterNodes: 1
esJavaOpts: "-Xmx2g -Xms2g"
resources:
requests:
cpu: 500m
memory: 3Gi
limits:
cpu: 2000m
memory: 4Gi
volumeClaimTemplate:
resources:
requests:
storage: 200Gi
storageClassName: local-path
persistence:
enabled: true
esJavaOpts — размер JVM heap. Правило: heap — половина лимита памяти контейнера. При лимите 4Gi значение -Xmx2g оставляет 2 ГБ под page cache ОС, который использует Lucene.
yaml# kibana
apiVersion: helm.toolkit.fluxcd.io/v2
kind: HelmRelease
metadata:
name: kibana
namespace: elk
spec:
chart:
spec:
chart: kibana
version: "8.x"
sourceRef:
kind: HelmRepository
name: elastic
values:
elasticsearchHosts: "http://elasticsearch-master.elk.svc.cluster.local:9200"
resources:
requests:
cpu: 200m
memory: 512Mi
limits:
cpu: 1000m
memory: 1Gi
yaml# apm-server
apiVersion: helm.toolkit.fluxcd.io/v2
kind: HelmRelease
metadata:
name: apm-server
namespace: elk
spec:
chart:
spec:
chart: apm-server
version: "8.x"
sourceRef:
kind: HelmRepository
name: elastic
values:
apmConfig:
apm-server.yml: |
apm-server:
host: "0.0.0.0:8200"
output.elasticsearch:
hosts: ["http://elasticsearch-master.elk.svc.cluster.local:9200"]
APM-агент в .NET
xml<PackageReference Include="Elastic.Apm.NetCoreAll" Version="1.*" />
Одна строка в Program.cs:
csharpbuilder.Services.AddAllElasticApm();
Конфигурация через переменные окружения:
yamlenv:
- name: ELASTIC_APM_SERVER_URL
value: "http://apm-server.elk.svc.cluster.local:8200"
- name: ELASTIC_APM_SERVICE_NAME
value: "my-service"
- name: ELASTIC_APM_ENVIRONMENT
value: "prod"
- name: ELASTIC_APM_LOG_LEVEL
value: "Warning"
- name: ELASTIC_APM_TRANSACTION_SAMPLE_RATE
value: "0.1" # сэмплирование 10% — снижает объём APM-данных
Агент автоматически инструментирует запросы ASP.NET Core, Entity Framework и HttpClient.
Собственные APM-спаны
csharpvar transaction = Agent.Tracer.CurrentTransaction;
using var span = transaction.StartSpan("ProcessPayment", "payment");
span.SetLabel("order_id", orderId.ToString());
try {
await _paymentService.ChargeAsync(orderId);
span.Outcome = Outcome.Success;
} catch (Exception ex) {
span.CaptureException(ex);
throw;
}
Index Lifecycle Management
jsonPUT _ilm/policy/k8s-logs-policy
{
"policy": {
"phases": {
"hot": {
"actions": {
"rollover": {
"max_size": "20gb",
"max_age": "1d"
}
}
},
"warm": {
"min_age": "7d",
"actions": {
"forcemerge": { "max_num_segments": 1 },
"shrink": { "number_of_shards": 1 }
}
},
"delete": {
"min_age": "30d",
"actions": { "delete": {} }
}
}
}
}
Данные старше 30 дней удаляются автоматически. В warm-фазе сегменты объединяются (forcemerge) для экономии диска.
Полезные запросы в Kibana
# Все ошибки за последний час
kubernetes.namespace: "app" AND log.level: ERROR
# Медленные HTTP-запросы (APM)
transaction.duration.us > 5000000
# Конкретный под
kubernetes.pod.name: "my-service-abc123"
# Exception
error.exception.message: *NullReference*
KQL (Kibana Query Language) читается лучше Lucene и поддерживает autocomplete в Discover.
APM → Service Map в Kibana
С APM в нескольких сервисах Kibana строит Service Map:
- Какие сервисы вызывают какие
- Средняя задержка по каждому ребру
- Частота ошибок на сервис
Это карта распределённой трассировки, которую APM строит автоматически из спанов.
Диагностика
APM-данные не появляются: проверьте логи APM Server и доступность ELASTIC_APM_SERVER_URL из пода.
OOM: уменьшите heap в esJavaOpts, если другие рабочие нагрузки конкурируют за память. Heap не должен превышать 50% лимита контейнера.
Индексы не создаются: Vector пишет в vector-YYYY-MM-DD. Проверьте ошибки sink в Vector.