Installing wkhtmltopdf 0.9.6 under FreeBSD
At my day job, our knowledge base software needs a specific version of wkhtmltopdf to work. Further, it needs the version built
against a specially patched set of QT libraries in order to do certain critical things (for example, to run headless). If you run
./wkhtmltopdf against a non-patched version, it will issue this
Reduced Functionality: This version of wkhtmltopdf has been compiled against a version of QT without the wkhtmltopdf patches. Therefore some features are missing, if you need these features please use the static version. Currently the list of features only supported with patch QT includes: * Printing more then one HTML document into a PDF file. * Running without an X11 server. * Adding a document outline to the PDF file. * Adding headers and footers to the PDF file. * Generating a table of contents. * Adding links in the generated PDF file. * Printing using the screen media-type. * Disabling the smart shrink feature of webkit.
FreeBSD has a port for wkhtmltopdf, which includes a patched QT, but version 0.9.6 will not build against this patched QT. Thus, we need to build both from scratch.
Further, when attempting to build the patched QT from source, there are at least two active bugs.
This is a similar error reported with another piece of software:
Patches in this bug listing tell us how to fix it, mostly (the patches are not FreeBSD specific, but the exact nature of the fix is easy to glean).
Second, WebKit seems to suffer a bug (referenced here) whereby it will pick up the system header files (even if you've told it to build with the builtin versions), so it will believe that the list of available functions is off, with an error like:
: undefined reference to `png_set_longjmp_fn' /data/home/dmahoney/wkqt/lib/libQtGui.a(qpnghandler.o)(.text+0x1b7c): In function `QPngHandlerPrivate::readPngHeader()': : undefined reference to `png_set_longjmp_fn' /data/home/dmahoney/wkqt/lib/libQtGui.a(qpnghandler.o)(.text+0x23a0): In function `QPngHandlerPrivate::readPngImage(QImage*)': : undefined reference to `png_set_longjmp_fn'
It's my hope that I can show how to get this tool, at this specific version, to install, and help others who may hit this. I'm also pasting in the actual compiler output such that people can google for it and find this entry.
It's probably a good idea to make and install this port anyway as it will pull in a bunch of X11 and font dependencies that we may later need, but once it's installed, it's probably safe to "make deinstall" it.
Part 1: wkhtmltopdf-qt
Get the wkhtmltopdf source
We grab the source for wkhtmltopdf at this phase because we need a file from it to get the build arguments for qt. Grab wkhtmltopdf version 0.9.6 from google code downloads page. Since it is a deprecated release, it will not be in the default list. Go here Select "All Downloads" and search for 0.9.6, to get:
Grab this with "fetch" or "wget" or just scp it over to the system.
Get the wkhtmltopdf-qt version you need
There was, at one time, a git repository at: git://gitorious.org/+wkhtml2pdf/qt/
Luckily, the repository has been mirrored onto Github.
Clone wkhtmltopdf-qt from this github page, then isolate it down to the 0.9.6 release tag.
%git clone git://github.com/jcsalterego/wkhtmltopdf-qt.git Cloning into wkhtmltopdf-qt... remote: Counting objects: 563729, done. remote: Compressing objects: 100% (104214/104214), done. remote: Total 563729 (delta 455301), reused 563645 (delta 455222) Receiving objects: 100% (563729/563729), 376.20 MiB | 2.34 MiB/s, done. Resolving deltas: 100% (455301/455301), done. %
(the above took about ten minutes on my very fast connection)
You can see that there are several "tagged" releases of code in this repository:
%git tag -l wkhtmltopdf-0.8.3 wkhtmltopdf-0.9.0-beta3 wkhtmltopdf-0.9.6 %
So you're going to want to reduce the repository to that version:
%git checkout wkhtmltopdf-0.9.6 Checking out files: 100% (22888/22888), done. Note: checking out 'wkhtmltopdf-0.9.6'. You are in 'detached HEAD' state. You can look around, make experimental changes and commit them, and you can discard any commits you make in this state without impacting any branches by performing another checkout. If you want to create a new branch to retain commits you create, you may do so (now or later) by using -b with the checkout command again. Example: git checkout -b new_branch_name HEAD is now at e63d059... Fix pdf title writeout %
(this took 3-5 minutes) Welcome to 2010!!!
Without the output, the two commands you really need are:
git clone git://github.com/jcsalterego/wkhtmltopdf-qt.git git checkout wkhtmltopdf-0.9.6
Patch wkhtmltopdf ### :
Manually apply this patch, but add a line for PLATFORM_FREEBSD.
So, on line 721 of
#if PLATFORM(X86_64) && (PLATFORM(DARWIN) || PLATFORM(LINUX) || PLATFORM(SOLARIS) || PLATFORM(HPUX))
#if PLATFORM(X86_64) && (PLATFORM(DARWIN) || PLATFORM(LINUX) || PLATFORM(SOLARIS) || PLATFORM(FREEBSD) || PLATFORM(HPUX))
Do the same on line 712 of
Per the build guide, you can get the configure arguments by doing
../wkhtmltopdf/static_qt_conf_linux | sed -re
Then, you get to go into a text editor and put them all on one line.
./configure -release -static -fast -no-exceptions -no-accessibility -no-stl -no-sql-ibase -no-sql-mysql -no-sql-odbc -no-sql-psql \ -no-sql-sqlite -no-sql-sqlite2 -no-qt3support -no-xmlpatterns -no-phonon -no-phonon-backend -webkit -no-scripttools -no-mmx \ -no-3dnow -no-sse -no-sse2 -qt-zlib -qt-gif -qt-libtiff -qt-libpng -qt-libmng -qt-libjpeg -graphicssystem raster -opensource \ -nomake tools -nomake examples -nomake demos -nomake docs -nomake translations -no-opengl -no-dbus -no-multimedia -fast -openssl \ -largefile -rpath -no-nis -no-cups -no-iconv -no-pch -no-gtkstyle -no-nas-sound -no-sm -no-xshape -no-xinerama -no-xcursor \ -no-xfixes -no-xrandr -no-xrender -no-mitshm -no-xinput -no-xkb -no-glib -no-openvg -no-opengl -no-xsync -no-svg -prefix "../wkqt"
(later amended to add
-system-png instead of
-libqt-png, due to a QT bug whereby QT will use the system header file but build
against the bundled lib, thus causing linking errors)
Once you type this, you'll have to type "yes" to accept the GPL. (Yes, GPL code with a EULA). It will run for a few minutes.
Build the library
If all went well, all you should need to do is:
gmake -j3 && gmake install
When this is done, you should have a "wkqt" directory just above your build dir, that has a ./bin/qmake in it (along with some other stuff).
Building wkhtmltopdf itself
This one is shockingly easy, presuming all the rest of the code worked:
cd ../wkhtmltopdf ../bin/wkqt/qmake
(I get a warning about
WARNING: /data/home/dmahoney/wkhtmltopdf/, but this seems to be mostly harmless since we're building a headless version.
Then, type make. It should spin for a few more minutes, and if all went correctly, you should have a wkhtmltopdf file in your home directory.
Test it with
./wkhtmltopdf and see if you get a basic help page. If
you do, you're probably in business!
If you're going through all this pain for Knowledge Base Manager Pro, copy it to the appropriate directory in your web root, and test it out.
If you're doing this for some other reason -- like, "you like running old, hard to compile code when there's an easy install option", there are self-help groups and therapy for this sort of thing :)
You probably don't need the "wkqt" directory any more, and you can probably also delete all the source files after that.
Compiling Guide: http://code.google.com/p/wkhtmltopdf/
About the author
Dan Mahoney is a sysadmin in the San Francsico Bay Area. He fixes computers.