From a45a0563dc43cc5b8941fbc90d7a05a2d7345293 Mon Sep 17 00:00:00 2001 From: Sylvain MARIE Date: Tue, 10 May 2022 22:30:19 +0200 Subject: [PATCH] Improved compatibility with other `pytest` plugins, in particular `pytest-repeat`, by support removal from fixture closure tree. Fixed #269 --- docs/changelog.md | 1 + src/pytest_cases/plugin.py | 26 ++++++++++++++++++- .../pytest_extension/issues/test_issue_269.py | 4 +-- 3 files changed, 28 insertions(+), 3 deletions(-) diff --git a/docs/changelog.md b/docs/changelog.md index 74d02281..8fbdc069 100644 --- a/docs/changelog.md +++ b/docs/changelog.md @@ -2,6 +2,7 @@ ### 3.6.12 - type hint fix + - Improved compatibility with other `pytest` plugins, in particular `pytest-repeat`, by support removal from fixture closure tree. Fixed [#269](https://github.com/smarie/python-pytest-cases/issues/269). - Fixed type hint errors detected by `pyright`. Fixed [#270](https://github.com/smarie/python-pytest-cases/issues/270) ### 3.6.11 - bugfix for pytest-xdist and `get_all_cases` API improvement diff --git a/src/pytest_cases/plugin.py b/src/pytest_cases/plugin.py index fabb2b2f..27367ed5 100644 --- a/src/pytest_cases/plugin.py +++ b/src/pytest_cases/plugin.py @@ -640,13 +640,21 @@ def __setitem__(self, i, o): return else: if isinstance(i, slice): - if set(o) == set(ref): + new_set = set(o) + ref_set = set(ref) + if new_set == ref_set: # a change is required in the order of fixtures. Ignore but continue warn("WARNING: An attempt was made to reorder a super fixture closure with unions. This is not yet " "supported since the partitions use subsets of the fixtures ; please report it so that we can " "find a suitable solution for your need.") return + added = new_set.difference(ref_set) + removed = ref_set.difference(new_set) + self.append_all(added) + self.remove_all(removed) + return + # At least one change of fixture name is required: not supported, and reject as it is raise NotImplementedError("It is not possible to replace an element in a super fixture closure," "as the partitions inside it do not have the same size") @@ -695,6 +703,14 @@ def insert(self, index, fixture_name): # Finally update self.fixture_defs so that the "list" view reflects the changes in self.tree self._update_fixture_defs() + def append_all(self, fixture_names): + """Append various fixture names to the closure""" + # appending is natively supported in our tree growing method + self.tree.build_closure(tuple(fixture_names)) + + # Finally update self.fixture_defs so that the "list" view reflects the changes in self.tree + self._update_fixture_defs() + def remove(self, value): """ Try to transparently support removal. Note: since the underlying structure is a tree, @@ -709,6 +725,14 @@ def remove(self, value): # update fixture defs self._update_fixture_defs() + def remove_all(self, values): + """Multiple `remove` operations at once.""" + # remove in the tree + self.tree.remove_fixtures(tuple(values)) + + # update fixture defs + self._update_fixture_defs() + def getfixtureclosure(fm, fixturenames, parentnode, ignore_args=()): """ diff --git a/tests/pytest_extension/issues/test_issue_269.py b/tests/pytest_extension/issues/test_issue_269.py index 3d73120b..225fe366 100644 --- a/tests/pytest_extension/issues/test_issue_269.py +++ b/tests/pytest_extension/issues/test_issue_269.py @@ -40,6 +40,6 @@ def test_repeat(arg): def test_synthesis(module_results_dct): """Make sure that two tests were created.""" assert list(module_results_dct) == [ - "test_repeat-1-2", - "test_repeat-2-2" + "test_repeat[my_fix-1-2]", + "test_repeat[my_fix-2-2]" ]