&НаКлиенте
Процедура УстановитьДоступностьКоманд(ТекущиеДанные)
Если Элементы.Обзор.Видимость Тогда
Префикс = "";
Иначе
Префикс = "Создание";
КонецЕсли;
Если ТекущиеДанные = Неопределено
Или ТипЗнч(Элементы["Файлы"+Префикс].ТекущаяСтрока) = Тип("СтрокаГруппировкиДинамическогоСписка") Тогда
УстановитьДоступностьКоманды(Элементы["ОткрытьФайл"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыОткрытьФайл"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["Напечатать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыНапечатать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["Редактировать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыРедактировать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ЗакончитьРедактирование"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗакончитьРедактирование"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["Изменить"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыИзменить"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["Занять"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗанять"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["СохранитьИзменения"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьИзменения"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["Удалить"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыУдалить"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["СохранитьКак"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьКак"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["Освободить"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыОсвободить"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ОбновитьИзФайлаНаДиске"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыОбновитьИзФайлаНаДиске"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыРаспознать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыРаспознать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыПодписатьФайл"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыПодписатьФайл"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыДобавитьЭПИзФайла"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыДобавитьЭПИзФайла"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыСохранитьВместеСЭП"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьВместеСЭП"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыЗашифровать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗашифровать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыРасшифровать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыРасшифровать"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыЗаполнитьФайлДаннымиДокумента"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗаполнитьФайлДаннымиДокумента"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыВставитьРегистрационныйНомер"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыВставитьРегистрационныйНомер"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыВставитьШтрихкод"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыВставитьШтрихкод"+Префикс], Ложь);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСнятьОтметкуСканКопияОригиналаУВсехФайлов"+Префикс], Ложь);
// начало модификации кода
УстановитьДоступностьКоманды(Элементы["ФайлыКонтекстноеМенюВизулизацияЭЦП"], Ложь);
УстановитьДоступностьКоманды(Элементы["ВизулизацияЭЦП"], Ложь);
УстановитьДоступностьКоманды(Элементы["ФайлыКонтекстноеМенюСоздатьФайлВизуализации"], Ложь);
УстановитьДоступностьКоманды(Элементы["СоздатьФайлВизуализации"], Ложь);
// конец модификации кода
Иначе
РедактируетТекущийПользователь = ТекущиеДанные.РедактируетТекущийПользователь;
Редактирует = ТекущиеДанные.Редактирует;
ПодписанЭП = ТекущиеДанные.ПодписанЭП;
Зашифрован = ТекущиеДанные.Зашифрован;
СозданПоШаблонуДокумента = ТекущиеДанные.СозданПоШаблонуДокумента;
РазрешеноРедактирование = Не (ЗапретитьРедактироватьФайлы И СозданПоШаблонуДокумента);
РазрешеноУдаление = Не (ЗапретитьУдалятьФайлы И СозданПоШаблонуДокумента);
УстановитьДоступностьКоманды(Элементы["ОткрытьФайл"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыОткрытьФайл"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["Напечатать"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыНапечатать"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["Редактировать"+Префикс], НЕ ТекущиеДанные.ПодписанЭП И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыРедактировать"+Префикс], НЕ ТекущиеДанные.ПодписанЭП И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["ЗакончитьРедактирование"+Префикс], РедактируетТекущийПользователь И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗакончитьРедактирование"+Префикс], РедактируетТекущийПользователь И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["Изменить"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыИзменить"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["Занять"+Префикс], Редактирует.Пустая() И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗанять"+Префикс], Редактирует.Пустая() И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["СохранитьИзменения"+Префикс], РедактируетТекущийПользователь И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьИзменения"+Префикс], РедактируетТекущийПользователь И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["Удалить"+Префикс], РазрешеноУдаление);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыУдалить"+Префикс], РазрешеноУдаление);
УстановитьДоступностьКоманды(Элементы["СохранитьКак"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьКак"+Префикс], Истина);
УстановитьДоступностьКоманды(Элементы["Освободить"+Префикс], Не Редактирует.Пустая() И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыОсвободить"+Префикс], Не Редактирует.Пустая() И РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["ОбновитьИзФайлаНаДиске"+Префикс], РазрешеноРедактирование);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыОбновитьИзФайлаНаДиске"+Префикс], РазрешеноРедактирование);
Расширение = ТекущиеДанные.Расширение;
ИспользоватьImageMagickДляРаспознаванияPDF = ФайловыеФункцииКлиентПовтИсп.ПолучитьПерсональныеНастройкиРаботыСФайлами().ИспользоватьImageMagickДляРаспознаванияPDF;
РасширениеПоддерживается = РаботаСФайламиКлиентСервер.ЭтотФайлМожноРаспознать(Расширение, ИспользоватьImageMagickДляРаспознаванияPDF);
УстановитьДоступностьКоманды(Элементы["ФайлыРаспознать"+Префикс], РасширениеПоддерживается И Редактирует.Пустая());
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыРаспознать"+Префикс], РасширениеПоддерживается И Редактирует.Пустая());
УстановитьДоступностьКоманды(Элементы["ФайлыПодписатьФайл"+Префикс], Редактирует.Пустая() И НЕ Зашифрован);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыПодписатьФайл"+Префикс], Редактирует.Пустая() И НЕ Зашифрован);
УстановитьДоступностьКоманды(Элементы["ФайлыДобавитьЭПИзФайла"+Префикс], Редактирует.Пустая() И НЕ Зашифрован);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыДобавитьЭПИзФайла"+Префикс], Редактирует.Пустая() И НЕ Зашифрован);
УстановитьДоступностьКоманды(Элементы["ФайлыСохранитьВместеСЭП"+Префикс], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьВместеСЭП"+Префикс], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["ФайлыЗашифровать"+Префикс], Редактирует.Пустая() И НЕ Зашифрован);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗашифровать"+Префикс], Редактирует.Пустая() И НЕ Зашифрован);
УстановитьДоступностьКоманды(Элементы["ФайлыРасшифровать"+Префикс], Зашифрован);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыРасшифровать"+Префикс], Зашифрован);
УстановитьДоступностьКоманды(Элементы["ФайлыВставитьШтрихкод"+Префикс], Редактирует.Пустая());
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыВставитьШтрихкод"+Префикс], Редактирует.Пустая());
УстановитьДоступностьКоманды(Элементы["ФайлыВставитьРегистрационныйНомер"+Префикс], ЗначениеЗаполнено(Объект.РегистрационныйНомер));
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыВставитьРегистрационныйНомер"+Префикс], ЗначениеЗаполнено(Объект.РегистрационныйНомер));
УстановитьДоступностьКоманды(Элементы["ФайлыСохранитьВместеСЭП"+Префикс], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСохранитьВместеСЭП"+Префикс], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["ФайлыЗаполнитьФайлДаннымиДокумента"+Префикс], ТекущиеДанные.СозданИзШаблона И Редактирует.Пустая());
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыЗаполнитьФайлДаннымиДокумента"+Префикс], ТекущиеДанные.СозданИзШаблона И Редактирует.Пустая());
УстановитьДоступностьКоманды(Элементы["КонтекстноеМенюФайлыСнятьОтметкуСканКопияОригиналаУВсехФайлов"+Префикс], Не Элементы.Оригинал.ТолькоПросмотр);
// начало модификации кода
УстановитьДоступностьКоманды(Элементы["ФайлыКонтекстноеМенюВизулизацияЭЦП"], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["ВизулизацияЭЦП"], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["ФайлыКонтекстноеМенюСоздатьФайлВизуализации"], ПодписанЭП);
УстановитьДоступностьКоманды(Элементы["СоздатьФайлВизуализации"], ПодписанЭП);
// конец модификации кода
КонецЕсли;
КонецПроцедуры
Здравствуйте.
Правильно ли я понимаю, что штамп позиционируется только при использовании шаблона файла, а в случае, если файл будет загружен не по шаблону, а произвольный, то установка штампа не произойдёт?
И вопросец. А пробовали добавлять штамп в xml в нижней части страницы, чтобы просто отдельной строкой или таблицей?
(2)То есть к первому вопросу. Если нет меток то штамп не будет вставлен, т.е. в произвольном документе, который загрузит пользователь ничего не изменится, если его попытаться подписать и впечатать штампы.
2. Во втором вопросе я имел в виду:
А почему бы не добавлять абзацы(строки) с подписями и штампами прямо в нижней части документа без использования позиционирования? Я предположил, что, возможно, вы это пробовали сделать, может быть столкнулись с трудностями.
Дело в том, что мне всю вставку штампа нужно обработать на сервере, т.к. клиентская машина может быть не-windows.
В добавок, шаблон документа не подходит, т.к. неизвестно заранее количество подписей, и часто сам документ пользователь может добавить не по шаблону.
Плюс ко всему этому есть желание подписывать именно уже визуализированный документ в pdf, чтобы отправлять подписанный, а не «визуализацию» подписанного файла. Думаю, подписывать оба файла будет правильнее. И уже после вставки штампика.
(2) Словил ошибку:
{ОбщийМодуль.ПЛ_ВизуализацияЭЦПСервер.Модуль(42)}: Поле объекта не обнаружено (SN)
?(Сертификат.Субъект.Свойство(«O»), Сертификат.Субъект.SN + » » + Сертификат.Субъект.GN, Сертификат.Субъект.CN)));
У себя поправил на:
…Сертификат.Субъект.Свойство(«SN «)…
И ещё:
МСВорд.Documents.Close();
по причине:
Произошла исключительная ситуация (Microsoft Word): Метод или свойство недоступны, поскольку эту команду нельзя использовать в режиме чтения.
1. Там в меню 2 команды: «Визуализация ЭЦП» и «Создать файл визуализации». По команде «Визуализация ЭЦП» метки не ищутся и выводится штамп прямо сверху документа, чтобы его можно было позиционировать руками куда надо (предварительно запрашиваются координаты). А по команде «Создать файл визуализации» ищутся метки и вместо них вставляются штампы. Если метки не найдены, то файл визуализации не формируется и выводится предупреждение.
2. Отвечу цитатой п.п. «а» п. 5.23 ГОСТ Р 7.0.97-2016: «место размещения отметки об электронной подписи должны соответствовать месту размещения собственноручной подписи в аналогичном документе на бумажном носителе;». Однако многим на это начхать. В версии 1С БГУ 1.0, например, информация об ЭЦП выводится над документом, полученным по ЭДО. И ничего страшного, мы публикуем такие документы на портале госзакупок и пока никто ничего не сказал. Несоответствие ГОСТу не делает документ юридически менее значимым.
3. По этому вопросу ничего не скажу. Выводить подписи снизу не по ГОСТу, но при формировании на сервере без меток непонятно как распределить штампы. ХЗ, короче.
Подписывать визуализированный файл идеологически неверно. По закону № 63-ФЗ «Об ЭЦП» есть определение: электронная подпись — информация в электронной форме, которая присоединена к другой информации в электронной форме (подписываемой информации) или иным образом связана с такой информацией и которая используется для определения лица, подписывающего информацию; Соответственно ЭЦП может быть прикреплённая и откреплённая (отдельный файл). Если Вы хотите отправлять юридически значимый файл контрагенту, то нужно его отправлять вместе с файлом ЭЦП, а на принимающей стороне должна производиться проверка корректности ЭЦП.
В настоящее время складывается практика отправки сканов документов со штампами ЭЦП (визуализированных документов), что неверно с точки зрения закона, но, как сказал наш юрист, «допустимо в сложившейся практике документооборота».
По поводу имён свойств не подскажу, всегда считал, что есть общепринятые свойства сертификата (O, CN, SN и т.д.), если у вас по-другому, то это странно.
Команду МСВорд.Documents.Close(); оберните в конструкцию Попытка … Исключение … У меня на клиентских машинах без данной команды оставались висеть процессы MS Word.
(5)
Это потому что подписывание идёт вслед за установкой штампа?
Но получается, что установка штампа после подписи сломает подпись.
(5)
А почему не по ГОСТу? Ведь даже в примере подпись (штампик) снизу.
Ну может я плохо объясняю.
Я имел в виду всю строку, где указан подписант, его должность и сам штамп формировать полностью.
(6) Да в итоге когда закомментировал уже ошибка совместного доступа.
Надо будет добавить проверку на существование одноимённого файла.
(5) И ещё
Правильно ли я понимаю, что на не-windows системах работать не будет?
1. Идеологически неверно потому, что визуализируется уже существующая подпись (так следует из ГОСТа), а сама подпись — это информация. И, конечно, вставка подписи в файл сделает подпись недействительной (1C:Документооборот не даст сохранить файл).
тут коллеге удалось, можно связаться и уточнить), но тогда нужно решать вопрос с созданием PDF и либо искать соответствующую команду COM-сервера, либо пытаться реализовать печать на виртуальном принтере PDF (примеры для 1С и windows я находил в сети).
2. В примере штампик внизу, но он находится между полей формы, которые заполняются при заполнении шаблона: слева должность подписанта, справа его ФИО, так, что строго выполняется п.п. «а» п. 5.23 ГОСТа.
3. Для не-Windows систем есть следующие выходы:
а) если не-Windows клиент, а сервер Windows, то можно переписать алгоритм для формирования визуализации на сервере, но тогда только по шаблону с метками;
б) если Windows нет совсем, то можно адаптировать работу алгоритма к LibreOffice (
4.Ошибка МСВорд.Documents.Close(); очень странная. Я тестировал работу алгоритма на MS Word 2007 и 2016 и всё было нормально. Может переменная МСВорд.Documents как-то переинициализируется. Не знаю что и предположить.
(6)
Оказалось, что документ открывался только на чтение в строке
Исправил на
и ошибка пропала.
Возможно разные версии office. Не понятно.
Ещё всё же, думаю, стоит имена файлов во временном хранилище формировать с помощью
ПолучитьИмяВременногоФайла ()
Ну или уникальный идентификатор приписывать…
и потом в конце прикрепления удалять файлы из временного хранилища. (в процессе их можно накапливать в массиве, к примеру)
«Произошла исключительная ситуация (Microsoft Word): Метод или свойство недоступны, поскольку эту команду нельзя использовать в режиме чтения.» — Такая же ошибкаи у меня. Ворд подвешивается, и если еще раз прожать, то уже «Процесс не может получить доступ к файлу» естественно.
(12) Очень жаль, что вы не указываете хотя бы номер строки, в которой произошла ошибка. А в телепатии я пока слаб.
Очень похоже на ошибку, описанную с посте № 4, уважаемого antonio_i, он нашёл решение и описал его в посте № 11. Лично я с такой ошибкой не сталкивался.
(12)
Посмотрите мой ответ № 11
Там у меня была такая же ошибка, я исправил.
Неплохая реализация, никаких проблем как у antonio_i не было. Жаль что юридическая составляющая этого всего никакая… т.к. док не подписан, а просто картинка.
А идей по поводу добавления визуализации в pdf нету?
(15) Позвольте не согласиться. Юридическая составляющая нормальная. Документ подписан в соответствии с ФЗ № 63 и визуализирован согласно ГОСТу.
Визуализация в pdf делается с помощью библиотеки pdftk. Там можно слепить 2 pdf-документа. Верхний содержит визуализацию и прозрачный фон, а нижний — сам документ. Тут сложными являются вопросы позиционирования штампа и согласования размеров изображений, на основании которых сделаны файлы pdf.
1. Если файл подписан несколькими подписями (Петров, Сидоров), то выводится 2 подписи Петрова.
2. Как заставить подпись позиционироваться внизу документа?
(17) 1. Я не тестировал на предмет вставки нескольких штампов (у меня только одна ЭП). Разные варианты штампов хранятся в массиве ГотовыеШтампыЭП. Надо посмотреть отладчиком что там. В новой версии ДО, разработчики суют все подписи в один штамп, может так и надо.
https://infostart.ru/public/931674/)
2. Штамп может вставляться вместо метки или по координатам. Подберите координаты, чтобы подпись вставала куда надо. Координаты указываются в форме настройки положения штрихода (
(18) 1. У Вас ошибка, Вы не обнуляете Шаблон после замены, поэтому при наличии нескольких подписей всегда печатается первая заполненная. Нужно добавить в конец цикла получение шаблона
ШаблонДляВставкиШтампа = ВизуализацияЭЦПСервер.ПолучитьТекстДляВставки();
Тогда все красиво
2. Подскажите, как получить координаты подвала последней страницы в файле?
а если нужно в обычную печатную форму сделать вывод и потом сохранить в PDF? есть варианты?
через Word все плывет, а вывод, т.е. дорисовка чего-либо в PDF требует дополнительных программ, что тоже стабильности и простоты не добавляет
(20) Добрый день. Не по теме вопрос. В данной публикации рассматривается подпись и визуализация произвольного документа (формат MS Word 2007+). В частности исходящего письма. А как у вас реализована генерация писем через обычную печатную форму? Поделитесь, интересно.
Если у Вас печатная форма, то всё значительно проще. Штамп с параметрами для подписи можно задизайнить прямо в макете и потом вжух:
и получить pdf-файл.
(21) еще не доделал, по сути таже зд, только другие детали
сохранение в виде Word, Excel, PDF роли не играет. Ваш вариант заточен на письма, мне нужно шире. Нужно сохранить печатную форму, наложить подпись ЭЦП, возможно подписать ЭЦП