Skip to content

No error raised when a method depends on Parameterized instances set after calling super() #566

@maximlt

Description

@maximlt

See this example taken from Panel's user guide. The two objects must be declared in the __init__ before calling super().

class P2(param.Parameterized):
    value = param.String()

class P1(param.Parameterized):
    
    def __init__(self, **params):
        # Works as expected when declared before
        # self.p2 = P2()
        super().__init__(**params)
        # Does not work when declared after super()
        # Raises an error in param<1.12, nothing for param 1.12
        self.p2 = P2()

    @param.depends('p2.value', watch=True)
    def cb(self):
        print('fired')

When they're declared after as in the example above, the following error used to be raised (this is param 1.11.1):

--------------------------------------------------------------------------
AttributeError                            Traceback (most recent call last)
<ipython-input-36-7e8d061f6e7f> in <module>
----> 1 p1 = P1()

<ipython-input-35-d76ac1c5846c> in __init__(self, **params)
      6     def __init__(self, **params):
      7 #         self.p2 = P2()
----> 8         super().__init__(**params)
      9         self.p2 = P2()
     10 

~/miniconda3/envs/holoviz37/lib/python3.7/site-packages/param/parameterized.py in __init__(self, **params)
   2610                 # 'dependers'.
   2611                 grouped = defaultdict(list)
-> 2612                 for dep in self.param.params_depended_on(n):
   2613                     grouped[(id(dep.inst),id(dep.cls),dep.what)].append(dep)
   2614                 for group in grouped.values():

~/miniconda3/envs/holoviz37/lib/python3.7/site-packages/param/parameterized.py in params_depended_on(self_, name)
   1858 
   1859     def params_depended_on(self_,name):
-> 1860         return _params_depended_on(MInfo(cls=self_.cls,inst=self_.self,name=name,method=getattr(self_.self_or_cls,name)))
   1861 
   1862 

~/miniconda3/envs/holoviz37/lib/python3.7/site-packages/param/parameterized.py in _params_depended_on(minfo)
    500     dinfo = getattr(minfo.method,"_dinfo", {})
    501     for d in dinfo.get('dependencies', list(minfo.cls.param)):
--> 502         things = (minfo.inst or minfo.cls).param._spec_to_obj(d)
    503         for thing in things:
    504             if isinstance(thing,PInfo):

~/miniconda3/envs/holoviz37/lib/python3.7/site-packages/param/parameterized.py in _spec_to_obj(self_, spec)
   1902         attr = m.group("attr")
   1903 
-> 1904         src = self_.self_or_cls if obj=='' else _getattrr(self_.self_or_cls,obj[1::])
   1905         cls,inst = (src, None) if isinstance(src, type) else (type(src), src)
   1906 

~/miniconda3/envs/holoviz37/lib/python3.7/site-packages/param/parameterized.py in _getattrr(obj, attr, *args)
    281     def _getattr(obj, attr):
    282         return getattr(obj, attr, *args)
--> 283     return reduce(_getattr, [obj] + attr.split('.'))
    284 
    285 

~/miniconda3/envs/holoviz37/lib/python3.7/site-packages/param/parameterized.py in _getattr(obj, attr)
    280 def _getattrr(obj, attr, *args):
    281     def _getattr(obj, attr):
--> 282         return getattr(obj, attr, *args)
    283     return reduce(_getattr, [obj] + attr.split('.'))
    284 

AttributeError: 'P1' object has no attribute 'p2'

Even though it's an error message that's quite hard to understand, at least there was an error. The current version on master doesn't raise any.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions