Pārlūkot izejas kodu

rx.call_script: a real EventHandler to execute arbitrary javascript (#1860)

Masen Furer 1 gadu atpakaļ
vecāks
revīzija
991c7202a7

+ 9 - 0
reflex/.templates/web/utils/state.js

@@ -182,6 +182,15 @@ export const applyEvent = async (event, socket) => {
     return false;
     return false;
   }
   }
 
 
+  if (event.name == "_call_script") {
+    try {
+      eval(event.payload.javascript_code);
+    } catch(e) {
+      console.log("_call_script", e);
+    }
+    return false;
+  }
+
   // Update token and router data (if missing).
   // Update token and router data (if missing).
   event.token = getToken()
   event.token = getToken()
   if (event.router_data === undefined || Object.keys(event.router_data).length === 0) {
   if (event.router_data === undefined || Object.keys(event.router_data).length === 0) {

+ 1 - 0
reflex/__init__.py

@@ -22,6 +22,7 @@ from .event import EVENT_ARG as EVENT_ARG
 from .event import EventChain as EventChain
 from .event import EventChain as EventChain
 from .event import FileUpload as upload_files
 from .event import FileUpload as upload_files
 from .event import background as background
 from .event import background as background
+from .event import call_script as call_script
 from .event import clear_local_storage as clear_local_storage
 from .event import clear_local_storage as clear_local_storage
 from .event import console_log as console_log
 from .event import console_log as console_log
 from .event import download as download
 from .event import download as download

+ 7 - 0
reflex/components/base/script.py

@@ -8,6 +8,7 @@ from typing import Any, Union
 
 
 from reflex.components.component import Component
 from reflex.components.component import Component
 from reflex.event import EventChain
 from reflex.event import EventChain
+from reflex.utils import console
 from reflex.vars import BaseVar, Var
 from reflex.vars import BaseVar, Var
 
 
 
 
@@ -87,4 +88,10 @@ def client_side(javascript_code) -> Var[EventChain]:
         An EventChain, passable to any component, that will execute the client side javascript
         An EventChain, passable to any component, that will execute the client side javascript
         when triggered.
         when triggered.
     """
     """
+    console.deprecate(
+        feature_name="rx.client_side",
+        reason="Replaced by rx.call_script, which can be used from backend EventHandler too",
+        deprecation_version="0.2.9",
+        removal_version="0.2.10",
+    )
     return BaseVar(name=f"...args => {{{javascript_code}}}", type_=EventChain)
     return BaseVar(name=f"...args => {{{javascript_code}}}", type_=EventChain)

+ 16 - 0
reflex/event.py

@@ -443,6 +443,22 @@ def download(url: str, filename: Optional[str] = None) -> EventSpec:
     )
     )
 
 
 
 
+def call_script(javascript_code: str) -> EventSpec:
+    """Create an event handler that executes arbitrary javascript code.
+
+    Args:
+        javascript_code: The code to execute.
+
+    Returns:
+        EventSpec: An event that will execute the client side javascript.
+    """
+    return server_side(
+        "_call_script",
+        get_fn_signature(call_script),
+        javascript_code=javascript_code,
+    )
+
+
 def get_event(state, event):
 def get_event(state, event):
     """Get the event from the given state.
     """Get the event from the given state.