From b14a48bd91262033c8cdfdceb296dc6db6aaf266 Mon Sep 17 00:00:00 2001 From: Sebastian Luther Date: Fri, 6 Aug 2010 21:14:21 +0200 Subject: [PATCH] autounmask: Add ability to adjust USE --- pym/_emerge/depgraph.py | 156 +++++++++++++++--- .../tests/resolver/ResolverPlayground.py | 26 ++- pym/portage/tests/resolver/test_autounmask.py | 131 +++++++++++++++ pym/portage/tests/resolver/test_eapi.py | 6 +- pym/portage/tests/resolver/test_simple.py | 4 +- 5 files changed, 288 insertions(+), 35 deletions(-) create mode 100644 pym/portage/tests/resolver/test_autounmask.py diff --git a/pym/_emerge/depgraph.py b/pym/_emerge/depgraph.py index b7bbbd4b5..691a7560e 100644 --- a/pym/_emerge/depgraph.py +++ b/pym/_emerge/depgraph.py @@ -111,7 +111,7 @@ class _frozen_depgraph_config(object): class _dynamic_depgraph_config(object): def __init__(self, depgraph, myparams, allow_backtracking, - runtime_pkg_mask, needed_user_config_changes): + runtime_pkg_mask, needed_user_config_changes, needed_use_config_changes): self.myparams = myparams.copy() self._vdb_loaded = False self._allow_backtracking = allow_backtracking @@ -195,6 +195,15 @@ class _dynamic_depgraph_config(object): dict((k.copy(), v.copy()) for (k, v) in \ needed_user_config_changes.items()) + if needed_use_config_changes is None: + self._needed_use_config_changes = {} + else: + self._needed_use_config_changes = \ + dict((k.copy(), (v[0].copy(), v[1].copy())) for (k, v) in \ + needed_use_config_changes.items()) + + self._autounmask = depgraph._frozen_config.myopts.get('--autounmask', 'n') == True + self._runtime_pkg_mask = runtime_pkg_mask self._need_restart = False @@ -265,13 +274,14 @@ class depgraph(object): _dep_keys = ["DEPEND", "RDEPEND", "PDEPEND"] def __init__(self, settings, trees, myopts, myparams, spinner, - frozen_config=None, runtime_pkg_mask=None, needed_user_config_changes=None, allow_backtracking=False): + frozen_config=None, runtime_pkg_mask=None, needed_user_config_changes=None, \ + needed_use_config_changes=None, allow_backtracking=False): if frozen_config is None: frozen_config = _frozen_depgraph_config(settings, trees, myopts, spinner) self._frozen_config = frozen_config self._dynamic_config = _dynamic_depgraph_config(self, myparams, - allow_backtracking, runtime_pkg_mask, needed_user_config_changes) + allow_backtracking, runtime_pkg_mask, needed_user_config_changes, needed_use_config_changes) self._select_atoms = self._select_atoms_highest_available self._select_package = self._select_pkg_highest_available @@ -1122,7 +1132,7 @@ class depgraph(object): myroot = pkg.root mykey = pkg.cpv metadata = pkg.metadata - myuse = pkg.use.enabled + myuse = self._pkg_use_enabled(pkg) jbigkey = pkg depth = pkg.depth + 1 removal_action = "remove" in self._dynamic_config.myparams @@ -1203,7 +1213,7 @@ class depgraph(object): dep_string = portage.dep.paren_normalize( portage.dep.use_reduce( portage.dep.paren_reduce(dep_string), - uselist=pkg.use.enabled)) + uselist=self._pkg_use_enabled(pkg))) dep_string = list(self._queue_disjunctive_deps( pkg, dep_root, dep_priority, dep_string)) @@ -1265,7 +1275,7 @@ class depgraph(object): try: selected_atoms = self._select_atoms(dep_root, - dep_string, myuse=pkg.use.enabled, parent=pkg, + dep_string, myuse=self._pkg_use_enabled(pkg), parent=pkg, strict=strict, priority=dep_priority) except portage.exception.InvalidDependString as e: show_invalid_depstring_notice(pkg, dep_string, str(e)) @@ -1985,7 +1995,9 @@ class depgraph(object): return False, myfavorites if set(self._dynamic_config.digraph.nodes.keys()).intersection( \ - set(self._dynamic_config._needed_user_config_changes.keys())): + set(self._dynamic_config._needed_user_config_changes.keys())) or \ + set(self._dynamic_config.digraph.nodes.keys()).intersection( \ + set(self._dynamic_config._needed_use_config_changes.keys())) : #We failed if the user needs to change the configuration return False, myfavorites @@ -2070,7 +2082,7 @@ class depgraph(object): dep_str = " ".join(pkg.metadata[k] for k in blocker_dep_keys) try: selected_atoms = self._select_atoms( - pkg.root, dep_str, pkg.use.enabled, + pkg.root, dep_str, self._pkg_use_enabled(pkg), parent=pkg, strict=True) except portage.exception.InvalidDependString: continue @@ -2125,6 +2137,9 @@ class depgraph(object): myuse=None, parent=None, strict=True, trees=None, priority=None): """This will raise InvalidDependString if necessary. If trees is None then self._dynamic_config._filtered_trees is used.""" + + _autounmask_backup = self._dynamic_config._autounmask + self._dynamic_config._autounmask = False pkgsettings = self._frozen_config.pkgsettings[root] if trees is None: trees = self._dynamic_config._filtered_trees @@ -2175,6 +2190,7 @@ class depgraph(object): selected_atoms[pkg] = [atom for atom in \ atom_graph.child_nodes(node) if atom in chosen_atoms] + self._dynamic_config._autounmask = _autounmask_backup return selected_atoms def _show_unsatisfied_dep(self, root, atom, myparent=None, arg=None, @@ -2239,7 +2255,7 @@ class depgraph(object): masked_pkg_instances.add(pkg) if atom.unevaluated_atom.use: if not pkg.iuse.is_valid_flag(atom.unevaluated_atom.use.required) \ - or atom.violated_conditionals(pkg.use.enabled).use: + or atom.violated_conditionals(self._pkg_use_enabled(pkg)).use: missing_use.append(pkg) if not mreasons: continue @@ -2257,7 +2273,7 @@ class depgraph(object): missing_use_reasons = [] missing_iuse_reasons = [] for pkg in missing_use: - use = pkg.use.enabled + use = self._pkg_use_enabled(pkg) missing_iuse = pkg.iuse.get_missing_iuse(atom.use.required) mreasons = [] if missing_iuse: @@ -2279,7 +2295,7 @@ class depgraph(object): # Lets see if the violated use deps are conditional. # If so, suggest to change them on the parent. mreasons = [] - violated_atom = atom.unevaluated_atom.violated_conditionals(pkg.use.enabled, myparent.use.enabled) + violated_atom = atom.unevaluated_atom.violated_conditionals(self._pkg_use_enabled(pkg), myparent.use.enabled) if not (violated_atom.use.enabled or violated_atom.use.disabled): #all violated use deps are conditional changes = [] @@ -2509,19 +2525,26 @@ class depgraph(object): def _select_pkg_highest_available_imp(self, root, atom, onlydeps=False): pkg, existing = self._wrapped_select_pkg_highest_available_imp(root, atom, onlydeps=onlydeps) - if self._frozen_config.myopts.get('--autounmask', 'n') is True: + if self._dynamic_config._autounmask is True: if pkg is not None and \ pkg.installed and \ not self._want_installed_pkg(pkg): pkg = None - if pkg is None: + + for allow_missing_keywords in False, True: + if pkg is not None: + break + pkg, existing = \ self._wrapped_select_pkg_highest_available_imp( root, atom, onlydeps=onlydeps, - allow_missing_keywords=True) + allow_use_changes=True, allow_missing_keywords=allow_missing_keywords) if pkg is not None and not pkg.visible: self._dynamic_config._needed_user_config_changes.setdefault(pkg, set()).add("unstable keyword") + + if self._dynamic_config._need_restart: + return None, None return pkg, existing @@ -2545,7 +2568,64 @@ class depgraph(object): else: return False - def _wrapped_select_pkg_highest_available_imp(self, root, atom, onlydeps=False, allow_missing_keywords=False): + def _pkg_use_enabled(self, pkg, target_use=None): + """ + If target_use is None, returns pkg.use.enabled + changes in _needed_use_config_changes. + If target_use is given, the need changes are computed to make the package useable. + Example: target_use = { "foo": True, "bar": False } + The flags target_use must be in the pkg's IUSE. + """ + needed_use_config_change = self._dynamic_config._needed_use_config_changes.get(pkg) + + if target_use is None: + if needed_use_config_change is None: + return pkg.use.enabled + else: + return needed_use_config_change[0] + + if needed_use_config_change is not None: + old_use = needed_use_config_change[0] + new_use = set() + old_changes = needed_use_config_change[1] + new_changes = old_changes.copy() + else: + old_use = pkg.use.enabled + new_use = set() + old_changes = {} + new_changes = {} + + for flag, state in target_use.items(): + if state: + if flag not in old_use: + if new_changes.get(flag) == False: + return old_use + new_changes[flag] = True + new_use.add(flag) + else: + if flag in old_use: + if new_changes.get(flag) == True: + return old_use + new_changes[flag] = False + new_use.update(old_use.difference(target_use.keys())) + + def want_restart_for_use_change(pkg): + if pkg not in self._dynamic_config.digraph.nodes: + return False + #TODO: We can be more clever here. No need to restart if + # 1) we don't have a parent that can't work with our + # new use config + # and + # 2) none of pkg's *DEPEND vars changed + return True + + if new_changes != old_changes: + self._dynamic_config._needed_use_config_changes[pkg] = (new_use, new_changes) + if want_restart_for_use_change(pkg): + self._dynamic_config._need_restart = True + return new_use + + def _wrapped_select_pkg_highest_available_imp(self, root, atom, onlydeps=False, \ + allow_use_changes=False, allow_missing_keywords=False): root_config = self._frozen_config.roots[root] pkgsettings = self._frozen_config.pkgsettings[root] dbs = self._dynamic_config._filtered_trees[root]["dbs"] @@ -2704,11 +2784,21 @@ class depgraph(object): # since IUSE cannot be adjusted by the user. continue - if atom.use.enabled.difference(pkg.use.enabled): + if allow_use_changes: + target_use = {} + for flag in atom.use.enabled: + target_use[flag] = True + for flag in atom.use.disabled: + target_use[flag] = False + use = self._pkg_use_enabled(pkg, target_use) + else: + use = self._pkg_use_enabled(pkg) + + if atom.use.enabled.difference(use): if not pkg.built: packages_with_invalid_use_config.append(pkg) continue - if atom.use.disabled.intersection(pkg.use.enabled): + if atom.use.disabled.intersection(use): if not pkg.built: packages_with_invalid_use_config.append(pkg) continue @@ -2749,7 +2839,7 @@ class depgraph(object): "--reinstall" in self._frozen_config.myopts or \ "--binpkg-respect-use" in self._frozen_config.myopts): iuses = pkg.iuse.all - old_use = pkg.use.enabled + old_use = self._pkg_use_enabled(pkg) if myeb: pkgsettings.setcpv(myeb) else: @@ -2778,7 +2868,7 @@ class depgraph(object): old_use = vardb.aux_get(cpv, ["USE"])[0].split() old_iuse = set(filter_iuse_defaults( vardb.aux_get(cpv, ["IUSE"])[0].split())) - cur_use = pkg.use.enabled + cur_use = self._pkg_use_enabled(pkg) cur_iuse = pkg.iuse.all reinstall_for_flags = \ self._reinstall_for_flags( @@ -3158,7 +3248,7 @@ class depgraph(object): portage.dep._dep_check_strict = False try: success, atoms = portage.dep_check(depstr, - final_db, pkgsettings, myuse=pkg.use.enabled, + final_db, pkgsettings, myuse=self._pkg_use_enabled(pkg), trees=self._dynamic_config._graph_trees, myroot=myroot) except Exception as e: if isinstance(e, SystemExit): @@ -4469,7 +4559,7 @@ class depgraph(object): os.path.dirname(ebuild_path))) else: repo_path_real = portdb.getRepositoryPath(repo_name) - pkg_use = list(pkg.use.enabled) + pkg_use = list(self._pkg_use_enabled(pkg)) if not pkg.built and pkg.operation == 'merge' and \ 'fetch' in pkg.metadata.restrict: fetch = red("F") @@ -4560,7 +4650,7 @@ class depgraph(object): forced_flags.update(pkgsettings.useforce) forced_flags.update(pkgsettings.usemask) - cur_use = [flag for flag in pkg.use.enabled \ + cur_use = [flag for flag in self._pkg_use_enabled(pkg) \ if flag in pkg.iuse.all] cur_iuse = sorted(pkg.iuse.all) @@ -5173,11 +5263,29 @@ class depgraph(object): else: raise NotImplementedError() + use_changes_msg = [] + for pkg, needed_use_config_change in self._dynamic_config._needed_use_config_changes.items(): + self._show_merge_list() + if pkg in self._dynamic_config.digraph.nodes.keys(): + changes = needed_use_config_change[1] + adjustments = [] + for flag, state in changes.items(): + if state: + adjustments.append(flag) + else: + adjustments.append("-" + flag) + use_changes_msg.append("=%s %s\n" % (pkg.cpv, " ".join(adjustments))) + if unstable_keyword_msg: writemsg_stdout("\nThe following " + colorize("BAD", "keyword changes") + \ " are necessary to proceed:\n", noiselevel=-1) writemsg_stdout("".join(unstable_keyword_msg), noiselevel=-1) + if use_changes_msg: + writemsg_stdout("\nThe following " + colorize("BAD", "USE changes") + \ + " are necessary to proceed:\n", noiselevel=-1) + writemsg_stdout("".join(use_changes_msg), noiselevel=-1) + # TODO: Add generic support for "set problem" handlers so that # the below warnings aren't special cases for world only. @@ -5574,7 +5682,9 @@ class depgraph(object): "needed_user_config_changes": self._dynamic_config._needed_user_config_changes.copy(), \ "runtime_pkg_mask": - self._dynamic_config._runtime_pkg_mask.copy() + self._dynamic_config._runtime_pkg_mask.copy(), + "needed_use_config_changes": + self._dynamic_config._needed_use_config_changes.copy() } diff --git a/pym/portage/tests/resolver/ResolverPlayground.py b/pym/portage/tests/resolver/ResolverPlayground.py index a9954fef1..3740f8314 100644 --- a/pym/portage/tests/resolver/ResolverPlayground.py +++ b/pym/portage/tests/resolver/ResolverPlayground.py @@ -14,6 +14,7 @@ from portage.package.ebuild.config import config from portage.sets import load_default_config from portage.versions import catsplit +from _emerge.Blocker import Blocker from _emerge.create_depgraph_params import create_depgraph_params from _emerge.depgraph import backtrack_depgraph from _emerge.RootConfig import RootConfig @@ -183,19 +184,30 @@ class ResolverPlayground(object): # Add a fake _test_ option that can be used for # conditional test code. myopts["_test_"] = True - + portage.util.noiselimit = -2 myparams = create_depgraph_params(myopts, myaction) success, mydepgraph, favorites = backtrack_depgraph( self.settings, self.trees, myopts, myparams, myaction, myfiles, None) + result = ResolverPlaygroundResult(success, mydepgraph, favorites) portage.util.noiselimit = 0 - if success: - mergelist = [x.cpv for x in mydepgraph._dynamic_config._serialized_tasks_cache] - return True, mergelist - else: - #TODO: Use mydepgraph.display_problems() to return a useful error message - return False, None + return result def cleanup(self): shutil.rmtree(self.root) + +class ResolverPlaygroundResult(object): + def __init__(self, success, mydepgraph, favorites): + self.success = success + self.depgraph = mydepgraph + self.favorites = favorites + self.mergelist = None + + if self.depgraph._dynamic_config._serialized_tasks_cache is not None: + self.mergelist = [] + for x in self.depgraph._dynamic_config._serialized_tasks_cache: + if isinstance(x, Blocker): + self.mergelist.append(x.atom) + else: + self.mergelist.append(x.cpv) diff --git a/pym/portage/tests/resolver/test_autounmask.py b/pym/portage/tests/resolver/test_autounmask.py new file mode 100644 index 000000000..944e5485b --- /dev/null +++ b/pym/portage/tests/resolver/test_autounmask.py @@ -0,0 +1,131 @@ +# Copyright 2010 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 + +from portage.tests import TestCase +from portage.tests.resolver.ResolverPlayground import ResolverPlayground + +class AutounmaskTestCase(TestCase): + + def testAutounmask(self): + ebuilds = { + #ebuilds to test use changes + "dev-libs/A-1": { "SLOT": 1, "DEPEND": "dev-libs/B[foo]", "EAPI": 2}, + "dev-libs/A-2": { "SLOT": 2, "DEPEND": "dev-libs/B[bar]", "EAPI": 2}, + "dev-libs/B-1": { "DEPEND": "foo? ( dev-libs/C ) bar? ( dev-libs/D )", "IUSE": "foo bar"}, + "dev-libs/C-1": {}, + "dev-libs/D-1": {}, + + #ebuilds to test keyword changes + "app-misc/Z-1": { "KEYWORDS": "~x86", "DEPEND": "app-misc/Y" }, + "app-misc/Y-1": { "KEYWORDS": "~x86" }, + "app-misc/W-1": {}, + "app-misc/W-2": { "KEYWORDS": "~x86" }, + "app-misc/V-1": { "KEYWORDS": "~x86", "DEPEND": ">=app-misc/W-2"}, + + #ebuilds for mixed test for || dep handling + "sci-libs/K-1": { "DEPEND": " || ( sci-libs/L[bar] || ( sci-libs/M sci-libs/P ) )", "EAPI": 2}, + "sci-libs/K-2": { "DEPEND": " || ( sci-libs/L[bar] || ( sci-libs/P sci-libs/M ) )", "EAPI": 2}, + "sci-libs/K-3": { "DEPEND": " || ( sci-libs/M || ( sci-libs/L[bar] sci-libs/P ) )", "EAPI": 2}, + "sci-libs/K-4": { "DEPEND": " || ( sci-libs/M || ( sci-libs/P sci-libs/L[bar] ) )", "EAPI": 2}, + "sci-libs/K-5": { "DEPEND": " || ( sci-libs/P || ( sci-libs/L[bar] sci-libs/M ) )", "EAPI": 2}, + "sci-libs/K-6": { "DEPEND": " || ( sci-libs/P || ( sci-libs/M sci-libs/L[bar] ) )", "EAPI": 2}, + "sci-libs/K-7": { "DEPEND": " || ( sci-libs/M sci-libs/L[bar] )", "EAPI": 2}, + "sci-libs/K-8": { "DEPEND": " || ( sci-libs/L[bar] sci-libs/M )", "EAPI": 2}, + + "sci-libs/L-1": { "IUSE": "bar" }, + "sci-libs/M-1": { "KEYWORDS": "~x86" }, + "sci-libs/P-1": { }, + + #ebuilds to conflicting use changes + "net-www/G-1": { "DEPEND": "net-www/I[foo]", "EAPI": 2 }, + "net-www/H-1": { "DEPEND": "net-www/I[-foo]", "EAPI": 2 }, + "net-www/I-1": { "IUSE": "foo" }, + "net-www/J-1": { "DEPEND": "|| ( net-www/G net-www/H )" }, + "net-www/J-2": { "DEPEND": "|| ( net-www/H net-www/G )" }, + "net-www/K-1": { "DEPEND": "!!net-www/G", "EAPI": 2 }, + } + + requests = ( + #Test USE changes. + #The simple case. + + (["dev-libs/A:1"], {"--autounmask": "n"}, None, False, None), + (["dev-libs/A:1"], {"--autounmask": True}, None, False, \ + ["dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1"]), + + #Make sure we restart if needed. + + (["dev-libs/B", "dev-libs/A:1"], {"--autounmask": True}, None, False, \ + ["dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1"]), + (["dev-libs/A:1", "dev-libs/B"], {"--autounmask": True}, None, False, \ + ["dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1"]), + (["dev-libs/A:1", "dev-libs/A:2"], {"--autounmask": True}, None, False, \ + ["dev-libs/D-1", "dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1", "dev-libs/A-2"]), + (["dev-libs/B", "dev-libs/A:1", "dev-libs/A:2"], {"--autounmask": True}, None, False, \ + ["dev-libs/D-1", "dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1", "dev-libs/A-2"]), + (["dev-libs/A:1", "dev-libs/B", "dev-libs/A:2"], {"--autounmask": True}, None, False, \ + ["dev-libs/D-1", "dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1", "dev-libs/A-2"]), + (["dev-libs/A:1", "dev-libs/A:2", "dev-libs/B"], {"--autounmask": True}, None, False, \ + ["dev-libs/D-1", "dev-libs/C-1", "dev-libs/B-1", "dev-libs/A-1", "dev-libs/A-2"]), + + #Test keywording. + #The simple case. + + (["app-misc/Z"], {"--autounmask": "n"}, None, False, None), + (["app-misc/Z"], {"--autounmask": True}, None, False, \ + ["app-misc/Y-1", "app-misc/Z-1"]), + + #Make sure that the backtracking for slot conflicts handles our mess. + + (["=app-misc/V-1", "app-misc/W"], {"--autounmask": True}, None, False, \ + ["app-misc/W-2", "app-misc/V-1"]), + (["app-misc/W", "=app-misc/V-1"], {"--autounmask": True}, None, False, \ + ["app-misc/W-2", "app-misc/V-1"]), + + #Mixed testing + #Make sure we don't change use for something in a || dep if there is another choice + #that needs no change. + + (["=sci-libs/K-1"], {"--autounmask": True}, None, True, \ + ["sci-libs/P-1", "sci-libs/K-1"]), + (["=sci-libs/K-2"], {"--autounmask": True}, None, True, \ + ["sci-libs/P-1", "sci-libs/K-2"]), + (["=sci-libs/K-3"], {"--autounmask": True}, None, True, \ + ["sci-libs/P-1", "sci-libs/K-3"]), + (["=sci-libs/K-4"], {"--autounmask": True}, None, True, \ + ["sci-libs/P-1", "sci-libs/K-4"]), + (["=sci-libs/K-5"], {"--autounmask": True}, None, True, \ + ["sci-libs/P-1", "sci-libs/K-5"]), + (["=sci-libs/K-6"], {"--autounmask": True}, None, True, \ + ["sci-libs/P-1", "sci-libs/K-6"]), + + #Make sure we prefer use changes over keyword changes. + (["=sci-libs/K-7"], {"--autounmask": True}, None, False, \ + ["sci-libs/L-1", "sci-libs/K-7"]), + (["=sci-libs/K-8"], {"--autounmask": True}, None, False, \ + ["sci-libs/L-1", "sci-libs/K-8"]), + + #Testing conflict bahviour + (["=net-www/G-1", "=net-www/H-1"], {"--autounmask": True}, None, False, None), + #Some of the following tests don't work because we are not able to take back + #changes that later on turn out to be not necessary, because the package + #that induced the change gets masked. + #~ (["=net-www/J-1", "=net-www/K-1"], {"--autounmask": True}, None, True, \ + #~ ["net-www/I-1", "net-www/H-1", "net-www/J-1", "net-www/K-1"] ), + (["=net-www/J-2", "=net-www/K-1"], {"--autounmask": True}, None, True, \ + ["net-www/I-1", "net-www/K-1", "net-www/H-1", "net-www/J-2", ] ), + #~ (["=net-www/K-1", "=net-www/J-1"], {"--autounmask": True}, None, True, \ + #~ ["net-www/I-1", "net-www/H-1", "net-www/J-1", "net-www/K-1"] ), + (["=net-www/K-1", "=net-www/J-2"], {"--autounmask": True}, None, True, \ + ["net-www/I-1", "net-www/K-1", "net-www/H-1", "net-www/J-2", ] ), + ) + + playground = ResolverPlayground(ebuilds=ebuilds) + try: + for atoms, options, action, \ + expected_result, expected_mergelist in requests: + result = playground.run(atoms, options, action) + self.assertEqual((result.success, result.mergelist), + (expected_result, expected_mergelist)) + finally: + playground.cleanup() diff --git a/pym/portage/tests/resolver/test_eapi.py b/pym/portage/tests/resolver/test_eapi.py index 19c7b2193..d9f34f43e 100644 --- a/pym/portage/tests/resolver/test_eapi.py +++ b/pym/portage/tests/resolver/test_eapi.py @@ -4,7 +4,7 @@ from portage.tests import TestCase from portage.tests.resolver.ResolverPlayground import ResolverPlayground -class SimpleResolverTestCase(TestCase): +class EAPITestCase(TestCase): def testEAPI(self): ebuilds = { @@ -95,8 +95,8 @@ class SimpleResolverTestCase(TestCase): try: for atoms, options, action, \ expected_result, expected_mergelist in requests: - success, mergelist = playground.run(atoms, options, action) - self.assertEqual((success, mergelist), + result = playground.run(atoms, options, action) + self.assertEqual((result.success, result.mergelist), (expected_result, expected_mergelist)) finally: playground.cleanup() diff --git a/pym/portage/tests/resolver/test_simple.py b/pym/portage/tests/resolver/test_simple.py index 0e77c9e6d..ef19abe1b 100644 --- a/pym/portage/tests/resolver/test_simple.py +++ b/pym/portage/tests/resolver/test_simple.py @@ -27,8 +27,8 @@ class SimpleResolverTestCase(TestCase): try: for atoms, options, action, \ expected_result, expected_mergelist in requests: - success, mergelist = playground.run(atoms, options, action) - self.assertEqual((success, mergelist), + result = playground.run(atoms, options, action) + self.assertEqual((result.success, result.mergelist), (expected_result, expected_mergelist)) finally: playground.cleanup() -- 2.26.2