expose NoUpdate
Expose NoUpdate at top-level dash.
The primary application is for type hinting, allowing for comprehensive type checking of dash callbacks.
See: #2799
Contributor Checklist
- [X] Expose
NoUpdatefromdash._callback - [X] I have run the tests locally and they passed. (refer to testing section in contributing)
- [X] I have added tests, or extended existing tests, to cover any new features or bugs fixed in this PR
I just pushed the minimal possible change in my mind: renaming NoUpdate to NoUpdateType and exposing it.
This does not implement the behavior @ndrezn mentions as it will still be of type dash._callback.NoUpdateType, but is there value in it being dash.NoUpdate? It's the only class as the other two imported into dash are functions, so maybe NoUpdate is just declared in the wrong module?
Given NoUpdate can be entirely described by {"_dash_no_update": "_dash_no_update"} (see context in #2800), can it not somehow inherit from Dict or TypedDict? This could make its behavior much more predictable and pythonic.
Given
NoUpdatecan be entirely described by{"_dash_no_update": "_dash_no_update"}(see context in #2800), can it not somehow inherit fromDictorTypedDict? This could make its behavior much more predictable and pythonic.
It does not equate to a typed dict, it's a singleton object, the dict representation is for internal use.
In an attempt to keep the implementation of this PR at a minimum and, if I'm interpreting the conversation correctly up until now, is there any objection to the current state of this PR?
any lingering comments from you?
I'd rather we fix the cases where using NoUpdate would be creating an error instead of renaming the variable in hope it won't be used.
I think the only case is actually just returning the class like this:
from dash import NoUpdate
def cb(...):
return NoUpdate
intead of return NoUpdate()
Think we can add the check like this:
@staticmethod
def is_no_update(obj):
return obj is NoUpdate or isinstance(obj, NoUpdate) or (
isinstance(obj, dict) and obj == {"_dash_no_update": "_dash_no_update"}
)
Then change all our checks to NoUpdate.is_no_update(obj):
- https://github.com/plotly/dash/blob/15e97b85d24461dfce907d038b7788db75d1f005/dash/_callback.py#L474
- https://github.com/plotly/dash/blob/15e97b85d24461dfce907d038b7788db75d1f005/dash/_callback.py#L479
any lingering comments from you?
I'd rather we fix the cases where using
NoUpdatewould be creating an error instead of renaming the variable in hope it won't be used. I think the only case is actually just returning the class like this:from dash import NoUpdate def cb(...): return NoUpdateintead of
return NoUpdate()Think we can add the check like this:
@staticmethod def is_no_update(obj): return obj is NoUpdate or isinstance(obj, NoUpdate) or ( isinstance(obj, dict) and obj == {"_dash_no_update": "_dash_no_update"} )Then change all our checks to
NoUpdate.is_no_update(obj):
- https://github.com/plotly/dash/blob/15e97b85d24461dfce907d038b7788db75d1f005/dash/_callback.py#L474
- https://github.com/plotly/dash/blob/15e97b85d24461dfce907d038b7788db75d1f005/dash/_callback.py#L479
I agree with this. Specifically, return NoUpdate seems like a more desirable behavior than return no_update.
However, such a change seems adjacent to the topic of this PR which is to simply expose the value. I am more than happy to open another PR suggesting this change.