I have written previously about signing Qt applications for Mac OS X. It all worked fine until I upgraded to Mac OS X 10.9.5, which broke my signing script. Those Apple chaps do love to break stuff. Grrr.
The problem appears to be that the directory structure of the app bundle has changed and the Qt4
macdeployqt command does not conform to the new layout (I believe this is also the case for Qt5). Oh joy. I managed to work out how to get it working again after a bit of digging around. The good news is that Apple have also made the
codesign command easier with a
--deep option to traverse and sign the whole bundle in a single command. About time.
So here is the basic process to build and sign your Qt .app on the latest versions of Mac OS X:
# deploy Qt frameworks into .app bundle
$QTDIR/bin/macdeployqt .app -verbose=1
# optionally delete unwanted framework and plugin folders, e.g.:
# rm -f -r <your_app>.app/Contents/Frameworks/QtDeclarative.framework
# rm -f -r <your_app>.app/Contents/PlugIns/sqldrivers
# correct .app bundle structure
python rebundle.py $QTDIR <your_app>.app
# sign .app bundle (including frameworks and plugins)
codesign --deep --force --verify --verbose --sign "Developer ID Application: " .app
# the 2 lines below are just for verification/diagnostics
otool -L <your_app>.app/Contents/MacOS/<your_app>
codesign --verify --verbose=4 <your_app>.app
(Sorry about the small font, but I wanted to avoid confusing line wraps).
I then invoke DropDmg to create a .dmg image file complete with licence and background image. This is all stuck it all in a bash script, which I can pretty much forget about it (until Apple break something else).
In the above
rebundle.py is a Python script written by some public spirited individual that can be downloaded from github (thank you, ‘kingcheez’). Note that you can just find and replace all the ‘5’ characters in the script by ‘4’ if you are still using Qt4.
The first time I ran my script I ended up with a whopping 50MB .app file. It turns out that the
cp -r commands in my script don’t preserve symbolic links. So you end up with 3 copies of each framework library. You can avoid this by using
cp -R instead.
On the subject of signing for Mac, Apple recently sent out an email stating:
Signatures created with OS X Mountain Lion 10.8.5 or earlier (v1 signatures) will be obsoleted and Gatekeeper will no longer recognize them. Users may receive a Gatekeeper warning and will need to exempt your app to continue using it. To ensure your apps will run without warning on updated versions of OS X, they must be signed on OS X Mavericks 10.9 or later (v2 signatures). … Apps signed with v2 signatures will work on older versions of OS X.
So you are going to have to start signing using 10.9, whether you like it or not.
** Update **
The Python script has gone from github. There was no licensing information or contact information in the script and it was published on the web. So I am assuming it was intended to be public domain (please contact me if you know otherwise). I have put a copy here. You can just find and replace ‘4’ with ‘5’ if you are using Qt 5.