summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristoph Reiter <reiter.christoph@gmail.com>2018-04-08 16:23:11 +0200
committerChristoph Reiter <reiter.christoph@gmail.com>2018-04-08 16:23:11 +0200
commit2f95ec07f1b5caba8b10eed56d0a0c6010218cda (patch)
treea4dbd340a6282f6d1a59baefb16f91953375423c
parent203fe3058cf999f763051740027582dd357f2028 (diff)
downloadpygobject-setup-py-install-hint.tar.gz
setup.py: print installation intstructions in case a dependency is missing. Fixes #194setup-py-install-hint
In case the .pc file can't be found check if either apt or dnf is installed and print a command for installing the missing package.
-rwxr-xr-xsetup.py79
1 files changed, 70 insertions, 9 deletions
diff --git a/setup.py b/setup.py
index 1ef7b90a..e9810c71 100755
--- a/setup.py
+++ b/setup.py
@@ -36,6 +36,7 @@ from distutils.errors import DistutilsSetupError, DistutilsOptionError
from distutils.ccompiler import new_compiler
from distutils.sysconfig import get_python_lib, customize_compiler
from distutils import dir_util, log
+from distutils.spawn import find_executable
PYGOBJECT_VERISON = "3.29.0"
@@ -101,7 +102,47 @@ def parse_pkg_info(conf_dir):
return message
-def _run_pkg_config(args, _cache={}):
+def pkg_config_get_install_hint(pkg_name):
+ """Returns an installation hint for a pkg-config name or None"""
+
+ if not sys.platform.startswith("linux"):
+ return
+
+ if find_executable("apt"):
+ dev_packages = {
+ "gobject-introspection-1.0": "libgirepository1.0-dev",
+ "glib-2.0": "libglib2.0-dev",
+ "gio-2.0": "libglib2.0-dev",
+ "cairo": "libcairo2-dev",
+ "cairo-gobject": "libcairo2-dev",
+ "libffi": "libffi-dev",
+ }
+ if pkg_name in dev_packages:
+ return "sudo apt install %s" % dev_packages[pkg_name]
+ elif find_executable("dnf"):
+ dev_packages = {
+ "gobject-introspection-1.0": "gobject-introspection-devel",
+ "glib-2.0": "glib2-devel",
+ "gio-2.0": "glib2-devel",
+ "cairo": "cairo-devel",
+ "cairo-gobject": "cairo-gobject-devel",
+ "libffi": "libffi-devel",
+ }
+ if pkg_name in dev_packages:
+ return "sudo dnf install %s" % dev_packages[pkg_name]
+
+
+class PkgConfigError(Exception):
+ pass
+
+
+class PkgConfigMissingPackageError(PkgConfigError):
+ pass
+
+
+def _run_pkg_config(pkg_name, args, _cache={}):
+ """Raises PkgConfigError"""
+
command = tuple(["pkg-config"] + args)
if command not in _cache:
@@ -109,27 +150,47 @@ def _run_pkg_config(args, _cache={}):
result = subprocess.check_output(command)
except OSError as e:
if e.errno == errno.ENOENT:
- raise SystemExit(
+ raise PkgConfigError(
"%r not found.\nArguments: %r" % (command[0], command))
- raise SystemExit(e)
+ raise PkgConfigError(e)
except subprocess.CalledProcessError as e:
- raise SystemExit(e)
+ try:
+ subprocess.check_output(["pkg-config", "--exists", pkg_name])
+ except (subprocess.CalledProcessError, OSError):
+ raise PkgConfigMissingPackageError(e)
+ else:
+ raise PkgConfigError(e)
else:
_cache[command] = result
return _cache[command]
-def pkg_config_version_check(pkg, version):
- _run_pkg_config([
+def _run_pkg_config_or_exit(pkg_name, args):
+ try:
+ return _run_pkg_config(pkg_name, args)
+ except PkgConfigMissingPackageError as e:
+ hint = pkg_config_get_install_hint(pkg_name)
+ if hint:
+ raise SystemExit(
+ "%s\n\nTry installing it with: %r" % (e, hint))
+ else:
+ raise SystemExit(e)
+ except PkgConfigError as e:
+ raise SystemExit(e)
+
+
+def pkg_config_version_check(pkg_name, version):
+ _run_pkg_config_or_exit(pkg_name, [
"--print-errors",
"--exists",
- '%s >= %s' % (pkg, version),
+ '%s >= %s' % (pkg_name, version),
])
-def pkg_config_parse(opt, pkg):
- ret = _run_pkg_config([opt, pkg])
+def pkg_config_parse(opt, pkg_name):
+ ret = _run_pkg_config_or_exit(pkg_name, [opt, pkg_name])
+
if sys.version_info[0] == 3:
output = ret.decode()
else: