При разработке функционала для работы с присоединенными файлами программисты часто используют встроенное в платформу Поле PDF документа. Это удобный инструмент, позволяющий пользователям просматривать содержимое документов без открытия сторонних приложений. Однако иногда стандартных возможностей недостаточно, и требуется более сложная работа с PDF файлами в 1С без внешних компонентов, например, для их конвертации в изображения или масштабирования. При переходе с файловой базы на клиент-серверный вариант (SQL) или при обновлении платформы до определенных релизов (например, 8.3.27.1859) можно столкнуться с критической ошибкой: «Файл документа изменен». При этом 1С может аварийно завершать работу, либо просто блокировать отображение файла.
В этой статье мы подробно разберем, почему возникает эта проблема, как она связана с архитектурой взаимодействия клиента и сервера, и рассмотрим все доступные способы её решения — от обновления платформы до программных «костылей».
Проанализируем ситуацию: ошибка чаще всего проявляется в клиент-серверном режиме, если в PDF-файле содержатся интерактивные элементы, такие как гиперссылки, аннотации или заполняемые поля форм. В файловой версии базы данных проверка целостности объекта может проходить мягче, но в режиме SQL-сервера механизмы синхронизации работают строже.
Суть проблемы заключается в так называемом «dirty flag» (флаге изменения). Когда встроенный компонент просмотра PDF загружает документ с гиперссылками, он может ошибочно пометить его в памяти как «измененный» сразу после открытия. Если в этот же момент (например, в процедуре ПриОткрытии) происходит контекстный серверный вызов, платформа пытается синхронизировать состояние формы и её реквизитов. Обнаружив, что объект PDF на клиенте якобы изменился по сравнению с данными, которые только что были получены с сервера, система выдает исключение для предотвращения потери данных.
Официально эта проблема зафиксирована как баг платформы (например, в реестре ошибок под номером 00166245). Рассмотрим, как мы можем это исправить.
Самый правильный и надежный путь — это установка версии платформы, в которой данная ошибка была исправлена разработчиками «1С». Опыт практикующих специалистов показывает, что проблема полностью уходит на релизах начиная с 8.3.27.1964 и выше. Если ваша организация позволяет оперативно проводить обновление, это должно стать приоритетным вариантом.
После обновления проверьте работу функционала: ошибка «Файл документа изменен» должна исчезнуть даже при наличии серверных вызовов в модуле формы.
Если по каким-то причинам обновить платформы прямо сейчас невозможно, разберем программный обходной путь. Поскольку конфликт возникает в момент инициализации формы и одновременного выполнения серверных вызовов, мы можем разнести эти события во времени.
Вместо того чтобы загружать PDF-данные напрямую в ПриСозданииНаСервере или ПриОткрытии, используем обработчик ожидания. Это позволит форме полностью отрисоваться, завершить все системные процессы синхронизации, и только после этого подгрузить содержимое документа. Рассмотрим пример реализации:
&НаКлиенте
Процедура ПриОткрытии(Отказ)
// Устанавливаем минимальную задержку в 0.1 секунды
ПодключитьОбработчикОжидания("Подключаемый_ЗагрузитьДанныеPDF", 0.1, Истина);
КонецПроцедуры
&НаКлиенте
Процедура Подключаемый_ЗагрузитьДанныеPDF()
// Здесь вызываем код загрузки файла в поле PDF
ЗагрузитьФайлНаФорму();
КонецПроцедуры
Такой подход «обманывает» механизм проверки изменений, так как загрузка происходит уже после того, как основной контекст формы стабилизировался.
Проанализируем, как именно поле PDF связано с данными. Часто разработчики привязывают ПутьКДанным элемента формы напрямую к реквизиту справочника, имеющему тип ХранилищеЗначения или ДвоичныеДанные. Это и провоцирует проверку на изменение.
Чтобы избежать этого, рекомендуем использовать несвязанное поле:
АдресФайлаВоВременномХранилище).УстановитьДанные() или просто присваивать навигационную ссылку временного хранилища этому реквизиту.Посмотрим на пример кода:
&НаСервере
Процедура ПриСозданииНаСервере(Отказ, СтандартнаяОбработка)
// Получаем навигационную ссылку на двоичные данные из присоединенного файла
АдресФайлаВоВременномХранилище = ПолучитьНавигационнуюСсылку(Объект.Ссылка, "ДанныеФайла");
КонецПроцедуры
Поскольку поле формы теперь связано не с самим объектом базы данных, а с временной строкой-ссылкой, платформа перестает считать состояние объекта «грязным» (измененным).
Если ваш проект требует гарантированной стабильности и вы часто сталкиваетесь с тем, что встроенное поле 1С «падает» на специфических файлах от контрагентов, стоит рассмотреть вариант использования PDF.js внутри Поля HTML документа. Также в ряде случаев может помочь программная конвертация отчетов 1С в графический формат для последующего отображения PDF как набора картинок.
Алгоритм действий следующий:
ПолеHTMLДокумента.Такой метод позволяет не только избежать ошибки «Файл документа изменен», но и дает гораздо больше возможностей по управлению масштабом, поиском по тексту и навигацией по страницам, которые во встроенном поле 1С ограничены.
Рассмотрим еще несколько важных моментов, которые помогут избежать проблем с PDF в будущем:
1cv8.exe. В таких случаях может потребоваться предварительное сжатие и обработка PDF перед выводом на экран.Подведем итог: если вы столкнулись с ошибкой «Файл документа изменен», в первую очередь попробуйте обновить платформу до актуального патча ветки 8.3.27. Если это невозможно — используйте ПодключитьОбработчикОжидания для загрузки данных, чтобы разнести во времени инициализацию формы и наполнение поля PDF.