pdf-docEin Gastbeitrag von : „Johannes Laier“.

Viele Webseiten und Online-Shops generieren automatisch PDF-Dateien für beispielsweise Rechnungen automatisiert mit PHP. Häufig werde ich gefragt wie sich so etwas realisieren lässt, deshalb habe ich hierzu eine Anleitung erstellt.
Wir erstellen eine Klasse welcher man mit PHP generierten HTML Code übergeben kann und nutzen das Tool wkhtmltopdf um daraus eine PDF-Datei zu erzeugen. Hier erfahrt ihr wie ihr dieses Tool auf eurem Server installieren könnt.

 

Um zu erfahren mit welchen Parametern das Konsolen-Programm wkhtmltopdf funktioniert öffnen wir nach der Installation eine neue Konsole und geben folgenden Befehl ein um alle Parameter aufgelistet zu bekommen:

$ wkhtmltopdf –help
wkhtmltopdf –help
Name:
wkhtmltopdf 0.12.2.1 (with patched qt)
Synopsis:
wkhtmltopdf [GLOBAL OPTION]… [OBJECT]… <output file>

Um eine PDF Datei aus einer URL zu erzeugen, können wir folgendes Kommando nutzen:

$ wkhtmltopdf http://your-domain.com output.pdf

Hat das Programm ohne Fehler seine Arbeit verrichtet, erscheint nun eine output.pdf-Datei welche die Webseite beinhaltet. Nun müssen wir herausfinden wie wir mit PHP Parameter an das Tool übergeben können. Hierzu nutzen wir so genannte Pipes. Mit ihnen können wir Infos an einen Prozess übergeben. Wkhtmltopdf kann mit einem „-“ Zeichen anstelle der URL angewiesen werden SDTIN anstelle eines Parameters auszuwerten.

$ echo “<h1>Hallo Welt!</h1>“ | wkhtmltopdf – output.pdf

Mithilfe des echo Kommandos und der Pipe „|“ übergeben wir unseren HTML Code an das Tool wkhtmltopdf welches, wir mit der Option „-“ dazu angewiesen haben aus STDIN zu lesen. Nach der Ausführung des Befehls sollte eine output.pdf Datei mit dem Inhalt „Hallo Welt!“ erscheinen.

Es wäre möglich mit der PHP system() Funktion das oben gelistete Kommando auszuführen und den Inhalt der output.pdf auszulesen und anschließend an den Benutzer zurück zu geben:

 

PHP bietet hierzu jedoch eine elegantere Möglichkeit an. Mit der Funktion proc_open() können Prozesse gestartet werden und File-Descriptoren übergeben werden. Mit diesen Descriptoren können wir Informationen an das gestartete Tool übergeben.

$descriptorspec = array(
0 => array("pipe", "r"),  // STDIN ist eine Pipe, von der das Child liest
1 => array("pipe", "w"),  // STDOUT ist eine Pipe, in die das Child schreibt
2 => array("pipe", "w") // STDERR ist eine Pipe, in die dass Child seine Fehler schreibt.
);
$process = proc_open('/usr/local/bin/wkhtmltopdf -q - -', $descriptorspec, $pipes, "/", array());
if (is_resource($process)) {
fwrite($pipes[0], $this->html);
fclose($pipes[0]);
$pdf = stream_get_contents($pipes[1]);
@fclose($pipes[0]);
@fclose($pipes[1]);
@fclose($pipes[2]);
$return_value = proc_close($process);
return $pdf;
}

Mit der Option „-“ anstelle der Output-Datei Teilen wir wkhtmltopdf mit, das generierte PDF-Dokument in den STDOUT-Buffer zu schreiben. Der Quiet Parameter „-q“ gibt an, dass nur das erzeugte PDF-Dokument, und keine Meldungen über beispielsweise den Fortschritt des Tools, in den STDOUT-Buffer geschrieben wird.

Die File-Descriptoren können mit üblichen File-Funktionen fgets(), fwrite() und fclose() behandelt werden.

Nachdem das Tool ordnungsgemäß gestartet und mit Daten befüllt wurde, nutzen wir die PHP Funktion stream_get_contents() um das erzeugte Dokument mithilfe von zu lesen.

Das die fertige Klasse steht auf Github unter MIT-Lizenz zur freien Verfügung.