Что такое пакет `slog` в Go и какие проблемы он решает?

Ответ

slog — это пакет для структурированного логирования, который был добавлен в стандартную библиотеку Go начиная с версии 1.21. Он предоставляет более мощный, гибкий и производительный механизм логирования по сравнению со старым пакетом log.

Основная проблема, которую решает slog, — это создание логов, которые легко читать не только человеку, но и машине (системам сбора и анализа логов, таким как ELK Stack, Grafana Loki, Datadog).

Ключевые особенности и преимущества:

  • Уровни логирования: Встроенная поддержка уровней (Debug, Info, Warn, Error), что позволяет гибко настраивать детализацию логов для разных окружений.
  • Структурированный вывод: Логи по умолчанию выводятся в виде пар ключ=значение или в формате JSON. Это упрощает их парсинг, фильтрацию и индексацию.
  • Контекстная информация: Возможность добавлять атрибуты к логгеру, которые будут присутствовать во всех последующих сообщениях. Отлично интегрируется с context.Context.
  • Высокая производительность: slog разработан с упором на минимизацию аллокаций и накладных расходов, что делает его одним из самых быстрых решений для логирования в Go.
  • Гибкая настройка: Позволяет легко заменять обработчик (Handler) для изменения формата вывода (например, JSON, logfmt) или направления (stdout, файл, сетевое хранилище).

Пример использования:

package main

import (
    "log/slog"
    "os"
)

func main() {
    // Создаем логгер с обработчиком, который пишет JSON в stdout
    logger := slog.New(slog.NewJSONHandler(os.Stdout, nil))

    // Логируем событие с дополнительными атрибутами
    logger.Info("user logged in",
        slog.Int("user_id", 12345),
        slog.String("ip_address", "192.168.1.101"),
    )
}

Пример вывода (JSON):

{"time":"2023-10-27T10:00:00.000Z","level":"INFO","msg":"user logged in","user_id":12345,"ip_address":"192.168.1.101"}

В целом, slog становится стандартом для логирования в современных Go-приложениях, заменяя сторонние библиотеки во многих проектах.

Ответ 18+ 🔞

Так, слушай, вот есть у тебя в Го этот старый log пакет, ну, который как дедушка в тапочках — простой, предсказуемый, но нихуя не умеет, кроме как строчку в консоль плюнуть. Так вот, начиная с версии 1.21, в стандартную библиотеку завезли нового игрока — slog. И это, блядь, не просто апгрейд, это как пересесть с запорожца на что-то с турбиной.

В чём, сука, соль?

Основная его фишка — структурированные логи. Раньше ты писал log.Printf("User %d logged in from %s", id, ip), и потом какой-нибудь бедолага-админ или система мониторинга должна была эту строку регулярками рвать на части, как последнюю курицу. Теперь же логи — это сразу готовые пары ключ=значение или, что ещё круче, JSON. Машинам это овердохуища как удобно парсить.

Что он умеет, этот красавчик?

  • Уровни, наконец-то! Debug, Info, Warn, Error. Можно на проде инфо и выше гнать, а на тестовом стенде включить дебаг и увидеть всю подноготную. Элементарно, Ватсон!
  • Контекст в дело. Можно прикрутить к логгеру общие атрибуты (типа request_id), и они автоматом будут в каждом сообщении. Или навесить их на context.Context — идеально для HTTP-обработчиков.
  • Быстрый, блядь. Его делали с оглядкой на производительность, минимум аллокаций, чтоб не тормозил твой хайлоад-сервис.
  • Гибкий до пизды. Хочешь JSON в stdout — пожалуйста. Хочешь текстовый формат в файл — без проблем. Меняешь один обработчик (Handler) — и всё, логи летят в другую сторону другим форматом.

Смотри, как это выглядит на практике:

package main

import (
    "log/slog"
    "os"
)

func main() {
    // Создаём логгер, который будет вываливать JSON в консоль
    logger := slog.New(slog.NewJSONHandler(os.Stdout, nil))

    // И теперь логируем событие с доп. инфой
    logger.Info("user logged in",
        slog.Int("user_id", 12345),
        slog.String("ip_address", "192.168.1.101"),
    )
}

И на выходе получится такая красота:

{"time":"2023-10-27T10:00:00.000Z","level":"INFO","msg":"user logged in","user_id":12345,"ip_address":"192.168.1.101"}

Любая система сбора логов схватит это, разжуёт и положит в нужную табличку без единого регулярного выражения. Красота, ёпта!

Итог: slog — это теперь де-факто стандарт для адекватного логирования в Го. Если пишешь что-то новое — бери его и не мучайся. Если поддерживаешь легаси — есть шанс потихоньку мигрировать с кучи сторонних библиотек на что-то одно, родное и охуенно быстрое. В общем, вещь!