amprolla

devuan's apt repo merger
git clone git://parazyd.org/amprolla.git
Log | Files | Refs | README | LICENSE

commit 4268288f669be5e023be2a53477caa81a95d4244
parent 6b27485f8e6a1ef3bc904db5ea47e01a4051ffa6
Author: KatolaZ <katolaz@freaknet.org>
Date:   Sun, 24 Jun 2018 12:39:20 +0200

Implement dependency alternatives parsing.

This commit adds support for parsing dependencies which contain
alternatives, e.g. "foo | bar".

Currently it is utilized for banning packages.

Diffstat:
MLICENSE | 2+-
Mlib/package.py | 39++++++++++++++++++++++++++++++++-------
Mlib/parse.py | 41+++++++++++++++++++++++------------------
3 files changed, 56 insertions(+), 26 deletions(-)

diff --git a/LICENSE b/LICENSE @@ -1,6 +1,6 @@ Copyright (c) 2017 Merlijn Wajer <merlijn@wizzup.org> Copyright (c) 2017 Evilham <devuan@evilham.com> -Copyright (c) 2017 KatolaZ <katolaz@freaknet.org> +Copyright (c) 2017-2018 KatolaZ <katolaz@freaknet.org> Copyright (c) 2017-2018 Ivan J. <parazyd@dyne.org> GNU AFFERO GENERAL PUBLIC LICENSE diff --git a/lib/package.py b/lib/package.py @@ -75,6 +75,33 @@ def load_packages_file(filename): return None +def depends_on_all_banned(deps, banned_pkgs): + """ + Gets a list of dicts of dep alternatives and a set of banned packages and + returns True if any of the dicts consist exclusively of banned_pkgs. + """ + for dep in deps: + alt = set(dep.keys()) + if len(alt.intersection(banned_pkgs)) == len(alt): + # All the alternatives are banned + return True + return False + + +def depends_on(deps, package_set): + """ + Gets a list of dicts of dep alternatives and a set of packages and returns + True if any of the dicts include at least one of the elements in + package_set. + """ + for dep in deps: + alt = set(dep.keys()) + if alt.intersection(package_set): + # At least one alternative is in package_set + return True + return False + + def package_banned(pkg, banned_pkgs): """ Returns True is the package contains a banned dependency. @@ -89,19 +116,17 @@ def package_banned(pkg, banned_pkgs): depends = parse_dependencies(pkg.get('Depends', '')) pre_depends = parse_dependencies(pkg.get('Pre-Depends', '')) - depends = [v for v in depends] - pre_depends = [v for v in pre_depends] - - deps = set(depends).union(set(pre_depends)) + depends.extend(pre_depends) - if 'libsystemd0' in deps: + if depends_on(depends, set(['libsystemd0'])): logtofile('libsystemd.txt', '%s,%s\n' % (globalvars.suite, pkg.get('Package'))) - if bool(deps.intersection(banned_pkgs)): + isbanned = depends_on_all_banned(depends, banned_pkgs) + if isbanned: logtofile('bannedpackages.txt', '%s,%s\n' % (globalvars.suite, pkg.get('Package'))) - return bool(deps.intersection(banned_pkgs)) + return isbanned def package_newer(pkg1, pkg2): diff --git a/lib/parse.py b/lib/parse.py @@ -127,28 +127,33 @@ def parse_dependencies(dependencies): Example line:: - 'lib6 (>= 2.4), libdbus-1-3 (>= 1.0.2), foo' + 'lib6 (>= 2.4), libdbus-1-3 (>= 1.0.2), foo | bar (>= 4.5.6)' Output:: - {'lib6': '(>= 2.4)', 'libdbus-1-3': '(>= 1.0.2)', 'foo': None} - """ - ret = {} - - for pkg_plus_version in dependencies.split(', '): - ver = pkg_plus_version.split(' ', 1) - name = ver[0] - - # If we get passed an empty string, the name is '', and we just - # outright stop - if not name: - return {} + A list of dep alternatives, whose elements are dicts, in the form: - if len(ver) == 2: - version = ver[1] - ret[name] = version - else: - ret[name] = None + [{'lib6': '(>= 2.4)'}, {'libdbus-1-3': '(>= 1.0.2)'}, + {'foo': None, 'bar': '(>= 4.5.6)'}] + """ + ret = [] + + for alternatives in dependencies.split(', '): + depset = {} + for pkg_plus_version in alternatives.split('|'): + ver = pkg_plus_version.strip(' ').split(' ', 1) + name = ver[0] + + # If we get passed an empty string, the name is '', and we just + # outright stop. + if not name: + return [] + if len(ver) == 2: + version = ver[1] + depset[name] = version + else: + depset[name] = None + ret.append(depset) return ret