@@ -56,7 +56,16 @@ def __get__(self, obj, objtype):
5656 (objtype .__name__ , self ._name )) from None
5757
5858 def __set__ (self , obj , value ):
59- obj .__dict__ [self ._name ] = remove_convertible (value )
59+ # NOTE: We extend the Python data model by returning the value that
60+ # would be otherwise written to the field, if ``obj`` is :obj:`None`.
61+ # Subclasses must make sure to return to the caller the value returned
62+ # from ``super().__set__(...)``.
63+
64+ value = remove_convertible (value )
65+ if obj is None :
66+ return value
67+
68+ obj .__dict__ [self ._name ] = value
6069
6170
6271class TypedField (Field ):
@@ -79,7 +88,7 @@ def _check_type(self, value):
7988 if not any (isinstance (value , t ) for t in self ._types ):
8089 typedescr = '|' .join (t .__name__ for t in self ._types )
8190 raise TypeError (
82- "failed to set field '%s': '%s' is not of type '%s'" %
91+ "failed to set variable '%s': '%s' is not of type '%s'" %
8392 (self ._name , value , typedescr ))
8493
8594 def __set__ (self , obj , value ):
@@ -100,18 +109,17 @@ def __set__(self, obj, value):
100109 except TypeError :
101110 continue
102111 else :
103- super ().__set__ (obj , value )
104- return
112+ return super ().__set__ (obj , value )
105113
106114 # Conversion failed
107115 typenames = [t .__name__ for t in self ._types ]
108116 raise TypeError (
109- f'failed to set field { self ._name !r} : '
117+ f'failed to set variable { self ._name !r} : '
110118 f'could not convert to any of the supported types: '
111119 f'{ typenames } '
112120 )
113121 else :
114- super ().__set__ (obj , value )
122+ return super ().__set__ (obj , value )
115123
116124
117125class ConstantField (Field ):
@@ -152,7 +160,7 @@ def __set__(self, obj, value):
152160 if not isinstance (value , ScopedDict ):
153161 value = ScopedDict (value ) if value is not None else value
154162
155- Field .__set__ (self , obj , value )
163+ return Field .__set__ (self , obj , value )
156164
157165
158166class DeprecatedField (Field ):
@@ -187,7 +195,7 @@ def __set__(self, obj, value):
187195 if self ._op & DeprecatedField .OP_SET :
188196 user_deprecation_warning (self ._message , self ._from_version )
189197
190- self ._target_field .__set__ (obj , value )
198+ return self ._target_field .__set__ (obj , value )
191199
192200 def __get__ (self , obj , objtype ):
193201 if self ._op & DeprecatedField .OP_GET :
0 commit comments