You are here

public function PdftkPdfBackend::mergeFile in FillPDF 5.0.x

Same name and namespace in other branches
  1. 8.4 src/Plugin/PdfBackend/PdftkPdfBackend.php \Drupal\fillpdf\Plugin\PdfBackend\PdftkPdfBackend::mergeFile()

Populate a PDF file with field data.

Parameters

\Drupal\file\FileInterface $template_file: The PDF template the field values specified in the mapping should be merged into.

\Drupal\fillpdf\FieldMapping[] $field_mappings: An array of FieldMapping objects mapping PDF field keys to the values they should be replaced with. Example:

[
  'Foo' => new TextFieldMapping('bar'),
  'Foo2' => new TextFieldMapping('bar2'),
  'Image1' => new ImageFieldMapping(base64_encode(file_get_contents($image)), 'jpg'),
];

array $context: The request context as returned by FillPdfLinkManipulator::parseLink().

Return value

string|null The raw file contents of the new PDF, or NULL if merging failed. The caller has to handle saving or serving the file accordingly.

Overrides PdfBackendInterface::mergeFile

See also

\Drupal\fillpdf\Plugin\PdfBackendInterface::mergeStream()

1 call to PdftkPdfBackend::mergeFile()
PdftkPdfBackend::mergeStream in src/Plugin/PdfBackend/PdftkPdfBackend.php
Populate a PDF file with field data.

File

src/Plugin/PdfBackend/PdftkPdfBackend.php, line 181

Class

PdftkPdfBackend
Pdftk PdfBackend plugin.

Namespace

Drupal\fillpdf\Plugin\PdfBackend

Code

public function mergeFile(FileInterface $template_file, array $field_mappings, array $context) {
  $template_uri = $template_file
    ->getFileUri();
  $fields = [];
  foreach ($field_mappings as $pdf_key => $mapping) {
    if ($mapping instanceof TextFieldMapping) {
      $fields[$pdf_key] = (string) $mapping;
    }
  }
  module_load_include('inc', 'fillpdf', 'xfdf');
  $xfdf_name = $template_uri . '.xfdf';
  $xfdf = create_xfdf(basename($xfdf_name), $fields);

  // Generate the file.
  $xfdf_file = file_save_data($xfdf, $xfdf_name, FileSystemInterface::EXISTS_RENAME);

  // @todo: Improve this approach when we turn $context into a value object.
  if (!isset($context['fid'])) {
    throw new InvalidArgumentException("pdftk requires \$context['fid'] to be set to the ID of the FillPDF Form so that it can check if encryption is configured. The merge was aborted because it was not set.");
  }
  $fillpdf_form = $this->entityTypeManager
    ->getStorage('fillpdf_form')
    ->load($context['fid']);

  // Configure PDF security.
  $arg_permissions = $arg_owner_password = $arg_user_password = '';
  $arg_pdftk_encryption = $fillpdf_form->pdftk_encryption->value ? " {$fillpdf_form->pdftk_encryption->value}" : '';
  $permissions = $fillpdf_form->permissions
    ->getString();
  if ($permissions) {

    // ItemList::getString() returns "Item1, Item2", but we don't want commas.
    $arg_permissions = ' allow ' . str_replace(',', '', $permissions);
  }
  $owner_password = $fillpdf_form->owner_password->value;
  if ($owner_password) {
    $arg_owner_password = ' owner_pw ' . $this->shellManager
      ->escapeShellArg($owner_password);
  }
  $user_password = $fillpdf_form->user_password->value;
  if ($user_password) {
    $arg_user_password = ' user_pw ' . $this->shellManager
      ->escapeShellArg($user_password);
  }

  // Escape the template's and the XFDF file's realpath.
  $template_path = $this->shellManager
    ->escapeShellArg($this->fileSystem
    ->realpath($template_uri));
  $xfdf_path = $this->shellManager
    ->escapeShellArg($this->fileSystem
    ->realpath($xfdf_file
    ->getFileUri()));

  // Now feed this to pdftk and save the result to a variable.
  $pdftk_path = $this
    ->getPdftkPath();
  ob_start();
  $command = "{$pdftk_path} {$template_path} fill_form {$xfdf_path} output - " . ($context['flatten'] ? 'flatten drop_xfa' : '') . "{$arg_pdftk_encryption}{$arg_permissions}{$arg_owner_password}{$arg_user_password}";
  passthru($command);
  $data = ob_get_clean();
  if ($data === FALSE) {
    $this
      ->messenger()
      ->addError($this
      ->t('pdftk not properly installed. No PDF generated.'));
  }
  $xfdf_file
    ->delete();
  if ($data) {
    return $data;
  }
  return NULL;
}