From f8ee9a2120250f3224627590c927643242927c82 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Piotr=20Ma=C5=9Blanka?= <piotr.maslanka@henrietta.com.pl> Date: Fri, 9 Apr 2021 18:58:06 +0200 Subject: [PATCH] add equality and membership tests to Optional --- CHANGELOG.md | 2 ++ satella/__init__.py | 2 +- satella/coding/optionals.py | 20 ++++++++++++++++++++ tests/test_coding/test_optionals.py | 11 +++++++++++ 4 files changed, 34 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f9f57d74..218f83ad 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1 +1,3 @@ # v2.15.6 + +* added equality checking and membership test to Optional diff --git a/satella/__init__.py b/satella/__init__.py index a493016b..bfc8e94c 100644 --- a/satella/__init__.py +++ b/satella/__init__.py @@ -1 +1 @@ -__version__ = '2.15.6a1' +__version__ = '2.15.6' diff --git a/satella/coding/optionals.py b/satella/coding/optionals.py index 893a16f9..596fe984 100644 --- a/satella/coding/optionals.py +++ b/satella/coding/optionals.py @@ -54,12 +54,32 @@ class Optional(Proxy): * getattr * getitem/setitem/delitem * testing for truth + * comparison (with nonexistent elements always comparing false) + * membership test (with nonexistent elements always returning false) + + .. warning:: Returned objects via getattr and getitem are NOT wrapped in an + Optional. You need to do it by hand or just file an issue. I'll add that when I + need it. + + :param obj: object to wrap """ __slots__ = () def __init__(self, obj): super().__init__(obj) + def __contains__(self, item) -> bool: + me = getattr(self, '_Proxy__obj') + if me is None: + return False + return item in me + + def __eq__(self, other) -> bool: + me = getattr(self, '_Proxy__obj') + if me is None: + return False + return me == other + def __getattr__(self, item): if getattr(self, '_Proxy__obj') is None: return EMPTY_OPTIONAL diff --git a/tests/test_coding/test_optionals.py b/tests/test_coding/test_optionals.py index fc7e7be8..34e75ce9 100644 --- a/tests/test_coding/test_optionals.py +++ b/tests/test_coding/test_optionals.py @@ -15,6 +15,17 @@ class TestOptionals(unittest.TestCase): self.assertFalse(c) self.assertTrue(b) + def test_optional_eq(self): + class Opt: + a = 5 + b = [2] + + a = Opt() + self.assertEqual(Optional(a).a, 5) + self.assertIn(2, Optional(a).b) + self.assertNotEqual(Optional(None).a, 5) + self.assertNotIn(2, Optional(None).b) + def test_optional(self): self.assertIsNone(call_if_nnone(None)) b = call_if_nnone(lambda y: y, 5) -- GitLab