Enhancements to AppImage

Enhance 'build-appimage' script:

- add initial comment block and comments for all major steps in the
  script for the benefit of casual users of the script
- 'configure' to build HTML + PDF documentation
- do not remove the man pages from the AppDir (will be used by custom
  AppRun script)
- use a bigger icon
- use '-g' for appimagetool so it can figure out the 'updateinfo' string
  on Travis CI
- output big fat warning to users who build AppImage in non-"Trusty"
  environments

Add 'AppStream' metadata file

This serves to satisfy desktop environments who want to automatically
create menu entries, show screenshots and display software descriptions.

Note, this file (qpdf.appdata.xml) may need more tweaking since the
Freedesktop folks aren't exactly sure themselves how their 'standard'
should exactly look like, and they changed their validation tools
quite a bit over the recent years in incompatible ways...

Extended and enhanced customized AppRun script

- Add a '--ai-usage' invokation param to the AppImage which serves as
  a starting point to explore the other embedded options
- Support displaying of manual pages by running AppImage with added
  parameter '--man ...'
- Also include HTML/PDF documentation, READMEs and licenses into AppImage
- Support for more parameters: '--list-man', '--list-pdf', '--list-readme',
  '--list-license', '--list-html', '--list-exe', '--pdf', '--readme',
  '--license', '--html' and '--show-apprun'
- Support 'fix-pdf' and 'zlib-' as sub-commands (not just as symlinks)
This commit is contained in:
Kurt Pfeifle 2018-02-25 00:38:44 +01:00 committed by Jay Berkenbilt
parent 079711a479
commit 315c3e7dbc
9 changed files with 705 additions and 28 deletions

View File

@ -3,11 +3,18 @@ compiler: gcc
sudo: require
dist: trusty
install:
- sudo apt-get update -qq
- sudo apt-get install -qq docbook* fop xsltproc less
script:
- appimage/build-appimage
after_success:
- cd appimage/build
- find ./appdir -executable -type f -exec ldd {} \; | grep " => /usr" | cut -d " " -f 2-3 | sort | uniq
- ls -l # for more debugging in Travis' log
- curl --upload-file ./qpdf*.AppImage https://transfer.sh/qpdf-git.$(git rev-parse --short HEAD)-x86_64.AppImage
- sha512sum ./qpdf*.AppImage
- sha512sum ./qpdf*.AppImage*
- wget -c https://github.com/probonopd/uploadtool/raw/master/upload.sh
- bash upload.sh qpdf-*x86_64.AppImage* # This should upload the .zsync file as well

21
README-appimage.md Normal file
View File

@ -0,0 +1,21 @@
# Using the QPDF AppImage bundle (for Linux x86_64 systems only)
First advice:
- After downloading, you have to set the executable bit for any AppImage (for security reasons
this is disabled by default): `chmod +x <name-of-application>.AppImage`
- Run the QPDF AppImage with the '--usage' parameter to start learning some useful details about
built-in features of this specific AppImage.
More tips:
- You can rename the AppImage to any name allowed for file names on Linux. The '.AppImage' suffix
is not required for it to function. It will also work as expected if you invoke it from a
symlink. Using 'qpdf' as its filename or symlink name is OK. However, you may want to continue
using the QPDF package provided by your system's package manager side by side with the AppImage
bundle: in this case it is recommended to use 'qpdf.ai' as a short name for (or as the symlink
name to) the qpdf-<version>.AppImage.
- [...more tips to come... work in progress...]

View File

