При работе с платформой 1С:Предприятие 8.3 программисты часто сталкиваются с одной из самых загадочных и неприятных ошибок — "Ошибка формата потока". Особенно критично это проявляется в файловых версиях баз данных при попытке программного или интерактивного доступа к списку регламентных заданий. Проблема коварна тем, что она не дает подробного описания и часто приводит к аварийному завершению работы (дампу) всей системы.
Рассмотрим ситуацию, когда при запуске стандартной консоли регламентных заданий или выполнении простого кода по получению списка заданий платформа «вылетает» без объяснения причин. Выясним причины такого поведения и разберем по шагам алгоритм восстановления работоспособности базы.
Обычно ошибка возникает в момент обращения к свойствам объекта РегламентноеЗадание. Посмотрим на пример кода, который вызывает падение системы:
Регламентные = РегламентныеЗадания.ПолучитьРегламентныеЗадания(Отбор);
РегламентныеЗаданияСоответствие.Очистить();
Для Каждого Регламентное из Регламентные Цикл
НоваяСтрока = СписокРегламентныхЗаданий.Добавить();
// Ошибка происходит на следующей строке:
НоваяСтрока.Метаданные = Регламентное.Метаданные.Представление();
КонецЦикла;
Проанализируем ситуацию: метод ПолучитьРегламентныеЗадания() успешно возвращает массив, однако при попытке прочитать Метаданные конкретного элемента система обнаруживает несоответствие внутренней структуры данных ожидаемому формату. Это прямое свидетельство того, что в базе данных существует запись о регламентном задании, которое ссылается на уже несуществующий или поврежденный объект конфигурации.
Первым делом проанализируем локальные файлы конфигурации. Локальный кэш 1С хранит временные копии структур метаданных. Если в процессе динамического обновления или из-за сбоя сети данные в кэше «рассинхронизировались» с реальной базой, обращение к РегламентныеЗадания вызовет ошибку формата потока.
Решение: Полная очистка кэша. Необходимо удалить содержимое папок %AppData%\Local\1C\1cv8\ и %AppData%\Roaming\1C\1cv8\. После этого следует заново добавить базу в список в окне запуска, чтобы сгенерировался новый идентификатор сеанса.
В файловом варианте 1С регламентные задания хранятся во внутренних служебных таблицах. Если произошел сбой питания или некорректное завершение процесса 1cv8.exe, индексы или данные этих таблиц могут быть повреждены.
Разберем по шагам процесс исправления:
1Cv8.1CD.chdbfl.exe (находится в папке bin установленной платформы). Установим флаг "Исправлять обнаруженные ошибки" и запустим проверку.Проанализируем технологический журнал (ТЖ), представленный в логах системы. Записи вида Exception=9db1fa37-b455-4f3f-b8dd-7de0ea7d6da3, Descr="src\ClientFileCacheImpl.cpp(275)... DynamicalWorkCache указывают на проблемы с механизмом динамического обновления.
Когда мы меняем общий модуль, в котором объявлен метод регламентного задания, и обновляем базу «на лету», в служебных таблицах Config могут остаться ссылки на старые версии объектов. При попытке метода Метаданные.Представление() обратиться к описанию объекта, платформа получает «битую» ссылку и выбрасывает ошибку формата потока.
Решение: Выполним «жесткое» обновление конфигурации. Для этого зайдем в Конфигуратор, внесем несущественное изменение (например, добавим пробел в комментарии любого модуля), сохраним и обновим конфигурацию базы данных (F7).
Посмотрим на записи в логах: Exception=DatabaseException8, Descr="Отсутствует файл базы данных 'D:\bases1C\Auto 8_3/1Cv8tmp.1CD'". В файловом режиме 1С активно использует временный файл 1Cv8tmp.1CD для управления блокировками и фоновыми заданиями.
Если у пользователя ОС нет полных прав на запись в папку с базой данных или если антивирус заблокировал создание временного файла, попытка инициализировать менеджер регламентных заданий приведет к сбою. Убедимся, что папка с базой добавлена в исключения антивируса и права доступа настроены корректно.
Важно помнить, что в файловой базе регламентные задания не запускаются автоматически службой (как в клиент-сервере). Они требуют запущенного клиентского сеанса, который будет выступать в роли «планировщика».
Рассмотрим, как правильно инициализировать выполнение заданий, чтобы избежать зависания менеджера:
// В модуле приложения или специализированной обработке
Процедура ПриНачалеРаботыСистемы()
#Если Клиент Тогда
// Для файловой базы необходимо явно разрешить обработку заданий
ВыполнитьОбработкуЗаданий();
#КонецЕсли
КонецПроцедуры
Если менеджер заданий не запущен или «подвис», обращения к коллекции РегламентныеЗадания могут возвращать невалидные объекты. Убедимся, что в настройках базы не стоит галочка "Блокировка регламентных заданий".
Если очистка кэша, chdbfl.exe и тестирование-исправление не помогают, воспользуемся проверенным методом пересборки базы:
Этот процесс полностью пересоздает структуру файла .1CD, очищает таблицы от «фантомных» записей и практически всегда устраняет ошибку формата потока, если она была вызвана логическим повреждением данных.
Если база падает при переборе всех заданий, попробуем локализовать поврежденный элемент. Вместо получения всех заданий, попробуем получить их по одному, используя Попытка...Исключение. Хотя ошибка формата потока часто является неуловимой для этого блока, иногда это позволяет пропустить проблемный объект:
Попытка
ВсеЗадания = РегламентныеЗадания.ПолучитьРегламентныеЗадания();
Для Каждого Задание Из ВсеЗадания Цикл
Попытка
ИмяЗадания = Задание.Метаданные.Имя;
Сообщить("Обработка задания: " + ИмяЗадания);
Исключение
Сообщить("Обнаружено поврежденное задание, пропускаем...");
// Здесь можно попробовать Задание.Удалить(), если объект доступен
КонецПопытки;
КонецЦикла;
Исключение
Сообщить("Критическая ошибка доступа к коллекции заданий.");
КонецПопытки;
В большинстве случаев комплексное использование chdbfl.exe и выгрузки в .dt полностью решает проблему "Ошибки формата потока" в регламентных заданиях.