mirror of
https://github.com/python/cpython.git
synced 2025-12-08 06:10:17 +00:00
bpo-44559: [Enum] restore fixes lost in 3.9 reversion (GH-29114)
- fix exception leaks - re-add deprecation warnings
This commit is contained in:
parent
64e83c711e
commit
2a9ab75af3
3 changed files with 194 additions and 42 deletions
60
Lib/enum.py
60
Lib/enum.py
|
|
@ -44,10 +44,11 @@ def _is_sunder(name):
|
|||
def _is_private(cls_name, name):
|
||||
# do not use `re` as `re` imports `enum`
|
||||
pattern = '_%s__' % (cls_name, )
|
||||
pat_len = len(pattern)
|
||||
if (
|
||||
len(name) >= 5
|
||||
len(name) > pat_len
|
||||
and name.startswith(pattern)
|
||||
and name[len(pattern)] != '_'
|
||||
and name[pat_len:pat_len+1] != ['_']
|
||||
and (name[-1] != '_' or name[-2] != '_')
|
||||
):
|
||||
return True
|
||||
|
|
@ -392,12 +393,19 @@ def __call__(cls, value, names=None, *, module=None, qualname=None, type=None, s
|
|||
start=start,
|
||||
)
|
||||
|
||||
def __contains__(cls, member):
|
||||
if not isinstance(member, Enum):
|
||||
def __contains__(cls, obj):
|
||||
if not isinstance(obj, Enum):
|
||||
import warnings
|
||||
warnings.warn(
|
||||
"in 3.12 __contains__ will no longer raise TypeError, but will return True if\n"
|
||||
"obj is a member or a member's value",
|
||||
DeprecationWarning,
|
||||
stacklevel=2,
|
||||
)
|
||||
raise TypeError(
|
||||
"unsupported operand type(s) for 'in': '%s' and '%s'" % (
|
||||
type(member).__qualname__, cls.__class__.__qualname__))
|
||||
return isinstance(member, cls) and member._name_ in cls._member_map_
|
||||
type(obj).__qualname__, cls.__class__.__qualname__))
|
||||
return isinstance(obj, cls) and obj._name_ in cls._member_map_
|
||||
|
||||
def __delattr__(cls, attr):
|
||||
# nicer error message when someone tries to delete an attribute
|
||||
|
|
@ -580,7 +588,7 @@ def _get_mixins_(class_name, bases):
|
|||
return object, Enum
|
||||
|
||||
def _find_data_type(bases):
|
||||
data_types = []
|
||||
data_types = set()
|
||||
for chain in bases:
|
||||
candidate = None
|
||||
for base in chain.__mro__:
|
||||
|
|
@ -588,19 +596,19 @@ def _find_data_type(bases):
|
|||
continue
|
||||
elif issubclass(base, Enum):
|
||||
if base._member_type_ is not object:
|
||||
data_types.append(base._member_type_)
|
||||
data_types.add(base._member_type_)
|
||||
break
|
||||
elif '__new__' in base.__dict__:
|
||||
if issubclass(base, Enum):
|
||||
continue
|
||||
data_types.append(candidate or base)
|
||||
data_types.add(candidate or base)
|
||||
break
|
||||
else:
|
||||
candidate = candidate or base
|
||||
if len(data_types) > 1:
|
||||
raise TypeError('%r: too many data types: %r' % (class_name, data_types))
|
||||
elif data_types:
|
||||
return data_types[0]
|
||||
return data_types.pop()
|
||||
else:
|
||||
return None
|
||||
|
||||
|
|
@ -693,19 +701,25 @@ def __new__(cls, value):
|
|||
except Exception as e:
|
||||
exc = e
|
||||
result = None
|
||||
if isinstance(result, cls):
|
||||
return result
|
||||
else:
|
||||
ve_exc = ValueError("%r is not a valid %s" % (value, cls.__qualname__))
|
||||
if result is None and exc is None:
|
||||
raise ve_exc
|
||||
elif exc is None:
|
||||
exc = TypeError(
|
||||
'error in %s._missing_: returned %r instead of None or a valid member'
|
||||
% (cls.__name__, result)
|
||||
)
|
||||
exc.__context__ = ve_exc
|
||||
raise exc
|
||||
try:
|
||||
if isinstance(result, cls):
|
||||
return result
|
||||
else:
|
||||
ve_exc = ValueError("%r is not a valid %s" % (value, cls.__qualname__))
|
||||
if result is None and exc is None:
|
||||
raise ve_exc
|
||||
elif exc is None:
|
||||
exc = TypeError(
|
||||
'error in %s._missing_: returned %r instead of None or a valid member'
|
||||
% (cls.__name__, result)
|
||||
)
|
||||
if not isinstance(exc, ValueError):
|
||||
exc.__context__ = ve_exc
|
||||
raise exc
|
||||
finally:
|
||||
# ensure all variables that could hold an exception are destroyed
|
||||
exc = None
|
||||
ve_exc = None
|
||||
|
||||
def _generate_next_value_(name, start, count, last_values):
|
||||
"""
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue