@@ -115,10 +115,10 @@ def _check_valid_scan(self, request: messages.ScanQueueMessage) -> None:
115115 if scan_type not in avail_scans .resource :
116116 raise ScanRejection (f"Unknown scan type { scan_type } ." )
117117
118- if scan_type == "device_rpc" :
118+ if scan_type in [ "device_rpc" , "_v4_device_rpc" ] :
119119 # ensure that the requested rpc is allowed for this particular device
120- params = request . content . get ( "parameter" )
121- if not self ._device_rpc_is_valid (device = params . get ( " device" ) , func = params . get ( " func" ) ):
120+ device , func = self . _extract_device_rpc_target ( request )
121+ if not self ._device_rpc_is_valid (device = device , func = func ):
122122 raise ScanRejection (f"Rejected rpc: { request .content } " )
123123
124124 def _device_rpc_is_valid (self , device : str , func : str ) -> bool :
@@ -142,10 +142,12 @@ def _check_motors_movable(self, request: messages.ScanQueueMessage) -> None:
142142 """
143143 parameter = request .parameter
144144 if request .scan_type in ["device_rpc" , "_v4_device_rpc" ]:
145- device = parameter . get ( "device" )
145+ device , _ = self . _extract_device_rpc_target ( request )
146146 if not isinstance (device , list ):
147147 device = [device ]
148148 for dev in device :
149+ if dev not in self .device_manager .devices :
150+ raise ScanRejection (f"Device { dev } is not known." )
149151 if not self .device_manager .devices [dev ].enabled :
150152 raise ScanRejection (f"Device { dev } is not enabled." )
151153 return
@@ -212,14 +214,24 @@ def _handle_scan_request(self, msg: messages.ScanQueueMessage, username: str):
212214 logger .info (f"Request was rejected: { scan_status .message } " )
213215 return
214216
215- if msg .scan_type == "device_rpc" :
216- func = msg . content . get ( "parameter" , {}). get ( "func" , "" )
217+ if msg .scan_type in [ "device_rpc" , "_v4_device_rpc" ] :
218+ _ , func = self . _extract_device_rpc_target ( msg )
217219 if func in ["get" , "read" ] or func .endswith (".get" ) or func .endswith (".read" ):
218220 logger .info ("Scan request is a read operation, not enqueuing." )
219221 self ._direct_device_rpc (msg )
220222 return
221223 self ._append_to_scan_queue (msg )
222224
225+ @staticmethod
226+ def _extract_device_rpc_target (
227+ msg : messages .ScanQueueMessage ,
228+ ) -> tuple [str | list [str ] | None , str ]:
229+ params = msg .content .get ("parameter" , {})
230+ if msg .scan_type == "_v4_device_rpc" :
231+ rpc_kwargs = params .get ("kwargs" , {})
232+ return rpc_kwargs .get ("device" ), rpc_kwargs .get ("func" , "" )
233+ return params .get ("device" ), params .get ("func" , "" )
234+
223235 def _direct_device_rpc (self , msg : messages .ScanQueueMessage ):
224236 """
225237 Directly send a device RPC request without enqueuing.
0 commit comments