Testing
The package provides a built-in fake for Laravel and implements a contract interface for easy mocking in any framework.
Laravel: WeasyPrint::fake()
The Laravel facade provides a fake() method that swaps the container binding with a test double. The fake records all calls without invoking the WeasyPrint binary and provides fluent assertion methods.
use WeasyPrint\Integration\Laravel\WeasyPrint;
it('generates an invoice PDF', function () {
$fake = WeasyPrint::fake();
$response = $this->get('/invoices/1/pdf');
$response->assertOk();
$fake->assertSourcePrepared()
->assertDownloaded('invoice.pdf');
});Available Assertions
All assertion methods are chainable.
assertBuilt()
Assert that build() was called. Optionally pass a count:
$fake->assertBuilt();
$fake->assertBuilt(times: 2);assertNotBuilt() / assertNothingBuilt()
Assert that build() was never called:
$fake->assertNotBuilt();assertSourcePrepared()
Assert that prepareSource() was called. Optionally pass a callback to inspect the source:
$fake->assertSourcePrepared();
$fake->assertSourcePrepared(function ($source) {
expect($source)->toBeInstanceOf(Source::class);
});assertDownloaded()
Assert that download() was called. Optionally assert the filename:
$fake->assertDownloaded();
$fake->assertDownloaded('invoice.pdf');assertInlined()
Assert that inline() was called. Optionally assert the filename:
$fake->assertInlined();
$fake->assertInlined('invoice.pdf');assertStreamed()
Assert that stream() was called. Optionally assert the filename and/or mode:
use WeasyPrint\Enums\StreamMode;
$fake->assertStreamed();
$fake->assertStreamed('invoice.pdf');
$fake->assertStreamed('invoice.pdf', mode: StreamMode::DOWNLOAD);assertAttachmentAdded()
Assert that addAttachment() was called. Optionally assert the path:
$fake->assertAttachmentAdded();
$fake->assertAttachmentAdded('/path/to/terms.pdf');assertXmpMetadataAdded()
Assert that addXmpMetadata() was called. Optionally assert the path:
$fake->assertXmpMetadataAdded();
$fake->assertXmpMetadataAdded('/path/to/metadata.xml');Fake Return Values
The fake returns sensible defaults so your code can run through its full path:
build()returns anOutputwith fake PDF datagetData()returns'%PDF-1.4 fake'stream(),download(),inline()return aStreamedResponsewith correct headersgetWeasyPrintVersion()returns'68.0'
Without a Framework
In a framework-agnostic setup, code against the WeasyPrint\Contracts\WeasyPrint interface and provide a mock in your tests:
use WeasyPrint\Contracts\WeasyPrint;
class InvoiceService
{
public function __construct(
private WeasyPrint $weasyprint,
) {}
public function generate(string $html): string
{
return $this->weasyprint
->prepareSource($html)
->getData();
}
}Then in your test:
$mock = Mockery::mock(WeasyPrint::class);
$mock->shouldReceive('prepareSource')
->with('<h1>Invoice</h1>')
->once()
->andReturnSelf();
$mock->shouldReceive('getData')
->once()
->andReturn('fake-pdf-data');
$service = new InvoiceService($mock);
$result = $service->generate('<h1>Invoice</h1>');
expect($result)->toBe('fake-pdf-data');You can also use the FakeWeasyPrint class directly without the facade:
use WeasyPrint\Testing\FakeWeasyPrint;
$fake = new FakeWeasyPrint();
$service = new InvoiceService($fake);
$service->generate('<h1>Invoice</h1>');
$fake->assertSourcePrepared()
->assertBuilt();Integration Testing
To verify the full pipeline including the WeasyPrint binary, use the factory directly. Make sure WeasyPrint is installed in your CI environment:
use WeasyPrint\WeasyPrintFactory;
it('produces valid PDF output', function () {
$data = (new WeasyPrintFactory())
->prepareSource('<h1>Test</h1>')
->getData();
expect($data)->toStartWith('%PDF-');
});