Примеры логирования действий пользователя в коде

Примеры логирования действий пользователя в коде на языке программирования 1С:Предприятие. Примеры позволяют быстро разобраться в вопросе и использовать код в своих разработках

Базовое логирование через Сообщить

// Простое логирование действий пользователя в окно сообщений
Процедура ВыполнитьРасчет()

    Сообщить("Пользователь " + Пользователи.ТекущийПользователь().Имя + " начал расчет");
    
    Результат = 0;
    Для Сч = 1 По 10 Цикл
        Результат = Результат + Сч;
        Сообщить("Итерация " + Сч + ", промежуточный результат: " + Результат);
    КонецЦикла;
    
    Сообщить("Расчет завершен. Итог: " + Результат);
    
КонецПроцедуры

Логирование в регистр сведений

// Запись действий пользователя в регистр сведений "ЖурналДействий"
Процедура ЗаписатьДействиеВЛог(Действие, Комментарий = "")

    // Создаем набор записей регистра сведений
    НаборЗаписей = РегистрыСведений.ЖурналДействий.СоздатьНаборЗаписей();
    
    // Добавляем новую запись
    НоваяЗапись = НаборЗаписей.Добавить();
    НоваяЗапись.Период = ТекущаяДата();
    НоваяЗапись.Пользователь = Пользователи.ТекущийПользователь().Имя;
    НоваяЗапись.Действие = Действие;
    НоваяЗапись.Комментарий = Комментарий;
    НоваяЗапись.Сеанс = ИнформацияОбОкружении().ИдентификаторСеанса;
    
    // Записываем в регистр
    НаборЗаписей.Записать(Истина);
    
КонецПроцедуры

// Пример использования
Процедура ОтгрузитьТовары()

    ЗаписатьДействиеВЛог("Начало отгрузки", "Пользователь инициировал отгрузку товаров");
    
    // Код отгрузки товаров
    // ...
    
    ЗаписатьДействиеВЛог("Окончание отгрузки", "Отгрузка успешно завершена");
    
КонецПроцедуры

Логирование с контролем ошибок

// Логирование с обработкой исключительных ситуаций
Процедура ВыполнитьОперациюСЛогированием()

    ИмяПользователя = Пользователи.ТекущийПользователь().Имя;
    Идентификатор = Новый УникальныйИдентификатор;
    
    Попытка
        // Запись начала операции
        ЗаписатьЛогСобытия(Идентификатор, "НАЧАЛО", "Выполнение критической операции");
        
        // Потенциально опасный код
        Результат = 10 / 0; // Искусственная ошибка
        
        // Запись успешного завершения
        ЗаписатьЛогСобытия(Идентификатор, "УСПЕХ", "Операция выполнена успешно");
        
    Исключение
        // Запись ошибки с деталями
        ОписаниеОшибки = ПодробноеПредставлениеОшибки(ИнформацияОбОшибке());
        ЗаписатьЛогСобытия(Идентификатор, "ОШИБКА", "Ошибка: " + ОписаниеОшибки);
        
        // Повторная генерация исключения, если нужно
        ВызватьИсключение "Операция прервана: " + ОписаниеОшибки;
    КонецПопытки;
    
КонецПроцедуры

Функция ЗаписатьЛогСобытия(Идентификатор, Статус, Сообщение)

    Набор = РегистрыСведений.ЖурналДействий.СоздатьНаборЗаписей();
    Запись = Набор.Добавить();
    Запись.Период = ТекущаяДата();
    Запись.Идентификатор = Идентификатор;
    Запись.Пользователь = Пользователи.ТекущийПользователь().Имя;
    Запись.Статус = Статус;
    Запись.Сообщение = Сообщение;
    Набор.Записать(Истина);
    
    Возврат Истина;
    
КонецФункции

Логирование с замерами времени выполнения

// Измерение и логирование времени выполнения операций
Процедура ОперацияСЗамеромВремени()

    ИмяПользователя = Пользователи.ТекущийПользователь().Имя;
    Идентификатор = "Расчет_Зарплаты_" + Формат(ТекущаяДата(), "ДФ=yyyyMMddHHmmss");
    
    // Начало замера
    ВремяНачала = ТекущаяУниверсальнаяДатаВМиллисекундах();
    
    // Код операции
    Для Индекс = 1 По 1000 Цикл
        // Эмуляция длительной операции
        Ожидание = Новый Ожидание;
        Ожидание.МаксимальнаяЗадержка = 0.001;
        Ожидание.Задержка();
    КонецЦикла;
    
    // Конец замера
    ВремяОкончания = ТекущаяУниверсальнаяДатаВМиллисекундах();
    ДлительностьМс = ВремяОкончания - ВремяНачала;
    
    // Логируем с длительностью
    ЗаписатьЖурналДействий(
        ИмяПользователя,
        "Расчет зарплаты",
        "Выполнен за " + Формат(ДлительностьМс / 1000, "ЧЦ=3; ЧРД=") + " секунд",
        ДлительностьМс
    );
    
