param icon indicating copy to clipboard operation
param copied to clipboard

Enforce user to specify a value

Open MarcSkovMadsen opened this issue 2 years ago • 1 comments

I am designing a Parameterized class that requires some of the parameters to be set on instantiation.

I would expect the below to raise an error. But it does not

import param
class CronjobSpec(param.Parameterized):
    schedule = param.String(default=None, allow_None=False)

CronjobSpec()

Workaround

If I create a custom __init__ I can get it working.

import param
class CronjobSpec(param.Parameterized):
    schedule = param.String()

    def __init__(self, schedule: str, **params):
        super().__init__(schedule, **params)

CronjobSpec()
$ python 'script.py'
Traceback (most recent call last):
  File "script.py", line 8, in <module>
    CronjobSpec()
TypeError: __init__() missing 1 required positional argument: 'schedule'

MarcSkovMadsen avatar Nov 22 '21 14:11 MarcSkovMadsen

Congratulations! You've made a duplicate of the very first issue ever opened on the Param github repo: https://github.com/holoviz/param/issues/1 . :-) Another user also requested this recently, on some other forum (Stackoverflow, maybe?). It's related to https://github.com/holoviz/param/issues/97 , in that I think we should define a non-None value that is Undefined or NotImplemented, to distinguish between a valid value of None and an invalid value that should force inheritance from a superclass and eventually error if not ever set.

I'd be happy for someone to investigate what it would take to close issues 1 and 97, which I don't think is difficult but requires some work to see what sentinel value is appropriate and whether we can preserve backwards compatibility properly if we change various None defaults to this sentinel. I'll close this issue as a duplicate, but it's still a valid request!

BTW, detecting the case you showed above is tricky, because allow_None is False by default, and so specifying it explicitly like that has no effect. It then falls down to the logic that infers that if a user creates a Parameter with a default value of None, None must be allowed, which is generally true but not your intention in this case. Detecting that you had specified allow_None=False explicitly would require something like making it None by default, treating that like False, and then raising an error in the above code. I suppose that would be a way to achieve what you are requesting (and what #1 requests) without a new sentinel value, but I'm not sure it's clearer.

jbednar avatar Nov 23 '21 00:11 jbednar

As mentioned above, this is a duplicate of #1

maximlt avatar Apr 15 '23 23:04 maximlt