Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[UPDATE] Update and modify some builder tests #54

Merged
merged 6 commits into from
Jun 1, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions phpstan.neon
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,10 @@ parameters:
- 'src'
- 'tests'
ignoreErrors:
-
message: "#^Cannot use array destructuring on array\\<int, string\\|null\\>\\|null\\.$#"
count: 1
path: src/DataCollector/GotenbergDataCollector.php
-
message: "#^Method Sensiolabs\\\\GotenbergBundle\\\\Tests\\\\Kernel\\:\\:configureContainer\\(\\) is unused\\.$#"
count: 1
Expand Down
2 changes: 1 addition & 1 deletion src/Builder/Pdf/AbstractPdfBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ abstract class AbstractPdfBuilder implements PdfBuilderInterface
private string $headerDisposition = HeaderUtils::DISPOSITION_INLINE;

/**
* @var array<string, (\Closure(mixed): array<string, array<string|int ,mixed>|non-empty-string|int|float|bool|DataPart>)>
* @var array<string, (\Closure(mixed): array<string, array<string|int, mixed>|non-empty-string|int|float|bool|DataPart>)>
*/
private array $normalizers;

Expand Down
9 changes: 5 additions & 4 deletions src/Builder/Pdf/LibreOfficePdfBuilder.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace Sensiolabs\GotenbergBundle\Builder\Pdf;

