Skip to content

Commit

Permalink
Fix Markdown screenshot URL + Add headers to client call + Some renam…
Browse files Browse the repository at this point in the history
…ing + Add metadata to files + Units in paper size (#41)

* [FIX] Markdown screenshot URL
* [FEATURE] Add headers to client call
* [UPDATE] Rename some classes 
* [FEATURE] Add units
* [UPDATE] Add Metadata for PDF files
* [UPDATE] Use ScreenshotFormat enum
  • Loading branch information
Neirda24 authored May 30, 2024
1 parent fc74cd5 commit b3e6d6c
Show file tree
Hide file tree
Showing 27 changed files with 321 additions and 118 deletions.
8 changes: 4 additions & 4 deletions docs/custom-builders.rst
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ Alternatively, you can use the BodyPart enum to rename your file on the fly.

.. code-block:: php
use Sensiolabs\GotenbergBundle\Enum\PdfPart;
use Sensiolabs\GotenbergBundle\Enum\Part;
use Symfony\Component\Mime\Part\DataPart;
use Symfony\Component\Mime\Part\File;
Expand All @@ -54,7 +54,7 @@ Alternatively, you can use the BodyPart enum to rename your file on the fly.
public function content(string $path): self
{
$dataPart = DataPart::fromPath($path, PdfPart::BodyPart->value);
$dataPart = DataPart::fromPath($path, Part::BodyPart->value);
$this->multipartFormData[] = [
'files' => $dataPart,
Expand Down Expand Up @@ -92,7 +92,7 @@ and use everything you want.

.. code-block:: php
use Sensiolabs\GotenbergBundle\Enum\PdfPart;
use Sensiolabs\GotenbergBundle\Enum\Part;
use Symfony\Component\Mime\Part\DataPart;
use Symfony\Component\Mime\Part\File;
Expand All @@ -107,7 +107,7 @@ and use everything you want.
public function content(string $path): self
{
$dataPart = DataPart::fromPath($path, PdfPart::BodyPart->value);
$dataPart = DataPart::fromPath($path, Part::BodyPart->value);
$this->multipartFormData[] = [
'files' => $dataPart,
Expand Down
127 changes: 91 additions & 36 deletions src/Builder/Pdf/AbstractChromiumPdfBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,11 @@
namespace Sensiolabs\GotenbergBundle\Builder\Pdf;

use Sensiolabs\GotenbergBundle\Client\GotenbergClientInterface;
use Sensiolabs\GotenbergBundle\Enum\PaperSize;
use Sensiolabs\GotenbergBundle\Enum\PaperSizeInterface;
use Sensiolabs\GotenbergBundle\Enum\PdfPart;
use Sensiolabs\GotenbergBundle\Enum\Part;
use Sensiolabs\GotenbergBundle\Enum\PdfFormat;
use Sensiolabs\GotenbergBundle\Enum\Unit;
use Sensiolabs\GotenbergBundle\Exception\InvalidBuilderConfiguration;
use Sensiolabs\GotenbergBundle\Exception\PdfPartRenderingException;
use Sensiolabs\GotenbergBundle\Formatter\AssetBaseDirFormatter;
Expand Down Expand Up @@ -36,6 +39,18 @@ public function setConfigurations(array $configurations): static
return $this;
}

/**
* Define whether to print the entire content in one single page.
*
* If the singlePage form field is set to true, it automatically overrides the values from the paperHeight and nativePageRanges form fields.
*/
public function singlePage(bool $bool = true): static
{
$this->formFields['singlePage'] = $bool;

return $this;
}

/**
* Overrides the default paper size, in inches.
*
Expand All @@ -55,32 +70,32 @@ public function setConfigurations(array $configurations): static
*
* @see https://gotenberg.dev/docs/routes#page-properties-chromium
*/
public function paperSize(float $width, float $height): static
public function paperSize(float $width, float $height, Unit $unit = Unit::Inches): static
{
$this->paperWidth($width);
$this->paperHeight($height);
$this->paperWidth($width, $unit);
$this->paperHeight($height, $unit);

return $this;
}

public function paperStandardSize(PaperSizeInterface $paperSize): static
{
$this->paperWidth($paperSize->width());
$this->paperHeight($paperSize->height());
$this->paperWidth($paperSize->width(), $paperSize->unit());
$this->paperHeight($paperSize->height(), $paperSize->unit());

return $this;
}

public function paperWidth(float $width): static
public function paperWidth(float $width, Unit $unit = Unit::Inches): static
{
$this->formFields['paperWidth'] = $width;
$this->formFields['paperWidth'] = $width.$unit->value;

return $this;
}

public function paperHeight(float $height): static
public function paperHeight(float $height, Unit $unit = Unit::Inches): static
{
$this->formFields['paperHeight'] = $height;
$this->formFields['paperHeight'] = $height.$unit->value;

return $this;
}
Expand All @@ -90,40 +105,40 @@ public function paperHeight(float $height): static
*
* @see https://gotenberg.dev/docs/routes#page-properties-chromium
*/
public function margins(float $top, float $bottom, float $left, float $right): static
public function margins(float $top, float $bottom, float $left, float $right, Unit $unit = Unit::Inches): static
{
$this->marginTop($top);
$this->marginBottom($bottom);
$this->marginLeft($left);
$this->marginRight($right);
$this->marginTop($top, $unit);
$this->marginBottom($bottom, $unit);
$this->marginLeft($left, $unit);
$this->marginRight($right, $unit);

return $this;
}

public function marginTop(float $top): static
public function marginTop(float $top, Unit $unit = Unit::Inches): static
{
$this->formFields['marginTop'] = $top;
$this->formFields['marginTop'] = $top.$unit->value;

return $this;
}

public function marginBottom(float $bottom): static
public function marginBottom(float $bottom, Unit $unit = Unit::Inches): static
{
$this->formFields['marginBottom'] = $bottom;
$this->formFields['marginBottom'] = $bottom.$unit->value;

return $this;
}

public function marginLeft(float $left): static
public function marginLeft(float $left, Unit $unit = Unit::Inches): static
{
$this->formFields['marginLeft'] = $left;
$this->formFields['marginLeft'] = $left.$unit->value;

return $this;
}

public function marginRight(float $right): static
public function marginRight(float $right, Unit $unit = Unit::Inches): static
{
$this->formFields['marginRight'] = $right;
$this->formFields['marginRight'] = $right.$unit->value;

return $this;
}
Expand Down Expand Up @@ -209,7 +224,7 @@ public function nativePageRanges(string $range): static
*/
public function header(string $template, array $context = []): static
{
return $this->withRenderedPart(PdfPart::HeaderPart, $template, $context);
return $this->withRenderedPart(Part::Header, $template, $context);
}

/**
Expand All @@ -220,23 +235,23 @@ public function header(string $template, array $context = []): static
*/
public function footer(string $template, array $context = []): static
{
return $this->withRenderedPart(PdfPart::FooterPart, $template, $context);
return $this->withRenderedPart(Part::Footer, $template, $context);
}

/**
* HTML file containing the header. (default None).
*/
public function headerFile(string $path): static
{
return $this->withPdfPartFile(PdfPart::HeaderPart, $path);
return $this->withPdfPartFile(Part::Header, $path);
}

/**
* HTML file containing the footer. (default None).
*/
public function footerFile(string $path): static
{
return $this->withPdfPartFile(PdfPart::FooterPart, $path);
return $this->withPdfPartFile(Part::Footer, $path);
}

/**
Expand Down Expand Up @@ -422,9 +437,15 @@ public function skipNetworkIdleEvent(bool $bool = true): static
*
* @See https://gotenberg.dev/docs/routes#pdfa-chromium.
*/
public function pdfFormat(string $format): static
public function pdfFormat(PdfFormat|null $format = null): static
{
$this->formFields['pdfa'] = $format;
if (null === $format) {
unset($this->formFields['pdfa']);

return $this;
}

$this->formFields['pdfa'] = $format->value;

return $this;
}
Expand All @@ -441,7 +462,33 @@ public function pdfUniversalAccess(bool $bool = true): static
return $this;
}

protected function withPdfPartFile(PdfPart $pdfPart, string $path): static
/**
* Resets the metadata.
*
* @see https://gotenberg.dev/docs/routes#metadata-chromium
* @see https://exiftool.org/TagNames/XMP.html#pdf
*
* @param array<string, mixed> $metadata
*/
public function metadata(array $metadata): static
{
$this->formFields['metadata'] = $metadata;

return $this;
}

/**
* The metadata to write.
*/
public function addMetadata(string $key, string $value): static
{
$this->formFields['metadata'] ??= [];
$this->formFields['metadata'][$key] = $value;

return $this;
}

protected function withPdfPartFile(Part $pdfPart, string $path): static
{
$dataPart = new DataPart(
new DataPartFile($this->asset->resolve($path)),
Expand All @@ -459,7 +506,7 @@ protected function withPdfPartFile(PdfPart $pdfPart, string $path): static
*
* @throws PdfPartRenderingException if the template could not be rendered
*/
protected function withRenderedPart(PdfPart $pdfPart, string $template, array $context = []): static
protected function withRenderedPart(Part $pdfPart, string $template, array $context = []): static
{
if (!$this->twig instanceof Environment) {
throw new \LogicException(sprintf('Twig is required to use "%s" method. Try to run "composer require symfony/twig-bundle".', __METHOD__));
Expand All @@ -478,15 +525,22 @@ protected function withRenderedPart(PdfPart $pdfPart, string $template, array $c

private function addConfiguration(string $configurationName, mixed $value): void
{
$splitAndParseStringWithUnit = static function (mixed $raw, callable $callback): void {
[$value, $unit] = sscanf((string) $raw, '%d%s') ?? throw new \InvalidArgumentException(sprintf('Unexpected value "%s", expected format is "%%d%%s"', $raw));

$callback((float) $value, Unit::tryFrom((string) $unit) ?? Unit::Inches);
};

match ($configurationName) {
'pdf_format' => $this->pdfFormat($value),
'single_page' => $this->singlePage($value),
'pdf_format' => $this->pdfFormat(PdfFormat::from($value)),
'pdf_universal_access' => $this->pdfUniversalAccess($value),
'paper_width' => $this->paperWidth($value),
'paper_height' => $this->paperHeight($value),
'margin_top' => $this->marginTop($value),
'margin_bottom' => $this->marginBottom($value),
'margin_left' => $this->marginLeft($value),
'margin_right' => $this->marginRight($value),
'margin_top' => $splitAndParseStringWithUnit($value, $this->marginTop(...)),
'margin_bottom' => $splitAndParseStringWithUnit($value, $this->marginBottom(...)),
'margin_left' => $splitAndParseStringWithUnit($value, $this->marginLeft(...)),
'margin_right' => $splitAndParseStringWithUnit($value, $this->marginRight(...)),
'prefer_css_page_size' => $this->preferCssPageSize($value),
'print_background' => $this->printBackground($value),
'omit_background' => $this->omitBackground($value),
Expand All @@ -501,6 +555,7 @@ private function addConfiguration(string $configurationName, mixed $value): void
'fail_on_http_status_codes' => $this->failOnHttpStatusCodes($value),
'fail_on_console_exceptions' => $this->failOnConsoleExceptions($value),
'skip_network_idle_event' => $this->skipNetworkIdleEvent($value),
'metadata' => $this->metadata($value),
default => throw new InvalidBuilderConfiguration(sprintf('Invalid option "%s": no method does not exist in class "%s" to configured it.', $configurationName, static::class)),
};
}
Expand Down
13 changes: 8 additions & 5 deletions src/Builder/Pdf/AbstractPdfBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

use Sensiolabs\GotenbergBundle\Client\GotenbergClientInterface;
use Sensiolabs\GotenbergBundle\Client\GotenbergResponse;
use Sensiolabs\GotenbergBundle\Enum\PdfPart;
use Sensiolabs\GotenbergBundle\Enum\Part;
use Sensiolabs\GotenbergBundle\Exception\JsonEncodingException;
use Sensiolabs\GotenbergBundle\Formatter\AssetBaseDirFormatter;
use Symfony\Component\HttpFoundation\File\File;
Expand Down Expand Up @@ -38,20 +38,23 @@ public function __construct(
'assets' => static function (array $value): array {
return ['files' => $value];
},
PdfPart::HeaderPart->value => static function (DataPart $value): array {
Part::Header->value => static function (DataPart $value): array {
return ['files' => $value];
},
PdfPart::BodyPart->value => static function (DataPart $value): array {
Part::Body->value => static function (DataPart $value): array {
return ['files' => $value];
},
PdfPart::FooterPart->value => static function (DataPart $value): array {
Part::Footer->value => static function (DataPart $value): array {
return ['files' => $value];
},
'failOnHttpStatusCodes' => function (mixed $value): array {
return $this->encodeData('failOnHttpStatusCodes', $value);
},
'cookies' => function (mixed $value): array {
return $this->encodeData('cookies', array_values($value));
return $this->encodeData('cookies', \array_values($value));
},
'metadata' => function (mixed $value): array {
return $this->encodeData('metadata', $value);
},
];
}
Expand Down
8 changes: 4 additions & 4 deletions src/Builder/Pdf/HtmlPdfBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

namespace Sensiolabs\GotenbergBundle\Builder\Pdf;

use Sensiolabs\GotenbergBundle\Enum\PdfPart;
use Sensiolabs\GotenbergBundle\Enum\Part;
use Sensiolabs\GotenbergBundle\Exception\MissingRequiredFieldException;
use Sensiolabs\GotenbergBundle\Exception\PdfPartRenderingException;

Expand All @@ -18,20 +18,20 @@ final class HtmlPdfBuilder extends AbstractChromiumPdfBuilder
*/
public function content(string $template, array $context = []): self
{
return $this->withRenderedPart(PdfPart::BodyPart, $template, $context);
return $this->withRenderedPart(Part::Body, $template, $context);
}

/**
* The HTML file to convert into PDF.
*/
public function contentFile(string $path): self
{
return $this->withPdfPartFile(PdfPart::BodyPart, $path);
return $this->withPdfPartFile(Part::Body, $path);
}

public function getMultipartFormData(): array
{
if (!\array_key_exists(PdfPart::BodyPart->value, $this->formFields)) {
if (!\array_key_exists(Part::Body->value, $this->formFields)) {
throw new MissingRequiredFieldException('Content is required');
}

Expand Down
Loading

0 comments on commit b3e6d6c

Please sign in to comment.