#!/bin/bash # Copyright (c) 2019-2021 Jay Berkenbilt and Kurt Pfeifle # # This script is used to build an 'AppImage' from GitHub sources of # QPDF (see https://appimage.org/). It is used in CI, but it also # allows Linux users to build such an AppImage on their own systems. # Please read 'README.md' from the top level Git sources to see what # preconditions you must meet to build QPDF in general. The same apply # to build an AppImage. Then follow these three steps: # # 1. Clone Git sources: `git clone https://github.com/qpdf/qpdf.git git.qpdf` # 2. Change into git dir: `cd git.qpdf` # 3. Run this script: `bash appimage/build-appimage` # # The resulting AppImage will be placed in # './appimage/build/QPDF-x86_64.AppImage'. Read the output of the # script for hints in case something goes wrong. # # You may pass custom options for the configure step by setting them # into the 'CUSTOM_CONFIGURE' environment variable and exporting it # before running this script. For example: # # export CUSTOM_CONFIGURE=" --enable-test-compare-images [--more-other-options]" # # ATTENTION: # # 1. To build the AppImage you should have a working internet # connection. Reason: the script downloads the most recent # 'linuxdeployqt' utility for building the AppImage. # 2. If you build the AppImage on a too recent Linux distribution, # it may only work on the exact distribution you build it on. For # an AppImage to work on a wide range of different distributions # from the last 3-4 years if should be built on the oldest # supported Ubuntu LTS release. set -ex # Support for signing the AppImage (only by original maintainer): sign= if [ "x$1" == "x--sign" ]; then sign=--sign fi # Check Ubuntu Distribution _osversion=$(cat /etc/os-release | grep PRETTY_NAME | awk -F'=' '{print $2}' | sed 's#"##g') # Warn users building the AppImage locally: if [[ ! $_osversion =~ Ubuntu\ 18.04.*\ LTS ]]; then set +x echo "" # 0 1 2 3 4 5 6 7 # 01234567890123456789012345678901234567890123456789012345678901234567890123456789 echo "+===========================================================================+" echo "|| WARNING: You are about to build a QPDF AppImage on a system which is ||" echo "|| NOT Ubuntu 18.04 LTS. ||" echo "|| ||" echo "|| It is recommended that you use a distribution that is at least a ||" echo "|| few years old to maximize the number of Linux distributions the ||" echo "|| resulting AppImage will work on. AppImages often don't work on ||" echo "|| distributions older than the one they were built on because of ||" echo "|| standard library differences. The oldest supported Ubuntu LTS is ||" echo "|| a good option. ||" echo "+===========================================================================+" echo "" set -x fi # From where do we run this script? here="$(dirname $(readlink -f "$0"))" top=$(dirname $here) # Move to root of GitHub sources: cd $top # Set 'appdir' environment variable name: appdir=$here/build/appdir # Clean up stuff from previous build attempts: rm -rf $here/build # Prepare build of QPDF from sources: ./configure --prefix=/usr --enable-werror \ --enable-crypto-gnutls --disable-implicit-crypto \ --enable-show-failed-test-output \ --enable-html-doc --enable-pdf-doc "$CUSTOM_CONFIGURE" # Build! make -j$(nproc) if [ "$SKIP_TESTS" = "" ]; then # Run built-in QPDF checks: make -k check fi # Prepare AppDir which is the basis for the AppImage: mkdir -p $appdir # Install build result into AppDir: make install DESTDIR=$appdir; find $appdir make doc-dist DOC_DEST=appdir/usr/share/doc/qpdf # Change into build directory: cd $here/build # Don't bundle developer stuff rm -rf appdir/usr/include appdir/usr/lib/pkgconfig appdir/usr/lib/*.{a,la,so} # Copy icon which is needed for desktop integration into place: for width in 64 128 256 512; do dir=appdir/usr/share/icons/hicolor/${width}x${width}/apps mkdir -p $dir inkscape -z -e qpdf-tmp.png -w $width -b white $top/logo/qpdf.svg convert qpdf-tmp.png -gravity center -background white -extent ${width}x${width} $dir/qpdf.png rm qpdf-tmp.png done # Copy .desktop and .appdata.xml metadata for desktop integration into place: for i in appdir/usr/share/applications; do mkdir -p $i cp $top/appimage/qpdf.desktop $i done for i in appdir/usr/share/metainfo; do mkdir -p $i cp $top/appimage/qpdf.appdata.xml $i done for i in appdir/usr/share/doc/qpdf; do mkdir -p $i cp $top/README* $i cp $top/NOTICE.md $i/README-notice.md cp $top/LICENSE.txt $i cp $top/Artistic-2.0 $i/Artistic-LICENSE.txt cp $top/ChangeLog $i/README-ChangeLog cp $top/TODO $i/README-todo done # The following lines are experimental (for debugging; and to test # support for unexpected future binaries added to QPDF): for i in /usr/bin/env /bin/less /bin/busybox; do cp $i appdir/usr/bin/ done ls -l /usr/bin/env /bin/less /bin/busybox # Fetch 'linuxdeployqt' which will transform the AppDir into an AppImage: wget -c "https://github.com/probonopd/linuxdeployqt/releases/download/continuous/linuxdeployqt-continuous-x86_64.AppImage" chmod a+x linuxdeployqt*.AppImage # Set up a clean environment: unset QTDIR; unset QT_PLUGIN_PATH; unset LD_LIBRARY_PATH # Let 'linuxdeployqt' do its first stage of work: ./linuxdeployqt*.AppImage appdir/usr/share/applications/*.desktop -bundle-non-qt-libs # In addition to the main executable, we have additional ones to process ./linuxdeployqt*.AppImage appdir/usr/bin/zlib-flate -bundle-non-qt-libs # To eventually generate the AppImage we extract the linuxdeployqt # AppImage to get access to the embedded 'appimagetool': ./linuxdeployqt*.AppImage --appimage-extract # We want to run our custom AppRun script. # Replace symlink with custom script rm appdir/AppRun; cp $top/appimage/AppRun appdir; chmod a+x appdir/AppRun # If we are not on Ubuntu Trusty, we need to disable 'appstreamcli' validation: if [[ $_osversion =~ Ubuntu\ 14.04.*\ LTS ]]; then appimagetool_param="" else appimagetool_param="-n" set +x echo "" echo " Running 'appimagetool' with '-n' parameter..." echo " Reason: this does not seem to be a build running on" echo " Ubuntu Trusty 14.04." echo " '-n' disables checking of AppStream data by the 'appstreamcli'" echo " utility since post-Trusty versions have incompatible changes." echo "" set -x fi # Set up a version string to include in the AppImage name MAJOR_QPDF_VERSION=$( ./appdir/usr/bin/qpdf --version | grep "qpdf version" | awk '{print $3}' ) declare -a UPDATE_INFO VERSION=${MAJOR_QPDF_VERSION} UPDATE_INFO=(-u "gh-releases-zsync|qpdf|qpdf|latest|qpdf-*x86_64.AppImage.zsync") # Remove the default AppRun/symlink and use our own custom AppRun script rm appdir/AppRun; cp $top/appimage/AppRun appdir; chmod a+x appdir/AppRun # Finally, generate the AppImage: PATH=./squashfs-root/usr/bin:$PATH ./squashfs-root/usr/bin/appimagetool $sign $UPDATE_FLAG ${UPDATE_INFO[*]} $appimagetool_param appdir qpdf-$VERSION-x86_64.AppImage set +x # Tell everyone where our result is stored: echo "" echo "=============================================================================" echo " === AppImage is ready in $top/appimage/build ===" echo "=============================================================================" echo ""