Skip to content

Commit

Permalink
Ensure operations that are unsafe during instance initialization rais…
Browse files Browse the repository at this point in the history
…e errors (#834)

Co-authored-by: maximlt <mliquet@anaconda.com>
  • Loading branch information
philippjfr and maximlt authored Sep 18, 2023
1 parent b7bb742 commit 0ee6ed9
Show file tree
Hide file tree
Showing 2 changed files with 64 additions and 0 deletions.
22 changes: 22 additions & 0 deletions param/parameterized.py
Original file line number Diff line number Diff line change
Expand Up @@ -2215,6 +2215,14 @@ def objects(self_, instance=True):
instance parameters to be returned by setting
instance='existing'.
"""
if self_.self is not None and not self_.self._param__private.initialized and instance is True:
raise RuntimeError(
'Cannot look up instantiated Parameter objects until the Parameterized instance '
'has been fully initialized. Ensure you have called super().__init__(**params) '
'in your Parameterized constructor before trying to access instance '
'parameter objects.'
)

cls = self_.cls
# We cache the parameters because this method is called often,
# and parameters are rarely added (and cannot be deleted)
Expand Down Expand Up @@ -2252,6 +2260,13 @@ def trigger(self_, *param_names):
changed for a Parameter of type Event, setting it to True so
that it is clear which Event parameter has been triggered.
"""
if self_.self is not None and not self_.self._param__private.initialized:
raise RuntimeError(
'Triggering watchers on a partially initialized Parameterized instance '
'is not supported. Ensure you have called super().__init__(**params) in '
'the Parameterized instance constructor before trying to set up a watcher.'
)

trigger_params = [p for p in self_.self_or_cls.param
if hasattr(self_.self_or_cls.param[p], '_autotrigger_value')]
triggers = {p:self_.self_or_cls.param[p]._autotrigger_value
Expand Down Expand Up @@ -2695,6 +2710,13 @@ def _spec_to_obj(self_, spec, dynamic=True, intermediate=True):
return deps, dynamic_deps

def _register_watcher(self_, action, watcher, what='value'):
if self_.self is not None and not self_.self._param__private.initialized:
raise RuntimeError(
'(Un)registering a watcher on a partially initialized Parameterized instance '
'is not supported. Ensure you have called super().__init__(**) in '
'the Parameterized instance constructor before trying to set up a watcher.'
)

parameter_names = watcher.parameter_names
for parameter_name in parameter_names:
if parameter_name not in self_.cls.param:
Expand Down
42 changes: 42 additions & 0 deletions tests/testparameterizedobject.py
Original file line number Diff line number Diff line change
Expand Up @@ -495,6 +495,48 @@ def __init__(self, x=1):
with pytest.raises(TypeError, match="Read-only parameter 'x' cannot be modified"):
P()

def test_param_error_unsafe_ops_before_initialized(self):
class P(param.Parameterized):

x = param.Parameter()

def __init__(self, **params):
with pytest.raises(
RuntimeError,
match=re.escape(
'Cannot look up instantiated Parameter objects until the Parameterized instance '
'has been fully initialized. Ensure you have called super().__init__(**params) '
'in your Parameterized constructor before trying to access instance '
'parameter objects.'
)
):
self.param.objects()

with pytest.raises(
RuntimeError,
match=re.escape(
'Triggering watchers on a partially initialized Parameterized instance '
'is not supported. Ensure you have called super().__init__(**params) in '
'the Parameterized instance constructor before trying to set up a watcher.'
)
):
self.param.trigger('x')

with pytest.raises(
RuntimeError,
match=re.escape(
'(Un)registering a watcher on a partially initialized Parameterized instance '
'is not supported. Ensure you have called super().__init__(**) in '
'the Parameterized instance constructor before trying to set up a watcher.'
)
):
self.param.watch(print, 'x')

self.param.objects(instance=False)
super().__init__(**params)

P()

def test_parameter_constant_iadd_allowed(self):
# Testing https://github.com/holoviz/param/pull/400
class P(param.Parameterized):
Expand Down

0 comments on commit 0ee6ed9

Please sign in to comment.