КонецПроцедуры

Процедура ЗаписатьЖурналДействий(Пользователь, Операция, Комментарий, ДлительностьМс = 0)

    Набор = РегистрыСведений.ЖурналДействий.СоздатьНаборЗаписей();
    Запись = Набор.Добавить();
    Запись.Период = ТекущаяДата();
    Запись.Пользователь = Пользователь;
    Запись.Операция = Операция;
    Запись.Комментарий = Комментарий;
    Запись.ДлительностьМс = ДлительностьМс;
    Набор.Записать(Истина);
    
КонецПроцедуры

Логирование в файл на диске

// Запись логов в текстовый файл с ротацией
Процедура ЗаписатьЛогВФайл(Уровень, Сообщение)

    // Определяем путь к файлу лога
    ПутьЛога = "C:\Logs\1C\Actions.log";
    ИмяПользователя = Пользователи.ТекущийПользователь().Имя;
    
    // Формируем строку лога
    СтрокаЛога = Формат(ТекущаяДата(), "ДФ=yyyy-MM-dd HH:mm:ss") + " | " +
                 Уровень + " | " +
                 ИмяПользователя + " | " +
                 Сообщение + Символы.ПС;
    
    // Запись в файл
    Файл = Новый ЗаписьТекста(ПутьЛога, КодировкаТекста.UTF8, Истина); // Истина - дозапись
    Файл.ЗаписатьСтроку(СтрокаЛога);
    Файл.Закрыть();
    
    // Контроль размера файла (ротация при превышении 10 МБ)
    КонтролироватьРазмерФайлаЛога(ПутьЛога);
    
КонецПроцедуры

Процедура КонтролироватьРазмерФайлаЛога(ПутьФайла)

    Инфо = Новый ИнформацияОФайле(ПутьФайла);
    Если Инфо.Существует И Инфо.Размер > 10 * 1024 * 1024 Тогда
        СкопироватьФайл(ПутьФайла, ПутьФайла + "." + Формат(ТекущаяДата(), "ДФ=yyyyMMddHHmmss"));
        УдалитьФайлы(ПутьФайла);
    КонецЕсли;
    
КонецПроцедуры

// Пример вызова
ЗаписатьЛогВФайл("INFO", "Пользователь открыл форму документа");
ЗаписатьЛогВФайл("WARNING", "Не заполнена обязательная реквизит");
ЗаписатьЛогВФайл("ERROR", "Ошибка при сохранении");

Логирование с фильтрацией по пользователю и уровню

// Продвинутое логирование с настройками фильтрации
Перем НастройкиЛогирования;

Процедура ИнициализироватьНастройкиЛогирования()

    НастройкиЛогирования = Новый Структура;
    НастройкиЛогирования.Вставить("Уровень", "ИНФО"); // ИНФО, ПРЕДУПРЕЖДЕНИЕ, ОШИБКА, ОТЛАДКА
    НастройкиЛогирования.Вставить("ПользователиИсключения", "Админ,Гость");
    НастройкиЛогирования.Вставить("ВРегистр", Истина);
    НастройкиЛогирования.Вставить("ВФайл", Ложь);
    
КонецПроцедуры

Процедура ЛогироватьСФильтрацией(Уровень, Сообщение, Метаданные = Неопределено)

    // Проверка уровня логирования
    Приоритеты = Новый Соответствие;
    Приоритеты.Вставить("ОТЛАДКА", 1);
    Приоритеты.Вставить("ИНФО", 2);
    Приоритеты.Вставить("ПРЕДУПРЕЖДЕНИЕ", 3);
    Приоритеты.Вставить("ОШИБКА", 4);
    
    ТекущийПриоритет = Приоритеты.Получить(НастройкиЛогирования.Уровень);
    ПриоритетСобытия = Приоритеты.Получить(Уровень);
    
    Если ПриоритетСобытия < ТекущийПриоритет Тогда
        Возврат; // Не логируем события ниже установленного уровня
    КонецЕсли;
    
    // Проверка исключений по пользователям
    ТекущийПользователь = Пользователи.ТекущийПользователь().Имя;
    СтрокаИсключений = НастройкиЛогирования.ПользователиИсключения;
    Если Найти(СтрокаИсключений, ТекущийПользователь) > 0 Тогда
        Возврат;
    КонецЕсли;
    
    // Формируем расширенное сообщение
    ПолноеСообщение = "[" + Уровень + "] " + Сообщение;
    Если Метаданные <> Неопределено Тогда
        ПолноеСообщение = ПолноеСообщение + " | Объект: " + Метаданные;
    КонецЕсли;
    
    // Запись согласно настройкам
    Если НастройкиЛогирования.ВРегистр Тогда
        ЗаписатьЛогВРегистр(Уровень, ПолноеСообщение);
    КонецЕсли;
    
    Если НастройкиЛогирования.ВФайл Тогда
        ЗаписатьЛогВФайл(Уровень, ПолноеСообщение);
    КонецЕсли;
    
КонецПроцедуры

