14 июня 2021

Цифровая подпись PDF документов созданных в FastReport

    С ростом популярности обмена документами в электронном виде тема защиты их от подделки становится все более важной. На прошлой неделе я писал о добавлении в PDF документ цифровой подписи с использованием Foxit Quick PDF Library. Сегодня хочу рассказать о возможности цифровой подписи PDF документов, созданных с использованием генератора отчетов FastReport.
    В выпущенном этой весной FastReport VCL 2021 появился новый объект "Цифровая подпись" (TfrxDigitalSignatureView). Он позволяет добавить цифровую подпись в документы формата PDF, которые были созданы экспортом из FastReport. Для подписи используется сертификат, хранящийся в файле формата PKCS#12 (PFX).
    Создадим в FastReport небольшой шаблон отчета и добавим в него объект TfrxDigitalSignature.
FastReport - frxDigitalSignature
В инспекторе объектов отчета у него всего две настройки, которые связанны с цифровой подписью:
  1. Kind – тип цифровой подписи (skVisible, skInvisible, skEmpty).
  2. Picture – изображение для видимой цифровой подписи.
Все остальные параметры цифровой подписи задаются в диалоге экспорта отчета в PDF-файл.
FastReport - Export to PDF
Только мне одному кажется странным, что пароль в открытом виде и GroupBox с параметрами цифровой подписи называется "Save the password"? Наведем "красоту":
  • В модуле frxrcExports.pas поменяем '<StrRes Name="8725" Text="Save the password"/>' на '<StrRes Name="8725" Text=" Signature properties "/>'.
  • В модуле frxExportPDFDialog.dfm свойству PasswordChar объекта CertificatePasswordE присвоим '*'.
Еще на закладку "Signature" я бы добавил выбор сертификата из хранилища сертификатов Windows. Мне кажется, что это более удобно, чем каждый раз выбирать файл с сертификатом и вводить пароль. Кроме диалога экспорта, параметры цифровой подписи можно задать в коде программы.
program frSignPDF;

{$APPTYPE CONSOLE}

uses
  System.SysUtils,
  frxClass, frxExportPDF;

procedure ExportSignPDF(const sPfxFileName, sPfxPassword: String);
var
  frxReport: TfrxReport;
  frxPDFExport: TfrxPDFExport;
begin
  frxReport := TfrxReport.Create(nil);
  try
    frxReport.ShowProgress := False;
    if frxReport.LoadFromFile('test.fr3') and frxReport.PrepareReport then
      begin
        frxPDFExport := TfrxPDFExport.Create(nil);
        try
          frxPDFExport.ShowDialog := False;
          frxPDFExport.ShowProgress := False;
          frxPDFExport.EmbeddedFonts := False;
          frxPDFExport.Quality := 100;

          // Параметры цифровой подписи 
          // местонахождение
          frxPDFExport.DigitalSignLocation := 'Belarus';
          // причина подписания
          frxPDFExport.DigitalSignReason   := 'Тестирование подписи FastReport';
          // контактная информация
          frxPDFExport.DigitalSignContactInfo := 'https://it-blackcat.blogspot.com';
          // файл сертификата
          frxPDFExport.DigitalSignCertificatePath     := sPfxFileName;
          // пароль сертификата
          frxPDFExport.DigitalSignCertificatePassword := sPfxPassword;

          frxPDFExport.FileName := 'FastReport - Signed PDF.pdf';
          frxReport.Export(frxPDFExport);
        finally
          frxPDFExport.Free;
        end;
      end;
  finally
    frxReport.Free
  end;
end;

begin
  ReportMemoryLeaksOnShutdown := True;
  try
    ExportSignPDF('test.pfx', 'пароль сертификата')
  except
    on E: Exception do
      Writeln(E.ClassName, ': ', E.Message);
  end;
end.
    Рассмотрим подробнее результаты экспорта в PDF-файл для каждого типа цифровой подписи.
  • Kind = skVisible – видимая цифровая подпись. Для этого вида подписи главное не забыть загрузить в свойство Picture красивую картинку.
    FastReport - Signed PDF
  • Kind = skInvisible – не видимая цифровая подпись. Думаю, что для этого варианта объект TfrxDigitalSignature в шаблоне можно сделать не обязательным, а в TfrxPDFExport добавить метод запускающий функцию создания подписи и на диалог frxExportPDFDialog добавить CheckBox связанный с ее вызовом. В результате можно было бы подписывать любой отчет без внесения изменений в его шаблон.
  • Kind = skEmpty – цифровая подпись без указания сертификата. В этом случае в PDF документе создается "не подписанное поле подписи".
    PDF - Unsigned signature field
    Если по нему кликнуть при просмотре, то откроется список сертификатов, которые доступны пользователю для подписи PDF документа.
    В результате экспериментов с цифровой подписью в FastReport у меня появилось всего одно небольшое замечание. В дизайнере шаблона на объекте TfrxDigitalSignature раздражает надпись "Digital Signature". Она мешает задать требуемый размер именованного поля для подписи (например, под размер загруженного изображения видимой подписи).
FastReport - надпись 'Digital Signature' у frxDigitalSignature
Как вы видите, надпись не только закрывает загруженную картинку, но и соседний объект. Решается этот вопрос просто. В модуле frxClass.pas у класса TfrxDigitalSignatureView нужно удалить метод Draw.
    Для первого релиза функции цифровой подписи PDF документов в FastReport весьма неплохо. Разработчикам осталось совсем немного "обработать ее напильником".

Комментариев нет:

Отправить комментарий