use Sensiolabs\GotenbergBundle\Enum\PdfFormat;
use Sensiolabs\GotenbergBundle\Exception\InvalidBuilderConfiguration;
use Sensiolabs\GotenbergBundle\Exception\MissingRequiredFieldException;
use Symfony\Component\Mime\Part\DataPart;
Expand Down Expand Up @@ -63,9 +64,9 @@ public function nativePageRanges(string $range): self
/**
* Convert the resulting PDF into the given PDF/A format.
*/
public function pdfFormat(string $format): self
public function pdfFormat(PdfFormat $format): self
{
$this->formFields['pdfa'] = $format;
$this->formFields['pdfa'] = $format->value;

return $this;
}
Expand Down Expand Up @@ -151,11 +152,11 @@ protected function getEndpoint(): string
private function addConfiguration(string $configurationName, mixed $value): void
{
match ($configurationName) {
'pdf_format' => $this->pdfFormat($value),
'pdf_format' => $this->pdfFormat(PdfFormat::from($value)),
'pdf_universal_access' => $this->pdfUniversalAccess($value),
'landscape' => $this->landscape($value),
'native_page_ranges' => $this->nativePageRanges($value),
'fail_on_console_exceptions' => $this->merge($value),
'merge' => $this->merge($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
2 changes: 1 addition & 1 deletion src/Client/GotenbergClient.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ public function __construct(private string $gotenbergBaseUri, private HttpClient
public function call(string $endpoint, array $multipartFormData, array $headers = []): GotenbergResponse
{
$formData = new FormDataPart($multipartFormData);
$headers = \array_merge($headers, $this->prepareHeaders($formData));
$headers = array_merge($headers, $this->prepareHeaders($formData));

$response = $this->client->request(
'POST',
Expand Down
10 changes: 5 additions & 5 deletions src/DependencyInjection/Configuration.php
Original file line number Diff line number Diff line change
Expand Up @@ -204,7 +204,7 @@ private function addChromiumPdfOptionsNode(NodeBuilder $treeBuilder): void
->end()
->enumNode('emulated_media_type')
->info('The media type to emulate, either "screen" or "print" - default "print". https://gotenberg.dev/docs/routes#emulated-media-type')
->values(\array_map(static fn (EmulatedMediaType $case): string => $case->value, EmulatedMediaType::cases()))
->values(array_map(static fn (EmulatedMediaType $case): string => $case->value, EmulatedMediaType::cases()))
->defaultNull()
->end()
->arrayNode('cookies')
Expand Down Expand Up @@ -273,7 +273,7 @@ private function addChromiumPdfOptionsNode(NodeBuilder $treeBuilder): void
->end()
->enumNode('pdf_format')
->info('Convert the resulting PDF into the given PDF/A format - default None. https://gotenberg.dev/docs/routes#pdfa-chromium')
->values(\array_map(static fn (PdfFormat $case): string => $case->value, PdfFormat::cases()))
->values(array_map(static fn (PdfFormat $case): string => $case->value, PdfFormat::cases()))
->defaultNull()
->end()
->booleanNode('pdf_universal_access')
Expand Down Expand Up @@ -301,7 +301,7 @@ private function addChromiumScreenshotOptionsNode(NodeBuilder $treeBuilder): voi
->end()
->enumNode('format')
->info('The image compression format, either "png", "jpeg" or "webp" - default png. https://gotenberg.dev/docs/routes#screenshots-route')
->values(\array_map(static fn (ScreenshotFormat $case): string => $case->value, ScreenshotFormat::cases()))
->values(array_map(static fn (ScreenshotFormat $case): string => $case->value, ScreenshotFormat::cases()))
->defaultNull()
->end()
->integerNode('quality')
Expand Down Expand Up @@ -340,7 +340,7 @@ private function addChromiumScreenshotOptionsNode(NodeBuilder $treeBuilder): voi
->end()
->enumNode('emulated_media_type')
->info('The media type to emulate, either "screen" or "print" - default "print". https://gotenberg.dev/docs/routes#emulated-media-type')
->values(\array_map(static fn (EmulatedMediaType $case): string => $case->value, EmulatedMediaType::cases()))
->values(array_map(static fn (EmulatedMediaType $case): string => $case->value, EmulatedMediaType::cases()))
->defaultNull()
->end()
->arrayNode('cookies')
Expand Down Expand Up @@ -437,7 +437,7 @@ private function addPdfOfficeNode(): NodeDefinition
->end()
->enumNode('pdf_format')
->info('Convert the resulting PDF into the given PDF/A format - default None. https://gotenberg.dev/docs/routes#pdfa-chromium')
->values(\array_map(static fn (PdfFormat $case): string => $case->value, PdfFormat::cases()))
->values(array_map(static fn (PdfFormat $case): string => $case->value, PdfFormat::cases()))
->defaultNull()
->end()
->booleanNode('pdf_universal_access')
Expand Down
3 changes: 1 addition & 2 deletions src/Twig/GotenbergAssetExtension.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@

use Sensiolabs\GotenbergBundle\Builder\Pdf\AbstractChromiumPdfBuilder;
use Sensiolabs\GotenbergBundle\Builder\Screenshot\AbstractChromiumScreenshotBuilder;
use Symfony\Component\Mime\Part\File;
use Twig\Extension\AbstractExtension;
use Twig\TwigFunction;

Expand All @@ -30,6 +29,6 @@ public function getAssetUrl(array $context, string $path): string

$builder->addAsset($path);

return (new File($path))->getFilename();
return basename($path);
}
}
17 changes: 13 additions & 4 deletions tests/Builder/AbstractBuilderTestCase.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
use PHPUnit\Framework\TestCase;
use Sensiolabs\GotenbergBundle\Client\GotenbergClientInterface;
use Sensiolabs\GotenbergBundle\Formatter\AssetBaseDirFormatter;
use Sensiolabs\GotenbergBundle\Twig\GotenbergAssetExtension;
use Symfony\Component\Filesystem\Filesystem;
use Symfony\Component\Mime\Part\DataPart;
use Twig\Environment;
Expand All @@ -26,7 +27,10 @@ abstract class AbstractBuilderTestCase extends TestCase

public static function setUpBeforeClass(): void
{
self::$twig = new Environment(new FilesystemLoader(self::FIXTURE_DIR));
self::$twig = new Environment(new FilesystemLoader(self::FIXTURE_DIR), [
'strict_variables' => true,
]);
self::$twig->addExtension(new GotenbergAssetExtension());
self::$assetBaseDirFormatter = new AssetBaseDirFormatter(new Filesystem(), self::FIXTURE_DIR, self::FIXTURE_DIR);
}

Expand All @@ -38,15 +42,20 @@ protected function setUp(): void
/**
* @param array<mixed> $data
*/
protected function assertFile(array $data, string $filename, string $expectedContent): void
protected static function assertFile(array $data, string $filename, string $contentType = 'text/html', string|null $expectedContent = null): void
{
self::assertArrayHasKey('files', $data);

$file = $data['files'];

self::assertInstanceOf(DataPart::class, $file);

self::assertSame($expectedContent, $file->getBody());
self::assertSame($filename, $file->getFilename());
self::assertSame($contentType, $file->getContentType());

if (null !== $expectedContent) {
self::assertSame($expectedContent, $file->getBody());
}

iterator_to_array($file->bodyToIterable()); // Check if path is correct
}
}
168 changes: 166 additions & 2 deletions tests/Builder/Pdf/AbstractChromiumPdfBuilderTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,18 +6,23 @@

use PHPUnit\Framework\Attributes\CoversClass;
use PHPUnit\Framework\Attributes\DataProvider;
use PHPUnit\Framework\Attributes\TestDox;
use PHPUnit\Framework\Attributes\UsesClass;
use Sensiolabs\GotenbergBundle\Builder\Pdf\AbstractChromiumPdfBuilder;
use Sensiolabs\GotenbergBundle\Builder\Pdf\AbstractPdfBuilder;
use Sensiolabs\GotenbergBundle\Enum\PaperSizeInterface;
use Sensiolabs\GotenbergBundle\Enum\PdfFormat;
use Sensiolabs\GotenbergBundle\Enum\Unit;
use Sensiolabs\GotenbergBundle\Exception\PdfPartRenderingException;
use Sensiolabs\GotenbergBundle\Formatter\AssetBaseDirFormatter;
use Sensiolabs\GotenbergBundle\Tests\Builder\AbstractBuilderTestCase;
use Sensiolabs\GotenbergBundle\Twig\GotenbergAssetExtension;

#[CoversClass(AbstractChromiumPdfBuilder::class)]
#[UsesClass(AbstractPdfBuilder::class)]
#[UsesClass(Unit::class)]
#[UsesClass(AssetBaseDirFormatter::class)]
#[UsesClass(GotenbergAssetExtension::class)]
class AbstractChromiumPdfBuilderTest extends AbstractBuilderTestCase
{
public static function configurationIsCorrectlySetProvider(): \Generator
Expand Down Expand Up @@ -100,6 +105,7 @@ public static function configurationIsCorrectlySetProvider(): \Generator
* @param array<mixed> $expected
*/
#[DataProvider('configurationIsCorrectlySetProvider')]
#[TestDox('Configuration "$_dataName" is correctly set')]
public function testConfigurationIsCorrectlySet(string $key, mixed $value, array $expected): void
{
$builder = $this->getChromiumPdfBuilder();
Expand Down Expand Up @@ -176,7 +182,7 @@ public function testPdfFormatCanBeReset(): void
self::assertEquals([], $builder->getMultipartFormData());
}

public function testHeaderIsCorrectlyRendered(): void
public function testTwigHeaderIsCorrectlyRendered(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->header('templates/header.html.twig', ['name' => 'World']);
Expand All @@ -197,7 +203,165 @@ public function testHeaderIsCorrectlyRendered(): void

HTML;

$this->assertFile($data, 'header.html', $expected);
self::assertFile($data, 'header.html', expectedContent: $expected);
}

public function testTwigFooterIsCorrectlyRendered(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->footer('templates/footer.html.twig', ['name' => 'World']);

$data = $builder->getMultipartFormData()[0];

$expected = <<<HTML
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>My Footer</title>
</head>
<body>
<h1>Hello World!</h1>
</body>
</html>

HTML;

self::assertFile($data, 'footer.html', expectedContent: $expected);
}

public function testPlainFileHeaderIsCorrectlyRendered(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->headerFile('files/header.html');

$data = $builder->getMultipartFormData()[0];

$expected = <<<HTML
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>My Header</title>
</head>
<body>
<h1>Hello Header</h1>
</body>
</html>

HTML;

self::assertFile($data, 'header.html', expectedContent: $expected);
}

public function testPlainFileFooterIsCorrectlyRendered(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->footerFile('files/footer.html');

$data = $builder->getMultipartFormData()[0];

$expected = <<<HTML
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8" />
<title>My Footer</title>
</head>
<body>
<h1>Hello Footer</h1>
</body>
</html>

HTML;

self::assertFile($data, 'footer.html', expectedContent: $expected);
}

public function testAssetsCanBeAddedUsingPhp(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->assets(
self::FIXTURE_DIR.'/assets/logo.png',
self::FIXTURE_DIR.'/assets/logo.png',
self::FIXTURE_DIR.'/assets/other_logo.png',
);

$data = $builder->getMultipartFormData();

self::assertCount(2, $data);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

self:: or $this->, that is the question.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No diff on phpunit side. Which one do you prefer ?

Copy link
Contributor

@Jean-Beru Jean-Beru May 31, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I does not matter to me.

toss a coin
...
wait a bit for suspens
...
STATIC !

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I will follow your lead

gandalf

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done


$logo = $data[0];
self::assertFile($logo, 'logo.png', 'image/png');

$otherLogo = $data[1];
self::assertFile($otherLogo, 'other_logo.png', 'image/png');
}

public function testAssetsCanBeAddedUsingTwig(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->header('templates/header_with_asset.html.twig', ['name' => 'World']);

$data = $builder->getMultipartFormData();

self::assertCount(2, $data);

$logo = $data[0];
self::assertFile($logo, 'logo.png', 'image/png');
}

public function testCanAddCookies(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->addCookies([
[
'name' => 'MyCookie',
'value' => 'Chocolate',
'domain' => 'sensiolabs.com',
],
[
'name' => 'MyCookie',
'value' => 'Vanilla',
Jean-Beru marked this conversation as resolved.
Show resolved Hide resolved
'domain' => 'sensiolabs.com',
],
]);

$data = $builder->getMultipartFormData();

self::assertEquals([
'cookies' => '[{"name":"MyCookie","value":"Vanilla","domain":"sensiolabs.com"}]',
], $data[0]);
}

public function testCanAddExtraHttpHeaders(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->addExtraHttpHeaders([
'MyHeader' => 'SomeValue',
]);
$builder->addExtraHttpHeaders([
'MyHeader' => 'SomeOtherValue',
]);

$data = $builder->getMultipartFormData();

self::assertEquals([
'extraHttpHeaders' => '{"MyHeader":"SomeOtherValue"}',
], $data[0]);
}

public function testCanAddMetadata(): void
{
$builder = $this->getChromiumPdfBuilder();
$builder->addMetadata('Author', 'Me');
$builder->addMetadata('Author', 'SensioLabs');

$data = $builder->getMultipartFormData();

self::assertEquals([
'metadata' => '{"Author":"SensioLabs"}',
], $data[0]);
}

public function testThrowIfTwigNotAvailable(): void
Expand Down
Loading