traits icon indicating copy to clipboard operation
traits copied to clipboard

Consider deprecating the ability to define Instance with an instance

Open mdickinson opened this issue 3 years ago • 0 comments

Current Traits allows an Instance trait to be given an instance rather than a type as the first argument. It then replaces that instance with its type. So for example, the trait declaration Instance(99.7) is equivalent to the declaration Instance(float):

>>> from traits.api import *
>>> class A(HasTraits):
...     weight = Instance(99.7)
... 
>>> a = A()
>>> a.weight = "a string"
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "/Users/mdickinson/Enthought/ETS/traits/traits/base_trait_handler.py", line 74, in error
    raise TraitError(
traits.trait_errors.TraitError: The 'weight' trait of an A instance must be a float or None, but a value of 'a string' <class 'str'> was specified.
>>> a.weight
>>> a.weight is None
True

However, note that if the argument to Instance is a string, it's treated specially, to allow classes to be referred to by name. That part is out of scope for this issue: I'm not proposing changing this aspect of the behaviour.

I'm proposing deprecating the functionality above. It represents an extra way to do it that provides little value over specifying the type directly; the behaviour is non-obvious for code readers - especially since the particular instance passed into Instance is simply discarded, and it's potentially a trap: if something that's not a type is passed by accident, the behaviour can be surprising. See #1408 for an example of this.

mdickinson avatar Jan 18 '21 15:01 mdickinson