Процедура ЗаписатьЛогВРегистр(Уровень, Сообщение)

    Набор = РегистрыСведений.ДетальныйЛог.СоздатьНаборЗаписей();
    Запись = Набор.Добавить();
    Запись.Период = ТекущаяДата();
    Запись.Пользователь = Пользователи.ТекущийПользователь().Имя;
    Запись.Уровень = Уровень;
    Запись.Сообщение = Сообщение;
    Запись.Компьютер = ИнформацияОбОкружении().ИмяКомпьютера;
    Запись.Приложение = ИнформацияОбОкружении().ИмяПрограммы;
    Набор.Записать(Истина);
    
КонецПроцедуры

// Пример использования
Процедура ОбработатьЗаказ()

    ИнициализироватьНастройкиЛогирования();
    
    ЛогироватьСФильтрацией("ИНФО", "Начало обработки заказа");
    
    Попытка
        // Код обработки заказа
        Заказ = Документы.ЗаказПокупателя.НайтиПоНомеру("З-123");
        Если Заказ = Неопределено Тогда
            ЛогироватьСФильтрацией("ОШИБКА", "Заказ не найден", "ЗаказПокупателя");
        КонецЕсли;
        
        ЛогироватьСФильтрацией("ОТЛАДКА", "Проведен расчет суммы заказа");
        
    Исключение
        ЛогироватьСФильтрацией("ОШИБКА", "Исключение: " + ОписаниеОшибки());
    КонецПопытки;
    
    ЛогироватьСФильтрацией("ИНФО", "Завершение обработки заказа");
    
КонецПроцедуры

Логирование с отправкой уведомлений администратору

// Критическое логирование с уведомлением администратора
Процедура ЛогироватьСУведомлением(Событие, Сообщение)

    // Базовое логирование
    Идентификатор = ЗаписатьКритическоеСобытие(Событие, Сообщение);
    
    // Дополнительная логика для критических ошибок
    Если Событие = "КРИТИЧЕСКАЯ_ОШИБКА" Тогда
        
        // Отправка email администратору
        Попытка
            Почта = Новый ИнтернетПочта;
            Почта.Подключиться("smtp.company.ru", 25, "", "",);
            
            СообщениеПочты = Новый ИнтернетПочтовоеСообщение;
            СообщениеПочты.Тема = "1С: Критическая ошибка";
            СообщениеПочты.Кому.Добавить("admin@company.ru");
            СообщениеПочты.Тело = "Пользователь: " + Пользователи.ТекущийПользователь().Имя + Символы.ПС +
                                    "Событие: " + Событие + Символы.ПС +
                                    "Сообщение: " + Сообщение + Символы.ПС +
                                    "ID события: " + Идентификатор;
            
            Почта.Послать(СообщениеПочты);
            Почта.Отключиться();
            
        Исключение
            // Тихая ошибка, чтобы не зацикливать логирование
        КонецПопытки;
        
        // Запись в системный журнал Windows
        ЗаписьСистемногоЖурнала(Событие + ": " + Сообщение);
        
    КонецЕсли;
    
КонецПроцедуры

Функция ЗаписатьКритическоеСобытие(Событие, Сообщение)

    Набор = РегистрыСведений.КритическиеСобытия.СоздатьНаборЗаписей();
    Запись = Набор.Добавить();
    Запись.Период = ТекущаяДата();
    Запись.Событие = Событие;
    Запись.Пользователь = Пользователи.ТекущийПользователь().Имя;
    Запись.Сообщение = Сообщение;
    Запись.Идентификатор = Новый УникальныйИдентификатор;
    Запись.Сеанс = ИнформацияОбОкружении().ИдентификаторСеанса;
    Набор.Записать(Истина);
    
    Возврат Запись.Идентификатор;
    
КонецФункции

// Пример использования
Попытка
    // Код, который может привести к критической ошибке
    Соединение = Новый COMОбъект("НесуществующийОбъект");
Исключение
    ЛогироватьСУведомлением(
        "КРИТИЧЕСКАЯ_ОШИБКА", 
        "Ошибка при создании COM-объекта: " + ОписаниеОшибки()
    );
    ВызватьИсключение;
КонецПопытки;

Примечания

// Важные рекомендации по логированию действий пользователя:
// 1. Всегда логируйте начало и окончание важных операций
// 2. Используйте различные уровни логирования (ИНФО, ОТЛАДКА, ПРЕДУПРЕЖДЕНИЕ, ОШИБКА)
// 3. Не логируйте конфиденциальные данные (пароли, персональные данные)
// 4. При интенсивном логировании используйте асинхронную запись или буферизацию
// 5. Регулярно архивируйте старые логи для экономии места
// 6. Для отладки используйте условные директивы препроцессора #Если Сервер или #Если Клиент
// 7. В пиковый период используйте фильтрацию событий по пользователям и уровню
// 8. Всегда оборачивайте критическое логирование в конструкцию Попытка...Исключение

Поделиться с друзьями
Smirnov code
Добавить комментарий