3333logger = logging .getLogger (__name__ )
3434
3535
36- def proxy (original_function : Callable [..., Any ] = None , * , timeout : float = 60 ):
36+ def proxy (_func : Callable [..., Any ] | None = None , * , timeout : float = 60 ):
3737 """
3838 Can be used as a decorator to any service method, that should act as a remote call, if the server provided
3939 is not on the same node.
@@ -44,54 +44,60 @@ async def my_fancy_method(self, server: Server, *args, **kwargs) -> Any:
4444
4545 This will call my_fancy_method on the remote node, if the server is remote, and on the local node, if it is not.
4646 """
47-
48- @wraps (original_function )
49- async def wrapper (self , * args , ** kwargs ):
50- signature = inspect .signature (original_function )
51- bound_args = signature .bind (self , * args , ** kwargs )
52- bound_args .apply_defaults ()
53- arg_dict = {k : v for k , v in bound_args .arguments .items () if k != "self" }
54-
55- # Dereference DataObject and Enum values in parameters
56- params = {
57- k : v .name if isinstance (v , DataObject )
58- else v .value if isinstance (v , Enum )
59- else v
60- for k , v in arg_dict .items ()
61- if v is not None # Ignore None values
62- }
63-
64- call = {
65- "command" : "rpc" ,
66- "service" : self .__class__ .__name__ ,
67- "method" : original_function .__name__ ,
68- "params" : params
69- }
70-
71- # Try to pick the node from the functions arguments
72- node = None
73- if arg_dict .get ("server" ):
74- node = arg_dict ["server" ].node
75- elif arg_dict .get ("instance" ):
76- node = arg_dict ["instance" ].node
77- elif arg_dict .get ("node" ):
78- node = arg_dict ["node" ]
79-
80- # Log an error if no valid object is found
81- if node is None :
82- raise ValueError (
83- f"Cannot proxy function { original_function .__name__ } : no valid reference object found in arguments. "
84- f"Expected 'server', 'instance', or 'node' parameter with valid node reference." )
85-
86- # If the node is remote, send the call synchronously
87- if node .is_remote :
88- data = await self .bus .send_to_node_sync (call , node = node .name , timeout = timeout )
89- return data .get ('return' )
90-
91- # Otherwise, call the original function directly
92- return await original_function (self , * args , ** kwargs )
93-
94- return wrapper
47+ def decorator (original_function : Callable [..., Any ]):
48+ @wraps (original_function )
49+ async def wrapper (self , * args , ** kwargs ):
50+ signature = inspect .signature (original_function )
51+ bound_args = signature .bind (self , * args , ** kwargs )
52+ bound_args .apply_defaults ()
53+ arg_dict = {k : v for k , v in bound_args .arguments .items () if k != "self" }
54+
55+ # Dereference DataObject and Enum values in parameters
56+ params = {
57+ k : v .name if isinstance (v , DataObject )
58+ else v .value if isinstance (v , Enum )
59+ else v
60+ for k , v in arg_dict .items ()
61+ if v is not None # Ignore None values
62+ }
63+
64+ call = {
65+ "command" : "rpc" ,
66+ "service" : self .__class__ .__name__ ,
67+ "method" : original_function .__name__ ,
68+ "params" : params
69+ }
70+
71+ # Try to pick the node from the functions arguments
72+ node = None
73+ if arg_dict .get ("server" ):
74+ node = arg_dict ["server" ].node
75+ elif arg_dict .get ("instance" ):
76+ node = arg_dict ["instance" ].node
77+ elif arg_dict .get ("node" ):
78+ node = arg_dict ["node" ]
79+
80+ # Log an error if no valid object is found
81+ if node is None :
82+ raise ValueError (
83+ f"Cannot proxy function { original_function .__name__ } : no valid reference object found in arguments. "
84+ f"Expected 'server', 'instance', or 'node' parameter with valid node reference." )
85+
86+ # If the node is remote, send the call synchronously
87+ if node .is_remote :
88+ data = await self .bus .send_to_node_sync (call , node = node .name , timeout = timeout )
89+ return data .get ('return' )
90+
91+ # Otherwise, call the original function directly
92+ return await original_function (self , * args , ** kwargs )
93+ return wrapper
94+
95+ # If used as @proxy(timeout=nn)
96+ if _func is None :
97+ return decorator
98+
99+ # If used as @proxy without parentheses
100+ return decorator (_func )
95101
96102
97103class Service (ABC ):
0 commit comments