8000 gh-93820: Fix copy() regression in enum.Flag (GH-93876) (#93886) · python/cpython@3fbf5c6 · GitHub
[go: up one dir, main page]

Skip to content

Commit 3fbf5c6

Browse files
gh-93820: Fix copy() regression in enum.Flag (GH-93876) (#93886)
GH-26658 introduced a regression in copy / pickle protocol for combined `enum.Flag`s. `copy.copy(re.A | re.I)` would fail with `AttributeError: ASCII|IGNORECASE`. `enum.Flag` now has a `__reduce_ex__()` method that reduces flags by combined value, not by combined name. (cherry picked from commit 05b32c1) Co-authored-by: Christian Heimes <christian@python.org> Co-authored-by: Christian Heimes <christian@python.org>
1 parent 7456109 commit 3fbf5c6

File tree

3 files changed

+33
-0
lines changed
  • test
  • Misc/NEWS.d/next/Library
  • 3 files changed

    +33
    -0
    lines changed

    Lib/enum.py

    Lines changed: 3 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -1372,6 +1372,9 @@ class Flag(Enum, boundary=STRICT):
    13721372
    Support for flags
    13731373
    """
    13741374

    1375+
    def __reduce_ex__(self, proto):
    1376+
    return self.__class__, (self._value_, )
    1377+
    13751378
    _numeric_repr_ = repr
    13761379

    13771380
    def _generate_next_value_(name, start, count, last_values):

    Lib/test/test_enum.py

    Lines changed: 28 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -1,3 +1,4 @@
    1+
    import copy
    12
    import enum
    23
    import doctest
    34
    import inspect
    @@ -732,6 +733,13 @@ def test_format_specs(self):
    732733
    self.assertFormatIsValue('{:5.2}', TE.third)
    733734
    self.assertFormatIsValue('{:f}', TE.third)
    734735

    736+
    def test_copy(self):
    737+
    TE = self.MainEnum
    738+
    copied = copy.copy(TE)
    739+
    self.assertEqual(copied, TE)
    740+
    deep = copy.deepcopy(TE)
    741+
    self.assertEqual(deep, TE)
    742+
    735743

    736744
    class _FlagTests:
    737745

    @@ -2652,6 +2660,26 @@ class MyIntFlag(int, Flag):
    26522660
    self.assertTrue(isinstance(MyIntFlag.ONE | MyIntFlag.TWO, MyIntFlag), MyIntFlag.ONE | MyIntFlag.TWO)
    26532661
    self.assertTrue(isinstance(MyIntFlag.ONE | 2, MyIntFlag))
    26542662

    2663+
    def test_int_flags_copy(self):
    2664+
    class MyIntFlag(IntFlag):
    2665+
    ONE = 1
    2666+
    TWO = 2
    2667+
    FOUR = 4
    2668+
    2669+
    flags = MyIntFlag.ONE | MyIntFlag.TWO
    2670+
    copied = copy.copy(flags)
    2671+
    deep = copy.deepcopy(flags)
    2672+
    self.assertEqual(copied, flags)
    2673+
    self.assertEqual(deep, flags)
    2674+
    2675+
    flags = MyIntFlag.ONE | MyIntFlag.TWO | 8
    2676+
    copied = copy.copy(flags)
    2677+
    deep = copy.deepcopy(flags)
    2678+
    self.assertEqual(copied, flags)
    2679+
    self.assertEqual(deep, flags)
    2680+
    self.assertEqual(copied.value, 1 | 2 | 8)
    2681+
    2682+
    26552683
    class TestOrder(unittest.TestCase):
    26562684
    "test usage of the `_order_` attribute"
    26572685

    Lines changed: 2 additions & 0 deletions
    Original file line numberDiff line numberDiff line change
    @@ -0,0 +1,2 @@
    1+
    Fixed a regression when :func:`copy.copy`-ing :class:`enum.Flag` with
    2+
    multiple flag members.

    0 commit comments

    Comments
     (0)
    0