@@ -190,6 +190,8 @@ class property(DynamicClassAttribute):
190
190
"""
191
191
192
192
member = None
193
+ _attr_type = None
194
+ _cls_type = None
193
195
194
196
def __get__ (self , instance , ownerclass = None ):
195
197
if instance is None :
@@ -199,33 +201,36 @@ def __get__(self, instance, ownerclass=None):
199
201
raise AttributeError (
200
202
'%r has no attribute %r' % (ownerclass , self .name )
201
203
)
202
- else :
203
- if self .fget is None :
204
- # look for a member by this name.
205
- try :
206
- return ownerclass ._member_map_ [self .name ]
207
- except KeyError :
208
- raise AttributeError (
209
- '%r has no attribute %r' % (ownerclass , self .name )
210
- ) from None
211
- else :
212
- return self .fget (instance )
204
+ if self .fget is not None :
205
+ # use previous enum.property
206
+ return self .fget (instance )
207
+ elif self ._attr_type == 'attr' :
208
+ # look up previous attibute
209
+ return getattr (self ._cls_type , self .name )
210
+ elif self ._attr_type == 'desc' :
211
+ # use previous descriptor
212
+ return getattr (instance ._value_ , self .name )
213
+ # look for a member by this name.
214
+ try :
215
+ return ownerclass ._member_map_ [self .name ]
216
+ except KeyError :
217
+ raise AttributeError (
218
+ '%r has no attribute %r' % (ownerclass , self .name )
219
+ ) from None
213
220
214
221
def __set__ (self , instance , value ):
215
- if self .fset is None :
216
- raise AttributeError (
217
- "<enum %r> cannot set attribute %r" % (self .clsname , self .name )
218
- )
219
- else :
222
+ if self .fset is not None :
220
223
return self .fset (instance , value )
224
+ raise AttributeError (
225
+ "<enum %r> cannot set attribute %r" % (self .clsname , self .name )
226
+ )
221
227
222
228
def __delete__ (self , instance ):
223
- if self .fdel is None :
224
- raise AttributeError (
225
- "<enum %r> cannot delete attribute %r" % (self .clsname , self .name )
226
- )
227
- else :
229
+ if self .fdel is not None :
228
230
return self .fdel (instance )
231
+ raise AttributeError (
232
+ "<enum %r> cannot delete attribute %r" % (self .clsname , self .name )
233
+ )
229
234
230
235
def __set_name__ (self , ownerclass , name ):
231
236
self .name = name
@@ -313,27 +318,38 @@ def __set_name__(self, enum_class, member_name):
313
318
enum_class ._member_names_ .append (member_name )
314
319
# if necessary, get redirect in place and then add it to _member_map_
315
320
found_descriptor = None
321
+ descriptor_type = None
322
+ class_type = None
316
323
for base in enum_class .__mro__ [1 :]:
317
- descriptor = base .__dict__ .get (member_name )
318
- if descriptor is not None :
319
- if isinstance (descriptor , (property , DynamicClassAttribute )):
320
- found_descriptor = descriptor
324
+ attr = base .__dict__ .get (member_name )
325
+ if attr is not None :
326
+ if isinstance (attr , (property , DynamicClassAttribute )):
327
+ found_descriptor = attr
328
+ class_type = base
329
+ descriptor_type = 'enum'
321
330
break
322
- elif (
323
- hasattr (descriptor , 'fget' ) and
324
- hasattr (descriptor , 'fset' ) and
325
- hasattr (descriptor , 'fdel' )
326
- ):
327
- found_descriptor = descriptor
331
+ elif _is_descriptor (attr ):
332
+ found_descriptor = attr
333
+ descriptor_type = descriptor_type or 'desc'
334
+ class_type = class_type or base
328
335
continue
336
+ else :
337
+ descriptor_type = 'attr'
338
+ class_type = base
329
339
if found_descriptor :
330
340
redirect = property ()
331
341
redirect .member = enum_member
332
342
redirect .__set_name__ (enum_class , member_name )
333
- # earlier descriptor found; copy fget, fset, fdel to this one.
334
- redirect .fget = found_descriptor .fget
335
- redirect .fset = found_descriptor .fset
336
- redirect .fdel = found_descriptor .fdel
343
+ if descriptor_type in ('enum' ,'desc' ):
344
+ # earlier descriptor found; copy fget, fset, fdel to this one.
345
+ redirect .fget = getattr (found_descriptor , 'fget' , None )
346
+ redirect ._get = getattr (found_descriptor , '__get__' , None )
347
+ redirect .fset = getattr (found_descriptor , 'fset' , None )
348
+ redirect ._set = getattr (found_descriptor , '__set__' , None )
349
+ redirect .fdel = getattr (found_descriptor , 'fdel' , None )
350
+ redirect ._del = getattr (found_descriptor , '__delete__' , None )
351
+ redirect ._attr_type = descriptor_type
352
+ redirect ._cls_type = class_type
337
353
setattr (enum_class , member_name , redirect )
338
354
else :
339
355
setattr (enum_class , member_name , enum_member )
0 commit comments