Handle Var passed to rx.toast (#4405)

* Handle Var passed to `rx.toast`

If the user provides a `Var` for `message` then apply it as `props["title"]` to
avoid a var operations error.

* remove unnecessary parentheses

* remove weird hacks

* get it right pyright

---------

Co-authored-by: Khaleel Al-Adhami <khaleel.aladhami@gmail.com>
This commit is contained in:
Masen Furer 2024-11-21 16:15:01 -08:00 committed by GitHub
parent d4b197b517
commit bbfbc82c9d
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 36 additions and 21 deletions

View File

@ -15,6 +15,8 @@ from reflex.utils.imports import ImportVar
from reflex.utils.serializers import serializer from reflex.utils.serializers import serializer
from reflex.vars import VarData from reflex.vars import VarData
from reflex.vars.base import LiteralVar, Var from reflex.vars.base import LiteralVar, Var
from reflex.vars.function import FunctionVar
from reflex.vars.object import ObjectVar
LiteralPosition = Literal[ LiteralPosition = Literal[
"top-left", "top-left",
@ -232,7 +234,9 @@ class Toaster(Component):
return [hook] return [hook]
@staticmethod @staticmethod
def send_toast(message: str = "", level: str | None = None, **props) -> EventSpec: def send_toast(
message: str | Var = "", level: str | None = None, **props
) -> EventSpec:
"""Send a toast message. """Send a toast message.
Args: Args:
@ -250,20 +254,27 @@ class Toaster(Component):
raise ValueError( raise ValueError(
"Toaster component must be created before sending a toast. (use `rx.toast.provider()`)" "Toaster component must be created before sending a toast. (use `rx.toast.provider()`)"
) )
toast_command = f"{toast_ref}.{level}" if level is not None else toast_ref
if message == "" and ("title" not in props or "description" not in props):
raise ValueError("Toast message or title or description must be provided.")
if props:
args = LiteralVar.create(ToastProps(component_name="rx.toast", **props)) # type: ignore
toast = f"{toast_command}(`{message}`, {str(args)})"
else:
toast = f"{toast_command}(`{message}`)"
toast_action = Var(_js_expr=toast) toast_command = (
return run_script(toast_action) ObjectVar.__getattr__(toast_ref.to(dict), level) if level else toast_ref
).to(FunctionVar)
if isinstance(message, Var):
props.setdefault("title", message)
message = ""
elif message == "" and "title" not in props and "description" not in props:
raise ValueError("Toast message or title or description must be provided.")
if props:
args = LiteralVar.create(ToastProps(component_name="rx.toast", **props)) # pyright: ignore [reportCallIssue, reportGeneralTypeIssues]
toast = toast_command.call(message, args)
else:
toast = toast_command.call(message)
return run_script(toast)
@staticmethod @staticmethod
def toast_info(message: str = "", **kwargs): def toast_info(message: str | Var = "", **kwargs):
"""Display an info toast message. """Display an info toast message.
Args: Args:
@ -276,7 +287,7 @@ class Toaster(Component):
return Toaster.send_toast(message, level="info", **kwargs) return Toaster.send_toast(message, level="info", **kwargs)
@staticmethod @staticmethod
def toast_warning(message: str = "", **kwargs): def toast_warning(message: str | Var = "", **kwargs):
"""Display a warning toast message. """Display a warning toast message.
Args: Args:
@ -289,7 +300,7 @@ class Toaster(Component):
return Toaster.send_toast(message, level="warning", **kwargs) return Toaster.send_toast(message, level="warning", **kwargs)
@staticmethod @staticmethod
def toast_error(message: str = "", **kwargs): def toast_error(message: str | Var = "", **kwargs):
"""Display an error toast message. """Display an error toast message.
Args: Args:
@ -302,7 +313,7 @@ class Toaster(Component):
return Toaster.send_toast(message, level="error", **kwargs) return Toaster.send_toast(message, level="error", **kwargs)
@staticmethod @staticmethod
def toast_success(message: str = "", **kwargs): def toast_success(message: str | Var = "", **kwargs):
"""Display a success toast message. """Display a success toast message.
Args: Args:

View File

@ -59,16 +59,16 @@ class Toaster(Component):
def add_hooks(self) -> list[Var | str]: ... def add_hooks(self) -> list[Var | str]: ...
@staticmethod @staticmethod
def send_toast( def send_toast(
message: str = "", level: str | None = None, **props message: str | Var = "", level: str | None = None, **props
) -> EventSpec: ... ) -> EventSpec: ...
@staticmethod @staticmethod
def toast_info(message: str = "", **kwargs): ... def toast_info(message: str | Var = "", **kwargs): ...
@staticmethod @staticmethod
def toast_warning(message: str = "", **kwargs): ... def toast_warning(message: str | Var = "", **kwargs): ...
@staticmethod @staticmethod
def toast_error(message: str = "", **kwargs): ... def toast_error(message: str | Var = "", **kwargs): ...
@staticmethod @staticmethod
def toast_success(message: str = "", **kwargs): ... def toast_success(message: str | Var = "", **kwargs): ...
@staticmethod @staticmethod
def toast_dismiss(id: Var | str | None = None): ... def toast_dismiss(id: Var | str | None = None): ...
@overload @overload
@ -176,7 +176,7 @@ class ToastNamespace(ComponentNamespace):
@staticmethod @staticmethod
def __call__( def __call__(
message: str = "", level: Optional[str] = None, **props message: Union[str, Var] = "", level: Optional[str] = None, **props
) -> "Optional[EventSpec]": ) -> "Optional[EventSpec]":
"""Send a toast message. """Send a toast message.

View File

@ -576,6 +576,10 @@ def _isinstance(obj: Any, cls: GenericType, nested: bool = False) -> bool:
return does_obj_satisfy_typed_dict(obj, cls) return does_obj_satisfy_typed_dict(obj, cls)
return isinstance(obj, dict) return isinstance(obj, dict)
# cls is a float
if cls is float:
return isinstance(obj, (float, int))
# cls is a simple class # cls is a simple class
return isinstance(obj, cls) return isinstance(obj, cls)