Библиотека предназначена для удобного вывода сообщений в привязке к их "уровням важности"
Функционал logos не повторяет полностью log4j, а, скорее, берет из него какие-то аспекты поведения.
Каждый лог имеет собственное имя, по которому он может быть идентифицирован. Имена логов глобально видимы и любой из них может быть получен по имени лога.
Для того, чтобы начать логирование, требуется вызвать метод ПолучитьЛог
модуля Логирование
Лог = Логирование.ПолучитьЛог("oscript.app.messages");
Принята следующая схема именования логов:
область.класс_приложения.имя_лога
- Область - это произвольное имя, определяющее некую совокупность возможных логов. Часто, в качестве области используется имя поставщика приложения, либо имя набора библиотек. Для всех пакетов, входящих в oscript-library используется имя области "oscript". Приложения, создаваемые, например, в рамках гипотетического проекта "Аврора" могут использовать область "aurora".
- Класс_приложения - это разделитель на тип модуля - библиотека, или приложение. Например, библиотечный пакет "cmdline" использует класс
lib
, а консольное приложение "gitsync" - класс 'app' - Имя_лога - это, собственно, идентификатор журнала.
В отличие от log4j логи в logos не являются иерархическими, но в перспективе могут стать таковыми.
Существует 5 уровней важности сообщений:
- Отладка
- Информация
- Предупреждение
- Ошибка
- Критичная ошибка
Для каждого из уровней logos предоставляет отдельный метод, который выводит сообщение с данным уровнем важности. В процессе эксплуатации приложения для каждого из логов можно устанавливать уровень выводимых сообщений. Например, если установлен уровень "Предупреждение", то выводиться будут только предупреждения или более важные сообщения (Ошибка, КритичнаяОшибка)
Лог.УстановитьУровень(УровниЛога.Отладка) // выводить все, в т.ч. отладочные сообщения
По умолчанию установлен уровень "Информация".
Лог = Логирование.ПолучитьЛог("oscript.test.levels");
Лог.УстановитьУровень(УровниЛога.Ошибка);
Лог.Отладка("Переменная А = 7");
Лог.Информация("Переменная А = 7");
Лог.Ошибка("Неверно указан путь к файлу!");
ПеремА = "А";
Лог.Отладка("Переменная %1 = %2", ПеремА, 7);
Лог.Информация("Переменная %1 = %2", ПеремА, 7);
Лог.Ошибка("Неверно указан путь к файлу %1!", ПеремА);
Приложение выводит сообщения в лог, а сам лог может выводиться в произвольное место. За конкретную реализацию вывода отвечает Способ вывода. В Log4j это называется appender.
В составе logos поставляется 2 способа вывода - в консоль и в файл. Причем, способы вывода - это список, т.е. лог может писаться в несколько мест одновременно.
ФайлЖурнала = Новый ВыводЛогаВФайл
ФайлЖурнала.ОткрытьФайл("/var/log/oscript.test.log");
Лог.ДобавитьСпособВывода(ФайлЖурнала);
Лог.Информация("Это строка лога");
Лог.Закрыть(); // при включении логирования в файл рекомендуется закрывать лог.
При создании лога в него автоматически будет добавлен способ вывода ВыводЛогаВКонсоль. Однако, если вручную в лог будет добавлен другой способ вывода, то "автоспособ" будет удален. Иными словами, пример кода выше будет писать только в файл, т.к. консольный вывод при ручном добавлении способа вывода будет отключен.
В связи с вводом API v2
для форматирования сообщений, появилась возможность передавать в объект форматирования дополнительные поля.
Для создания лога с дополнительными полями необходимо использовать следующие функции:
-
Поля
- принимает на вход поля и значения, где первый параметр имя поля, а второй значение поля и так до 4 полей -
ПоляИз
- принимает на соответствие или структуру полей для лога
Важно! Надо помнить, что при вызове этих функций создается объект класса
Лог
, вне модуляЛогирование
. И он не меняетЛог
с таким же именем и живет только внутри вызванных методов
Пример использования:
ЛогБиблиотеки = Логирование.ПолучитьЛог("oscript.lib.test");
ПоляЛога = Новый Структура("ДопПоле, ДопПоле2", "ДопПоле", "ДопПоле2");
Лог = ЛогБиблиотеки.ПоляИз(ПоляЛога);
Лог.Отладка("Это отладка");
// ИЛИ
ЛогБиблиотеки.Поля("ДатаВремя", ТекущаяДата(), "ПростоПоле", "ПростоПоле").Информация("Привет");
За форматирование выводимых сообщений отвечает Раскладка. Раскладка по умолчанию форматирует сообщения следующим образом:
УРОВЕНЬСООБЩЕНИЯ - ТекстСообщения
Раскладка - это класс, реализующий метод Форматировать(Знач Уровень, Знач Сообщение). Установить собственную раскладку можно методом "УстановитьРаскладку".
- API v1
Функция Форматировать(Знач Уровень, Знач Сообщение) Экспорт Возврат СтрШаблон("%1: %2 - %3", ТекущаяДата(), УровниЛога.НаименованиеУровня(Уровень), Сообщение); КонецФункции
- API v2
Функция ПолучитьФорматированноеСообщение(Знач СобытиеЛога) Экспорт // СобытиеЛога - Объект с методами // * ПолучитьУровень() - Число - уровень лога // * ПолучитьСообщение() - Строка - текст сообщения // * ПолучитьИмяЛога() - Строка - имя лога // * ПолучитьВремяСобытия() - Число - Универсальная дата-время события в миллисекундах // * ПолучитьДополнительныеПоля() - Соответствие - дополнительные поля события ФорматированноеСообщение = СобытиеЛога.ПолучитьСообщение(); Возврат ФорматированноеСообщение; КонецФункции
Лог = Логирование.ПолучитьЛог("oscript.lib.test"); Лог.УстановитьРаскладку(ЭтотОбъект);
В приведенной раскладке в сообщение помимо уровня и текста будет добавлено текущая дата.
Предусмотрено изменение параметров логирования через специальный файл конфигурации, либо через переменную окружения. Независимо от способа задания настроек, формат настроек остается одинаковым.
Файл конфигурации должен лежать рядом со стартовым скриптом (см. метод СтартовыйСценарий()) и называться logos.cfg. Кроме того, настройки можно задать через переменную окружения LOGOS_CONFIG. Из-за неудобства ввода перевода строк в переменных окружения - в данном случае настройки надо разделять не переводом строк, а точкой-с-запятой. Формат настроек идентичен, независимо от способа задания конфига - в файле или в переменной.
Следует учитывать, что переменная окружения имеет приоритет над файлом, и если задана она, то настройки берутся из нее, файл игнорируется.
set LOGOS_CONFIG=logger.oscript.lib.commands=DEBUG;logger.oscript.lib.cmdline=DEBUG
Если задать настройку:
set LOGOS_CONFIG=logger.oscript.lib.query=DEBUG;
И получить вот такие логи:
ЛогОбновления = Логирование.ПолучитьЛог("oscript.lib.query.update");
ЛогВыборки = Логирование.ПолучитьЛог("oscript.lib.query.select");
То оба лога унаследуют настройки oscript.lib.query
Каждая настройка задается в виде пары ключ=значение
. Причем, ключ является составным. Компоненты ключа разделены точками.
Первым компонентом ключа идет класс настройки. Предусмотрены 2 класса - logger и appender. Первый отвечает за настройку конкретного журнала. Второй - за настройку способов вывода, используемых журналами.
logger.имя_журнала=Уровень[,СпособыВывода]
- имя_журнала - это имя лога, как он описан в вызове метода
Логирование.ПолучитьЛог();
, например, oscript.lib.v8runner. - СпособыВывода - это список произвольных имен способов вывода, которые привязаны к журналу. Конкретная настройка каждого из заявленных способов вывода выполняется в классе настроек appender.
Например, журнал oscript.lib.v8runner может быть настроен следующим образом:
logger.oscript.lib.v8runner=DEBUG, v8rdebug, console
В классе настроек logger возможно указать специализированное имя rootLogger
. Настройки корневого логгера влияют на все прочие журналы. Это удобно, если вы хотите просто включить отладку по всем журналам или все журналы направить в файл.
Например:
logger.rootLogger=DEBUG
Обычная установка через командную строку, например, используя отдельный командный файл
set LOGOS_CONFIG=logger.rootLogger=DEBUG
или
set LOGOS_LEVEL=DEBUG
Установка и немедленный запуск команды-скрипта через командную строку без создания командного файла
(LOGOS_LEVEL=DEBUG) && (любая команда)
или
(set LOGOS_CONFIG=logger.rootLogger=DEBUG) && (любая команда)
Например:
(LOGOS_LEVEL=DEBUG) && (vanessa-runner help)
или
(set LOGOS_CONFIG=logger.rootLogger=DEBUG) && (vanessa-runner help)
logger.oscript.lib.v8runner=DEBUG, v8rdebug, console
appender.v8rdebug=ВыводЛогаВФайл
appender.v8rdebug.level=DEBUG
appender.v8rdebug.file=/var/log/v8runner-debug.log
appender.console=ВыводЛогаВКонсоль
appender.console.level=INFO
В приведенном примере для лога oscript.lib.v8runner установлен уровень Отладка и заявлено 2 способа вывода. Они названы v8rdebug и console (названия произвольные, т.е. здесь мы "объявляем" эти названия, придумав их самостоятельно, а ниже - по ним обращаемся к настройке логгера).
Далее, в конфигурации указаны настройки заявленных способов вывода (аппендеров). Обязательным параметром является класс (тип языка), реализующий способ вывода. В данном примере указаны типы ВыводЛогаВФайл и ВыводЛогаВКонсоль.
// формат указания класса реализации
appender.имя_способа_вывода=Класс
Для каждого класса можно установить собственный уровень вывода сообщений. В этом случае перед выводом сообщения система логирования будет фильтровать сообщения.
Для установки нужно заполнить свойство level
. Возможные значения для свойства - DEFAULT
, DEBUG
, INFO
, WARN
, ERROR
, CRITICALERROR
, DISABLE
Например, в указанном выше примере для способа вывода console
(который мы сами так назвали выше) установлен уровень вывода сообщений информации и более серьезных. Отладочные сообщения в эту консоль не выводятся.
А вот для способа вывода v8rdebug
(который мы тоже сами так назвали выше) установлен уровень вывода сообщений Отладка
. Т.е. этим способом вывода будут выводиться все сообщения!
appender.v8rdebug.level=DEBUG
appender.console.level=INFO
Для каждого класса могут потребоваться какие-то свои параметры. Например, класс ВыводЛогаВФайл требует задания свойства file. Свойства способа вывода задаются через точку от имени способа вывода:
// формат указания свойства
appender.имя_способа_вывода.свойство=значение
Для этого нужно включить уровень логирования DEBUG для всех логгеров приложения
logger.rootLogger=DEBUG
set LOGOS_CONFIG=logger.rootLogger=DEBUG
Обратите внимание, значение переменной LOGOS_CONFIG это то же самое, что строки файла logos.cfg. Строки отделяются друг-от-друга точкой с запятой.
Переменная LOGOS_LEVEL является сокращенным способом доступа к настройке logger.rootLogger, для удобства
set LOGOS_LEVEL=DEBUG
Дано: приложение SOME_APP, которое общается по сети с помощью библиотеки connector.
Пусть: известно, что библиотека connector пишет в лог с именем oscript.lib.connector
logger.oscript.lib.connector=INFO, foo
appender.foo=ВыводЛогаВФайл
appender.foo.file=/var/log/http.log
Обратите внимание, в первой строке объявлено, что логгер oscript.lib.connector связан с аппендером foo (название придумали сами, прямо тут). Далее, во второй строке указывается, что аппендер foo (который мы придумали) является классом ВыводЛогаВФайл
и пишет в файл /var/log/http.log
При использовании переменной окружения мы должны просто повторить строки файла конфигурации, разделив их точкой-с-запятой.
set LOGOS_CONFIG=logger.oscript.lib.connector=INFO, foo;appender.foo=ВыводЛогаВФайл;appender.foo.file=/var/log/http.log
Таким образом, если у нас есть приложение, настройки логирования которого надо переопределить, мы должны создать рядом со стартовым скриптом приложения файл logos.cfg, либо (если не знаем где лежит этот файл или нет к нему доступа) создать переменную окружения LOGOS_CONFIG, написав в ней строки конфигурирования, разделив их точкой-с-запятой.