Периодически возникает потребность анализировать большие объемы логов в поисках чего-то интересного. Причем ситуация усложняется тем, что в руки разработчика может попасть набор логов сразу с нескольких серверов кластера и приходится собирать цепочку, которая, например прошла с клиента до Worker. В идеале хотелось бы делать всё это в одно действие, сразу по всем необходимым файлам.
Ограничение – речь пойдёт про достаточно новые версии RX 4.*, поскольку идеально подходит для наших JSON логов.
Используется стек от Grafana. На сервере устанавливается Promtail, который будет перехватывать изменения в логах и отправлять в БД Loki. Grafana уже предоставляет доступ к данным, позволяет писать запросы и получать данные.
Приятная особенность– весь набор приложений отлично работает как под Windows, так и под Linux.
Суммарное потребление ресурсов:
Процесс |
Рабочий набор (память) |
Место на диске |
promtail-windows-amd64.exe |
45М |
80М |
loki-windows-amd64.exe |
100М |
60М |
grafana-server.exe |
50М |
230М |
ИТОГО |
~200М RAM |
~ 1Г HDD/SSD |
Для оптимизации накладных расходов на стенд (DEV / TEST) достаточно установить Promtail, который будет отправлять логи на единый сервер Loki (например на машине разработчика), Grafana так же установлена в одном экземпляре:
А можно на каждом стенде размещать полный комплект, это уже зависит от привычек и удобства.
Скачиваем с https://github.com/grafana/loki/releases файлы loki-windows-amd64.exe.zip, promtail-windows-amd64.exe.zip (в случае с Linux смотрите документацию на сайте).
Скачиваем с https://grafana.com/grafana/download?platform=windows , Edition – OSS, Standalone Windows Binaries, файл .zip
Распаковать всё в каталог С:\LOKI. Итоговый результат после всех настроек будет выглядеть так:
Документация: https://grafana.com/docs/loki/latest/
Пример конфига: https://raw.githubusercontent.com/grafana/loki/main/cmd/loki/loki-local-config.yaml
Требуется создать конфиг-файл C:\LOKI\loki-config.yaml:
auth_enabled: false
server:
http_listen_port: 3100
grpc_listen_port: 9096
schema_config:
configs:
- from: 2021-08-01
store: tsdb
object_store: filesystem
schema: v12
index:
prefix: index_
period: 24h
limits_config:
enforce_metric_name: false
reject_old_samples: true
reject_old_samples_max_age: 30d
max_query_length: 0h
max_query_parallelism: 32
ingestion_rate_strategy: local
ingestion_rate_mb: 1000
ingestion_burst_size_mb: 1000
max_streams_per_user: 0
max_global_streams_per_user: 0
querier:
max_concurrent: 2048
frontend:
max_outstanding_per_tenant: 4096
compress_responses: true
common:
instance_addr: 127.0.0.1
path_prefix: c:\loki\db
storage:
filesystem:
chunks_directory: c:\loki\db\chunks
rules_directory: c:\loki\db\rules
replication_factor: 1
ring:
kvstore:
store: inmemory
query_range:
split_queries_by_interval: 0
parallelise_shardable_queries: false
results_cache:
cache:
embedded_cache:
enabled: true
max_size_mb: 1000
ruler:
alertmanager_url: http://localhost:9093
analytics:
reporting_enabled: false
Что здесь настроено:
• авторизации нет – локальное использование, не production
• путь до файлов БД - path_prefix: С:\LOKI\db
• блок limits_config – подобранный за время использования набор настроек, которые снимают ограничения при импорте больших пачек логов и для больших аналитических запросов, более подробно читайте в документации.
• Записи старше 30 дней отбрасываются (reject_old_samples_max_age)
Команда запуска для командной строки (абсолютные пути, чтобы запускать откуда угодно):
C:\LOKI\loki-windows-amd64.exe --config.file=c:\LOKI\loki-config.yaml
Документация: https://grafana.com/docs/loki/latest/send-data/promtail/
Пример конфига: https://github.com/grafana/loki/blob/main/clients/cmd/promtail/promtail-local-config.yaml
Требуется создать конфиг-файл C:\LOKI\promtail-config.yaml:
server:
http_listen_port: 9080
grpc_listen_port: 0
positions:
filename: C:\LOKI\promtail-positions.yaml
clients:
- url: http://127.0.0.1:3100/loki/api/v1/push
scrape_configs:
- job_name: system
static_configs:
- targets:
- localhost
labels:
job: rx/DEMO
__path__: c:\inetpub\logs\*\*.log
pipeline_stages:
- json:
expressions:
logger: lg
level: l
msg: mt
pid: pid
timestamp: t
- labels:
logger:
level:
- timestamp:
source: timestamp
format: "2006-01-02 15:04:05.999-07:00"
На что обратить внимание:
• filename: C:\LOKI\promtail-positions.yaml – путь до файла, где хранится текущая позиция отслеживания по логам, если его удалить – логи будут перечитываться с нуля.
• url: http://127.0.0.1:3100/loki/api/v1/push - путь до сервера Loki, если он вынесен на компьютер разработчика – поменять на его IP адрес, убедиться, что брандмауэр разрешает внешние подключения на 3100 порт.
• job: rx/DEMO – метка, по которой можно различать стенды и проекты, для каждого экземпляра нужно прописать свою, чтобы можно было искать только в рамках проекта.
• Путь до логов: __path__ – пути до логов, в 4.2+ они по умолчанию складываются уже в один каталог, в примере указан поиск для двухуровневого хранения логов, если смотреть для новых версий по умолчанию, то параметр будет выглядеть так: __path__: C:\Storage\logs\*.log .
• блок pipeline_stages - реализует первичное извлечение необходимых данных
• блок expressions – из лога извлекаются поля для укрупнённой фильтрации и называются более удобными именами
• блок labels -дополнительные названия потоков для использования в конструкторе запроса. По ним строится первичный индекс, рекомендуется не увлекаться с их количеством
• format: "2006-01-02 15:04:05.999-07:00" – шаблон метки времени, анализируется время лога их файла и отправляется на сервер Loki в качестве метки времени (если этого не указать, меткой времени считается время поступления строки), очень удобно если требуется подгрузить для анализа исторические данные. Встречал вариант, когда время в логе было без часового пояса, в этом случае потребуется использовать format: "2006-01-02 15:04:05.999"
Формат этой строки использует строку формата из GO, все значения в строке не случайны. Допустимые значения: https://go.dev/src/time/format.go
Команда запуска (абсолютные пути, чтобы запускать откуда угодно):
C:\LOKI\promtail-windows-amd64.exe --config.file=c:\LOKI\promtail-config.yaml
Дополнительные настройки не требуются. После скачивания переименовать подкаталог в Grafana, чтобы не зависеть от версии.
Запускать - c:\LOKI\Grafana\bin\grafana-server.exe
При входе в первый раз потребуется предварительная настройка:
1. Зайти в Grafana: http://localhost:3000, вход – admin:admin, сразу предложит сменить пароль
2. Раздел Home -> Connections -> Data sources / Add data source. Выбрать Loki, указать URL: http://localhost:3100, Save & test
Создаём в каталоге командный файл start_all.cmd, чтобы запускать всё в один заход:
start C:\LOKI\loki-windows-amd64.exe --config.file=c:\LOKI\loki-config.yaml
start C:\LOKI\promtail-windows-amd64.exe --config.file=c:\LOKI\promtail-config.yaml
cd C:\LOKI\grafana\bin
grafana-server.exe
Работа с данными производится в разделе Home / Explore (аналог Discovery в Kibana).
Интерфейс выглядит следующим образом:
Еще есть удобный режим для просмотра Stacktrace. Требуется включить Prettify JSON, Escape newlines:
В итоге большие длинные строки корректно отформатируются:
Также здесь довольно удобный язык запросов. В последних версиях Grafana добавился построитель выражений, чаще всего хватает его. Обычное использование - в grep стиле собирается цепочка фильтров и немного форматируется вывод.
Примеры:
{job="rx/DEV1-AVP",level="Error"} |="5668+84"
Можно собрать цепочку из уточняющих фильтров:
{job="rx/DEV1-AVP"} |="durationMs" |="LogService"
Можно обработать строку как JSON и использовать данные для вычислений:
{job="rx/DEV1-AVP"} |="durationMs" |="LogService"| json duration="span.durationMs" | duration > 0
1. Парсим строку как JSON
2. В переменную duration помещаем значение из полученного результата
3. Полученную переменную используем в условии фильтрации
Можно отформатировать строку, чтобы там были только нужные поля:
{level="Debug"} |json | line_format "{{ .mt }}" |="AutoRegistration"
Причем для отобранных записей доступна ссылка «Show Context», которая позволит посмотреть (уже без красот и оформления) соседние записи в логе.
При достаточной фантазии из логов можно извлечь достаточно информации, чтобы быстро понять – что происходит, происходило и где ошибки. Ну и не забываем, что это Grafana, так что доступны все возможности по созданию dashboard и отправке алертов кучей методов.
Подробнее по языку запросов можно посмотреть у авторов: https://grafana.com/docs/loki/latest/logql/log_queries/
NSSM обеспечивает автозапуск приложений как службы в Windows и логирование stdOut, stdErr в файлы.
Потребуется скачать nssm.exe в c:\LOKI\nssm.exe и в cmd.exe с правами администратора запустить создание трёх служб:
nssm install _GRAFANA c:\LOKI\Grafana\bin\grafana-server.exe
nssm install _LOKI c:\LOKI\loki-windows-amd64.exe --config.file=C:\LOKI\loki-config.yaml
nssm install _PROMTAIL c:\LOKI\promtail-windows-amd64.exe --config.file=C:\LOKI\promtail-config.yaml
Но у всего вышеперечисленного есть «фатальный недостаток» (с). Это делал не я :)
Получается довольно лёгкий и быстрый аналог большому и толстому ELK стеку. Для анализа гигабайтов логов служит лучше, чем linux консоль, поскольку умеет индексировать данные, позволяет сохранять запросы, можно легко переформатировать вывод и выводить только нужные поля по достаточно сложным условиям.
Преимущества:
Недостатки:
На поодакшен пробовали использовать данный вариант? Насколько удобно в работе использовать данный инструмент?
Дмитрий, На проде обычно хватает места на полноценный ElasticSearch и сервер мониторинга. В моём случае скорей быстрая замена для grep с заранее сохранёнными запросами, для девстенда - чудесно.
Всё же магию, которую делает LogStash с логами - тут повторить крайне сложно
Авторизуйтесь, чтобы написать комментарий