@ -1,5 +1,13 @@
# QPDF [![Build Status](https://travis-ci.org/qpdf/qpdf.svg?branch=master)](https://travis-ci.org/qpdf/qpdf)
----
<sup>
(This repository is a temporary clone of the original upstream one in order to test (and possibly improve) the AppImage created via the Travis CI integration which was recently added by Jay.)
</sup>
----
[![QPDF](logo/qpdf.svg)](http://qpdf.sourceforge.net)
This is the QPDF package. Information about it can be found at http://qpdf.sourceforge.net. The source code repository is hosted at github: https://github.com/qpdf/qpdf.

View File

@ -1,19 +1,492 @@
#!/bin/bash
# The purpose of this custom AppRun script is
# to allow symlinking the AppImage and invoking
# the corresponding binary depending on which
# symlink was used to invoke the AppImage
# Copyright (c) 2017 Simon Peter (@probonopd)
# Copyright (c) 2018 Kurt Pfeifle (@pdfkungfoo)
#
# License: MIT
#
# The purpose of this custom AppRun script is to enable symlinking the AppImage and invoking the corresponding
# binary depending on which symlink name was used to invoke the AppImage.
#
# At the same time it also allows to invoke the embedded binaries as 'sub-commands'. This is in the interest of
# saving users from creating extra symlinks (without preventing others from STILL using such, should they want
# or need these).
#
# It also provides some additional help parameters in order to allow faster familiarization with functionality
# embedded in this AppImage. For example it support the listing and viewing of embedded manpages, HTML files,
# PDF files, licenses and READMEs.
#
# Note, the AppImage can be renamed to anything what's 'legal' for an executable name under Linux or used via
# a symlink under any name and it should behave like 'qpdf' is expected to behave. If the symlink name is
# 'fix-qdf' or 'zlib-flate' it should behave like these...
HERE="$(dirname "$(readlink -f "${0}")")"
if [ ! -z $APPIMAGE ] ; then
BINARY_NAME=$(basename "$ARGV0")
if [ -e "$HERE/usr/bin/$BINARY_NAME" ] ; then
exec "$HERE/usr/bin/$BINARY_NAME" "$@"
else
exec "$HERE/usr/bin/qpdf" "$@"
fi
else
exec "$HERE/usr/bin/qpdf" "$@"
# Set APPDIR and ARGV0 when running directly from the AppDir.
# Running from the AppDir can be beneficial when debugging the AppImage (or give performance improvements):
if [ -z $APPDIR ]; then
APPDIR="$HERE"
ARGV0="$0"
fi
# This is a semi-secret environment variable which can be set for debugging the AppImage.
# For now it is only meant for temporary use and may be removed again in the near future once things have
# settled:
if [ "x$SET_BASH_X_FOR_APPRUN" == "xYeSS" ] ; then
set -x
else
set +x
fi
# Another semi-secret environment var:
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
env | less
fi
if [ "x$SET_SHOW_ENV_FOR_APPIMAGE" == "xYeSS" ] ; then
env | grep --color -E '(APPIMAGE|APPDIR|APP|ARGV0|HERE)'
fi
function usage() {
echo "
--------------------------------------------------------------------------
All QPDF command line functionality inside an AppImage package.
--------------------------------------------------------------------------
(This package uses the AppImage software packaging technology for Linux ['One App == One File']
for easy availability of the newest QPDF releases across all major Linux distributions.)
Usage:
------
$ARGV0 --help
# Show help screen of QPDF itself
$ARGV0 --ai-usage
# This message (it's only present in the AppImage incarnation of QPDF)
$ARGV0 fix-qdf|zlib-flate
# Run the named sub-command
$ARGV0 --list-exe
# List all executables embedded in AppImage
$ARGV0 --list-man
# List available, embedded manual pages
$ARGV0 --man qpdf|zlib-flate|fix-qdf
# Display embedded manual page(s)
$ARGV0 --list-html
# List all HTML documents embedded in AppImage
$ARGV0 --html <path/to/file>
# Use browser to show HTML file embedded in AppImage
# (for list of available HTML files see \"$ARGV0 --list-html\")
$ARGV0 --list-pdf
# List all PDF documents embedded in AppImage
$ARGV0 --pdf <path/to/file>
# Use system default PDF viewer to display embedded PDF document(s)
# (for list of available PDF files see \"$ARGV0 --list-pdf\")
$ARGV0 --list-readme
# List all READMEs embedded in AppImage
$ARGV0 --readme <path/to/readme>
# Show content of README embedded in AppImage
# (for list of available READMEs see \"$ARGV0 --list-readme\")
$ARGV0 --list-license
# List all LICENSE files embedded in AppImage
$ARGV0 --license <name-of-license>
# Show content of LICENSE file embedded in AppImage (piped thru 'less -N')
$ARGV0 --show-apprun|--self-show|--selfshow
# Show 'AppRun' invoked by 'less -N'; type '-N' to toogle line number display
$ARGV0 --appimage-help
# Show AppImage options available for all 'type 2' AppImages
$ARGV0 --help
# Show help screen of QPDF itself
------------------------------------------------------------------------------------------------
NOTE: The execution of this AppImage is controlled by a custom AppRun script. The state of this
script is experimental and preliminary. Hence it may not work as expected, or miss some
functionality. You can hack on this script by unpacking this AppImage into a local sub directory
[currently named 'squashfs-root'] with this command:
$ARGV0 --appimage-extract
After you're done with your hacks, repackage the AppImage again with this command:
appimagetool [/path/to/]squashfs-root [/path/to/]QPDF-*.AppImage
Latest versions of tools provided by AppImageKit are always available from
* https://github.com/AppImage/AppImageKit/releases/ and
* https://github.com/AppImage/AppImageUpdate/releases/ and
* https://github.com/AppImage/zsync2/releases and
* https://github.com/probonopd/linuxdeployqt/releases/
------------------------------------------------------------------------------------------------
"
}
function mimetype() {
case "$#" in
1)
# 'file --mime-type some-foo-file.ext' usually returns: 'some-foo-file.ext: major/minor', on stderr...
# However, we want to get back only 'major/minor', on stdout!
file --mime-type "$1" 2>&1 | sed 's#'"$1"':##;s# ##'
;;
0)
echo "" 1>&2
echo " # This is a Bash function, named \"$FUNCNAME\"." 1>&2
echo " # You cannot run it without an argument. If you run it with a" 1>&2
echo " # [path to a] file as a single argument, it simply returns the" 1>&2
echo " # 'major/minor' MIME type. If you add multiple [paths to] files" 1>&2
echo " # as arguments, it returns a list of 'major/minor' MIME types with" 1>&2
echo " # the respective file names prepended. Example usage:" 1>&2
echo " #" 1>&2
echo " # $> $FUNCNAME /path/to/a.pdf" 1>&2
echo " #" 1>&2
echo " # $> $FUNCNAME /path/to/a.txt ./myscript.sh ../some.txt" 1>&2
echo " #" 1>&2
echo " # This Bash function's source code is this:" 1>&2
echo "" 1>&2
typeset -f "${FUNCNAME}" 1>&2
echo "" 1>&2
;;
*)
file --mime-type "$@"
;;
esac
}
if [ x"$1" == "xshow-apprun" -o x"$1" == "x--show-apprun" -o x"$1" == "x--apprunshow" -o x"$1" == "x--apprun-show" -o x"$1" == "xselfshow" -o x"$1" == "x--selfshow" -o x"$1" == "xself-show" -o x"$1" == "x--self-show" -o x"$1" == "x--show-self" -o x"$1" == "x--showself" -o x"$1" == "xshow-self" -o x"$1" == "xshowself" ] ; then
cd "$HERE"
less -N AppRun
exit $?
fi
if [ x"$1" == "xlistlicense" -o x"$1" == "x--listlicense" -o x"$1" == "xlist-license" -o x"$1" == "x--list-license" -o x"$1" == "x--licenselist" -o x"$1" == "x--license-list" ] ; then
cd "$HERE"
echo ""
echo "You may invoke \"$ARGV0\" with one of the following additional arguments."
echo "This will then display the respective license file:"
echo ""
find . -type f -name "*LICENSE*" -o -name "*license*" | sed 's#^./# --license #'
echo ""
exit $?
fi
if [ "x$1" == "xai-usage" -o "x$1" == "x--aiusage" -o "x$1" == "x--ai-usage" -o "x$1" == "x-u" ] ; then
usage | less
#usage
exit $?
fi
if [ x"$1" == "xlistman" -o x"$1" == "x--listman" -o x"$1" == "xlist-man" -o x"$1" == "x--list-man" -o x"$1" == "x--manlist" -o x"$1" == "x--man-list" ] ; then
cd "$HERE"
echo ""
echo "You may invoke \"$ARGV0\" with one of the following additional arguments."
echo "This will then open the respective manual page:"
echo ""
find usr/share/man* -type f | sed 's#^# --man #'
echo ""
exit $?
fi
if [ x"$1" == "xlistexe" -o x"$1" == "x--listexe" -o x"$1" == "xlist-exe" -o x"$1" == "x--list-exe" -o x"$1" == "x--exelist" -o x"$1" == "x--exe-list" ] ; then
cd "$HERE"
echo ""
echo "You may invoke \"$ARGV0\" with one of the following additional arguments."
echo "This would run the respective exe as a 'sub-command':"
echo ""
find . \( \( -type f -o -type l -o -type s -o -type p \) -a -executable \) | grep '/bin/' | grep -v qpdf | sed 's#./usr/bin/# #' | sort -V | grep -v ".sh$"
echo ""
find . \( \( -type f -o -type l -o -type s -o -type p \) -a -executable \) | grep '/bin/' | grep -v qpdf | sed 's#./usr/bin/# #' | sort -V | grep ".sh$"
echo ""
exit $?
fi
if [ x"$1" == "xlistreadme" -o x"$1" == "x--listreadme" -o x"$1" == "xlist-readme" -o x"$1" == "x--list-readme" -o x"$1" == "x--readmelist" -o x"$1" == "x--readme-list" ] ; then
cd "$HERE"
echo ""
echo "You may invoke \"$ARGV0\" with one of the following additional arguments."
echo "This will then display the respective README file:"
echo ""
find . -type f -iname "*README*" -o -iname "*.txt" -o -iname "*.md" -o -iname "*copyright*" -o -iname "*changelog*" -o -iname "*todo*" | sed 's#^./# --readme #'
echo ""
exit $?
fi
if [ x"$1" == "xlisthtml" -o x"$1" == "x--listhtml" -o x"$1" == "xlist-html" -o x"$1" == "x--list-html" -o x"$1" == "x--htmllist" -o x"$1" == "x--html-list" ] ; then
cd "$HERE"
echo ""
echo "You may invoke \"$ARGV0\" with one of the following additional arguments."
echo "This will then open the respective HTML file in your preferred browser:"
echo ""
find . -type f -name "*.html" | sed 's#^./# --html #'
echo ""
exit $?
fi
if [ x"$1" == "xlistpdf" -o x"$1" == "x--listpdf" -o x"$1" == "xlist-pdf" -o x"$1" == "x--list-pdf" -o x"$1" == "x--pdflist" -o x"$1" == "x--pdf-list" ] ; then
cd "$HERE"
echo ""
echo "You may invoke \"$ARGV0\" with one of the following additional arguments."
echo "This will then open the respective PDF file in your preferred viewer program:"
echo ""
find . -type f -name "*.pdf" | sed 's#^./# --pdf #'
echo ""
exit $?
fi
if [ x"$1" == "xreadme" -o x"$1" == "x--readme" ] ; then
cd "$HERE"
shift
echo ""
if [ x"$1" == "x" ] ; then
echo " You must give a path to the README you want to open."
echo " For available READMEs run \"$ARGV0 --listreadme\"."
else
readmefile=$( find . -type f -iname "*README*" -o -iname "*.txt" -o -iname "*.md" -o -iname "*copyright*" -o -iname "*changelog*" | grep "${1}" | sort -rV | head -n 1 )
MIME=$(mimetype $readmefile)
case $MIME in
text/html|application/pdf|application/epub*)
xdg-open "$readmefile"
sleep 3 # sleep to allow slow xdg-open do its job
;;
inode/x-empty)
echo ""
echo " Sorry, this file, \"$readmefile\", is empty and has no content."
echo ""
;;
text/*)
less -N "$readmefile"
;;
esac
sleep 0
fi
echo ""
exit $?
fi
if [ x"$1" == "xlicense" -o x"$1" == "x--license" ] ; then
cd "$HERE"
shift
echo ""
if [ x"$1" == "x" ] ; then
echo " You must give a path to the LICENSE you want to open."
echo " For available LICENSE run \"$ARGV0 --list-license\"."
else
licensefile=$( find . -type f -iname "*LICENSE*" | grep "${1}" | sort -rV | head -n 1 )
#if PDF or EPUB or HTML ; then xdg-open $licensefile ; else
MIME=$(mimetype $licensefile)
case $MIME in
text/html|application/pdf|application/epub*)
xdg-open "$licensefile"
sleep 3 # sleep to allow slow xdg-open do its job
;;
inode/x-empty)
echo ""
echo " Sorry, this file, \"$licensefile\", is empty and has no content."
echo ""
;;
text/*)
less -N "$licensefile"
;;
esac
sleep 0
fi
echo ""
exit $?
fi
if [ x"$1" == "xman" -o x"$1" == "x--man" ] ; then
export MANPATH="$HERE/usr/share/man:$MANPATH"
shift
exec man "$@" || man $(basename $1)
fi
if [ x"$1" == "xpdf" -o x"$1" == "x--pdf" ] ; then
cd "$HERE"
shift
echo ""
if [ x"$1" == "x" ] ; then
echo ""
echo " You must give a path to the PDF file you want to open."
echo " For available PDFs run \"$ARGV0 --list-pdf\""
echo ""
else
pdffile=$( find . -type f -name "*.pdf" | grep "${1/.pdf/}.pdf" | sort -rV | head -n 1 )
xdg-open "$pdffile"
sleep 5
fi
echo ""
exit $?
fi
if [ x"$1" == "xhtml" -o x"$1" == "x--html" ] ; then
cd "$HERE"
shift
if [ x"$1" == "x" ] ; then
echo ""
echo " You must give a path to the HTML file you want to open."
echo " For available HTMLs run \"$ARGV0 --list-html\""
echo ""
else
htmlfile=$( find . -type f -name "*.html" | grep "${1}" | sort -rV | head -n 1 )
xdg-open "$htmlfile"
sleep 5
fi
exit $?
fi
if [ x"$1" == "x--appimage-help" ] ; then
cd "$HERE"
shift
if [ x"$APPIMAGE" == "x" ] ; then
echo ""
echo " The parameter '--appimage-help' does not work if you run this application from an AppDir (as you do)."
echo " To create an AppImage from your AppDir run this command:"
echo ""
echo " appimagetool -n $APPDIR qpdf.AppImage"
echo ""
echo " You can download the latest version of 'appimagetool' (as an AppImage) from here:"
echo ""
echo " https://github.com/AppImage/AppImageKit/releases"
echo ""
fi
exit $?
fi
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into output of qpdf|fix-qdf|zlib-flate which goes to stdout!
echo ARGV0=$ARGV0 1>&2 # Don't leak strings into output of qpdf|fix-qdf|zlib-flate which goes to stdout!
echo dollar0=$0 1>&2 # Don't leak strings into output of qpdf|fix-qdf|zlib-flate which goes to stdout!
echo dollar1=$1 1>&2 # Don't leak strings into output of qpdf|fix-qdf|zlib-flate which goes to stdout!
echo dollar_at="$@" 1>&2 # Don't leak strings into output of qpdf|fix-qdf|zlib-flate which goes to stdout!
fi
### Main stuff happens from here:
if [ ! -z $APPIMAGE ] ; then
# We run as an AppImage
BINARY_NAME=$(basename "$ARGV0")
APPIMAGE=$APPIMAGE
CALLED_SUBCMD=$( basename $1 2>/dev/null )
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into output of qpdf|fix-pdf|zlib-flate going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into output of qpdf|fix-pdf|zlib-flate going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into output of qpdf|fix-pdf|zlib-flate going to stdout!
fi
if [ -x "$HERE/usr/bin/$BINARY_NAME" ] && [ x"$BINARY_NAME" != "x" ] ; then
# We are invoked from a symlink (like 'fix-qdf' or 'zlib-flate')
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
shift
exec "$HERE/usr/bin/$BINARY_NAME" "$@"
else
if [ -x "$HERE/usr/bin/$CALLED_SUBCMD" ] && [ x"$CALLED_SUBCMD" != "x" ] ; then
# We are invoked by a (currently not yet known future) binary name which may be located in ./usr/bin/ ...
BINARY_NAME=$1
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
shift
exec "$HERE/usr/bin/$BINARY_NAME" "$@"
elif [ -x "$HERE/$CALLED_SUBCMD" ] && [ x"$CALLED_SUBCMD" != "x" ] ; then
# We are invoked by a (currently not yet known future) binary name which may be located in our root AppDir ...
BINARY_NAME=$CALLED_SUBCMD
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
shift
exec "$HERE/$BINARY_NAME" "$@"
else
# this clause may not be necessary...
exec "$HERE/usr/bin/qpdf" "$@"
fi
fi
else
# Most likely we run from an AppDir, not as an AppImage:
BINARY_NAME=$(basename "$ARGV0")
APPIMAGE=$APPIMAGE
CALLED_SUBCMD=$( basename $1 2>/dev/null )
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
if [ -x "$HERE/usr/bin/$CALLED_SUBCMD" ] && [ "x$CALLED_SUBCMD" != "x" ]; then
#echo befor shift dollar_at=$@
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
shift
#echo after shift dollar_at=$@
#echo CALLED_SUBCMD=$CALLED_SUBCMD
exec "$HERE/usr/bin/$CALLED_SUBCMD" "$@"
elif [ -x "$HERE/usr/bin/$BINARY_NAME" ] && [ "x$BINARY_NAME" != "x" ] ; then
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
shift
exec "$HERE/usr/bin/$BINARY_NAME" "$@"
else
if [ "x$SET_SHOW_ENV_FOR_APPRUN" == "xYeSS" ] ; then
# We have the (hidden) env var for debugging stuff set
echo BINARY_NAME=$BINARY_NAME 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo APPIMAGE=$APPIMAGE 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
echo CALLED_SUBCMD=$CALLED_SUBCMD 1>&2 # Don't leak strings into qpdf|fix-pdf|zlib-flate output going to stdout!
fi
exec "$HERE/usr/bin/qpdf" "$@"
fi
fi

View File

@ -1,40 +1,162 @@
#!/bin/sh
#!/bin/bash
# Copyright (c) 2018 Jay Berkenbilt and Kurt Pfeifle
#
# This script is mainly meant to build an 'AppImage' from GitHub sources of QPDF via Travis CI on an
# Ubuntu Trusty (14.04) LTS system (see https://appimage.org/).
#
# 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 Ubuntu Trusty (14.04).
set -ex
# Support for signing the AppImage (only by original maintainer):
sign=
if [ "$1" = "--sign" ]; then
if [ "x$1" == "x--sign" ] ; then
sign=--sign
fi
# Check if we are on Ubuntu Trusty
_osversion=$(cat /etc/os-release | grep PRETTY_NAME | awk -F'=' '{print $2}' | sed 's#"##g')
# Warn users building the AppImage locally:
if [ x"$_osversion" != x"Ubuntu 14.04.5 LTS" ] ; then
set +x
echo ""
echo "+==============================================================================================================+"
echo "|| WARNING: You are about to build a QPDF AppImage on a system which is NOT Ubuntu 14.04.5 LTS ('Trusty'). ||"
echo "|| ||"
echo "|| Very likely you use a newer Linux distribution. ||"
echo "|| The resulting AppImage will not be 'universally' usable. ||"
echo "|| Hence, it likely will not be capable of running on a large range of Linux distributions. ||"
echo "|| It will only reliably run on the very same systems it has been created on, and maybe some similar ones. ||"
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:
./autogen.sh
./configure --prefix=/usr --enable-werror --enable-show-failed-test-output
./configure --prefix=/usr --enable-werror --enable-show-failed-test-output --enable-html-doc --enable-pdf-doc "$CUSTOM_CONFIGURE"
# Build!
make -j$(nproc)
# Run built-in QPDF checks:
make check
# Prepare AppDir which is the basis for the AppImage:
mkdir -p $appdir
make install DESTDIR=$appdir; find $appdir
# Install build result into AppDir:
make install DESTDIR=$appdir ; find $appdir
# 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}
rm -rf appdir/usr/share/doc appdir/usr/share/man
for i in appdir/usr/share/icons/hicolor/128x128/apps; do
# Copy icon which is needed for desktop integration into place:
for i in appdir/usr/share/icons/hicolor/512x512/apps ; do
mkdir -p $i
cp $top/logo/qpdf.svg $i
convert -resize '128x128>' $top/logo/qpdf.svg $i/qpdf.png
cp $top/logo/qpdf.png $i
done
for i in appdir/usr/share/applications; do mkdir -p $i; cp $top/appimage/qpdf.desktop $i; 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
unset QTDIR; unset QT_PLUGIN_PATH ; unset LD_LIBRARY_PATH
# 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
# Generate AppImage
# To eventually generate the AppImage we extract the linuxdeployqt AppImage to get access to the embedded 'appimagetool':
./linuxdeployqt*.AppImage --appimage-extract
rm appdir/AppRun ; cp $top/appimage/AppRun appdir; chmod a+x appdir/AppRun # Replace symlink with custom script
PATH=./squashfs-root/usr/bin:$PATH ./squashfs-root/usr/bin/appimagetool $sign appdir
# We want to run our custom AppRun script:
rm appdir/AppRun ; cp $top/appimage/AppRun appdir ; chmod a+x appdir/AppRun # Replace symlink with custom script
# If we are not on Ubuntu Trusty, we need to disable 'appstreamcli' validation:
if [ x"$_osversion" == x"Ubuntu 14.04.5 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 Travis CI build running on Ubuntu Trusty 14.04."
echo " '-n' disables checking of AppStream data by the 'appstreamcli' 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}' )
VERSION=${MAJOR_QPDF_VERSION}-continuous-${TRAVIS_JOB_NUMBER}-$(date "+%Y-%m-%d")-git.$(git rev-parse --short HEAD)-x86_64
# 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
set +x
# Finally, generate the AppImage:
PATH=./squashfs-root/usr/bin:$PATH ./squashfs-root/usr/bin/appimagetool $sign -g $appimagetool_param appdir qpdf-$VERSION.AppImage
# Tell everyone where our result is stored:
echo ""
echo "*** AppImage is ready in appimage/build ***"
echo "===================================================================================="
echo " === AppImage is ready in $top/appimage/build ==="
echo "===================================================================================="
echo ""

Binary file not shown.

After

Width:  |  Height:  |  Size: 596 KiB

45
appimage/qpdf.appdata.xml Normal file
View File

@ -0,0 +1,45 @@
<?xml version="1.0" encoding="UTF-8"?>
<!-- Copyright 2005-2018 Jay Berkenbilt -->
<component>
<id>org.QPDF.qpdf.desktop</id>
<metadata_license>MIT</metadata_license>
<project_license>Apache-2.0</project_license>
<name>QPDF</name>
<summary>Structural, content-preserving transformations on PDF files</summary>
<description>
<p> QPDF is a command-line program that does structural, content-preserving transformations on PDF files.
It could have been called something like pdf-to-pdf.
It also provides many useful capabilities to developers of PDF-producing software or for people
who just want to look at the innards of a PDF file to learn more about how they work.</p>
<p> QPDF is capable of creating linearized (also known as web-optimized) files and encrypted files.
It is also capable of converting PDF files with object streams (also known as compressed objects)
to files with no compressed objects or to generate object streams from files that don't have them
(or even those that already do). QPDF also supports a special mode designed to allow you to edit
the content of PDF files in a text editor. For more details, please see the documentation links
below.</p>
<p> QPDF includes support for merging and splitting PDFs through the ability to copy objects from one PDF
file into another and to manipulate the list of pages in a PDF file. The QPDF library also makes
it possible for you to create PDF files from scratch. In this mode, you are responsible for
supplying all the contents of the file, while the QPDF library takes care off all the syntactical
representation of the objects, creation of cross references tables and, if you use them, object
streams, encryption, linearization, and other syntactic details.</p>
<p>QPDF is not a PDF content creation library, a PDF viewer, or a program capable of converting PDF into
other formats. In particular, QPDF knows nothing about the semantics of PDF content streams.
If you are looking for something that can do that, you should look elsewhere.
However, once you have a valid PDF file, QPDF can be used to transform that file in ways perhaps
your original PDF creation can't handle. For example, programs generate simple PDF files but
can't password-protect them, web-optimize them, or perform other transformations of that type.</p>
</description>
<x-launchable type="desktop-id">qpdf.desktop</x-launchable>
<url type="homepage">http://qpdf.sourceforge.net/</url>
<url type="bugtracker">https://github.com/qpdf/qpdf/issues</url>
<screenshots>
<screenshot type="default">
<image width="798" height="1550">https://i.stack.imgur.com/coCKR.jpg</image>
</screenshot>
</screenshots>
<provides>
<id>org.QPDF.qpdf.desktop</id>
</provides>
<!-- <update_contact></update_contact> -->
</component>

View File

@ -5,3 +5,4 @@ Exec=qpdf
Name=qpdf
Comment=Structural, content-preserving transformations on PDF files
Icon=qpdf
Categories=Utility;Office;ConsoleOnly;

BIN
logo/qpdf.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.4 KiB