bec-ipython-client 3.161.0__tar.gz → 3.162.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/PKG-INFO +1 -1
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/ipython_live_updates.py +29 -89
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/live_table.py +0 -9
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/demo.py +0 -32
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/pyproject.toml +1 -1
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_ipython_live_updates.py +11 -11
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_acl_e2e.py +7 -4
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_scans_e2e.py +52 -102
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_scans_lib_e2e.py +6 -36
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_scans_v4_lib_e2e.py +5 -14
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/.gitignore +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/__init__.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/beamline_mixin.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/bec_magics.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/bec_startup.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/__init__.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/device_progress.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/move_device.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/utils.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/high_level_interfaces/__init__.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/high_level_interfaces/bec_hli.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/high_level_interfaces/spec_hli.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/main.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/SLS/__init__.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/SLS/sls_info.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/XTreme/__init__.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/XTreme/x-treme.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/__init__.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/flomni/flomni_config.yaml +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/prettytable.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/progressbar.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/signals.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/conftest.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_beamline_mixins.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_bec_client.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_device_progress.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_live_table.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_move_callback.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_pretty_table.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_signals.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/conftest.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/_ensure_requirements_container.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_actors_e2e.py +0 -0
- {bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_procedures_e2e.py +0 -0
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
|
-
import collections
|
|
4
3
|
import time
|
|
5
4
|
from contextvars import Token
|
|
6
5
|
from typing import TYPE_CHECKING, Any
|
|
@@ -41,12 +40,9 @@ class IPythonLiveUpdates:
|
|
|
41
40
|
"""
|
|
42
41
|
self.client = client
|
|
43
42
|
self._interrupted_request = None
|
|
44
|
-
self._active_callback = None
|
|
45
43
|
self._processed_instructions = 0
|
|
46
44
|
self._active_request: messages.ScanQueueMessage | None = None
|
|
47
45
|
self._user_callback = None
|
|
48
|
-
self._request_block_index = collections.defaultdict(lambda: 0)
|
|
49
|
-
self._request_block_id = None
|
|
50
46
|
self._current_queue = None
|
|
51
47
|
self._status_live: Live | None = None
|
|
52
48
|
|
|
@@ -68,9 +64,6 @@ class IPythonLiveUpdates:
|
|
|
68
64
|
"""
|
|
69
65
|
if not self._active_request:
|
|
70
66
|
return
|
|
71
|
-
scan_type = self._active_request.scan_type
|
|
72
|
-
if scan_type == "close_scan_group":
|
|
73
|
-
return
|
|
74
67
|
|
|
75
68
|
if not report_instructions:
|
|
76
69
|
return
|
|
@@ -90,62 +83,33 @@ class IPythonLiveUpdates:
|
|
|
90
83
|
instr (dict): The instruction to process.
|
|
91
84
|
"""
|
|
92
85
|
scan_report_type = list(instr.keys())[0]
|
|
93
|
-
scan_def_id = self.client.scans._scan_def_id
|
|
94
|
-
interactive_scan = self.client.scans._interactive_scan
|
|
95
86
|
if self._active_request is None:
|
|
96
87
|
# Already checked in caller method. It is just for type checking purposes.
|
|
97
88
|
return
|
|
98
|
-
if
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
LiveUpdatesTable(
|
|
108
|
-
self.client,
|
|
109
|
-
report_instruction=instr,
|
|
110
|
-
request=self._active_request,
|
|
111
|
-
callbacks=self._user_callback,
|
|
112
|
-
print_table_data=self.print_table_data,
|
|
113
|
-
).run()
|
|
114
|
-
elif scan_report_type == "device_progress":
|
|
115
|
-
LiveUpdatesDeviceProgress(
|
|
116
|
-
self.client,
|
|
117
|
-
report_instruction=instr,
|
|
118
|
-
request=self._active_request,
|
|
119
|
-
callbacks=self._user_callback,
|
|
120
|
-
).run()
|
|
121
|
-
else:
|
|
122
|
-
raise ValueError(f"Unknown scan report type: {scan_report_type}")
|
|
123
|
-
else:
|
|
124
|
-
if self._active_callback:
|
|
125
|
-
if scan_report_type == "readback":
|
|
126
|
-
LiveUpdatesReadbackProgressbar(
|
|
127
|
-
self.client,
|
|
128
|
-
report_instruction=instr,
|
|
129
|
-
request=self._active_request,
|
|
130
|
-
callbacks=self._user_callback,
|
|
131
|
-
).run()
|
|
132
|
-
else:
|
|
133
|
-
self._active_callback.resume(
|
|
134
|
-
request=self._active_request,
|
|
135
|
-
report_instruction=instr,
|
|
136
|
-
callbacks=self._user_callback,
|
|
137
|
-
)
|
|
138
|
-
|
|
139
|
-
return
|
|
140
|
-
|
|
141
|
-
self._active_callback = LiveUpdatesTable(
|
|
89
|
+
if scan_report_type == "readback":
|
|
90
|
+
LiveUpdatesReadbackProgressbar(
|
|
91
|
+
self.client,
|
|
92
|
+
report_instruction=instr,
|
|
93
|
+
request=self._active_request,
|
|
94
|
+
callbacks=self._user_callback,
|
|
95
|
+
).run()
|
|
96
|
+
elif scan_report_type == "scan_progress":
|
|
97
|
+
LiveUpdatesTable(
|
|
142
98
|
self.client,
|
|
143
99
|
report_instruction=instr,
|
|
144
100
|
request=self._active_request,
|
|
145
101
|
callbacks=self._user_callback,
|
|
146
102
|
print_table_data=self.print_table_data,
|
|
147
|
-
)
|
|
148
|
-
|
|
103
|
+
).run()
|
|
104
|
+
elif scan_report_type == "device_progress":
|
|
105
|
+
LiveUpdatesDeviceProgress(
|
|
106
|
+
self.client,
|
|
107
|
+
report_instruction=instr,
|
|
108
|
+
request=self._active_request,
|
|
109
|
+
callbacks=self._user_callback,
|
|
110
|
+
).run()
|
|
111
|
+
else:
|
|
112
|
+
raise ValueError(f"Unknown scan report type: {scan_report_type}")
|
|
149
113
|
|
|
150
114
|
def _available_req_blocks(
|
|
151
115
|
self, queue: QueueItem, request: messages.ScanQueueMessage
|
|
@@ -190,15 +154,14 @@ class IPythonLiveUpdates:
|
|
|
190
154
|
|
|
191
155
|
self._current_queue = queue = scan_request.scan_queue_request.queue
|
|
192
156
|
request_context.queue_status = queue.status
|
|
193
|
-
self._request_block_id = req_id = self._active_request.metadata.get("RID")
|
|
194
157
|
|
|
195
158
|
while queue.status not in ["COMPLETED", "ABORTED", "HALTED", "CANCELLED"]:
|
|
196
159
|
request_context.queue_status = queue.status
|
|
197
|
-
if self._process_queue(queue, request
|
|
160
|
+
if self._process_queue(queue, request):
|
|
198
161
|
break
|
|
199
162
|
|
|
200
163
|
available_blocks = self._available_req_blocks(queue, request)
|
|
201
|
-
req_block = available_blocks[
|
|
164
|
+
req_block = available_blocks[0]
|
|
202
165
|
report_instructions = req_block.report_instructions or []
|
|
203
166
|
self._process_report_instructions(report_instructions)
|
|
204
167
|
|
|
@@ -218,15 +181,15 @@ class IPythonLiveUpdates:
|
|
|
218
181
|
self._interrupted_request = (request,)
|
|
219
182
|
if self._current_queue and self.client._service_config.abort_on_ctrl_c:
|
|
220
183
|
self._wait_for_cleanup()
|
|
221
|
-
self._reset(
|
|
184
|
+
self._reset()
|
|
222
185
|
raise scan_interr
|
|
223
186
|
except KeyboardInterrupt as exc:
|
|
224
187
|
self._stop_status_live()
|
|
225
188
|
if self.client._service_config.abort_on_ctrl_c and self._abort_pending_request():
|
|
226
189
|
self._wait_for_cleanup()
|
|
227
|
-
self._reset(
|
|
190
|
+
self._reset()
|
|
228
191
|
raise ScanInterruption("User abort.") from exc
|
|
229
|
-
self._reset(
|
|
192
|
+
self._reset()
|
|
230
193
|
raise
|
|
231
194
|
finally:
|
|
232
195
|
if context_token is not None:
|
|
@@ -285,16 +248,13 @@ class IPythonLiveUpdates:
|
|
|
285
248
|
return False
|
|
286
249
|
return any(queue_item.queue_id == self._current_queue.queue_id for queue_item in queue_info)
|
|
287
250
|
|
|
288
|
-
def _process_queue(
|
|
289
|
-
self, queue: QueueItem, request: messages.ScanQueueMessage, req_id: str
|
|
290
|
-
) -> bool:
|
|
251
|
+
def _process_queue(self, queue: QueueItem, request: messages.ScanQueueMessage) -> bool:
|
|
291
252
|
"""
|
|
292
253
|
Process the queue and return True if the scan is completed.
|
|
293
254
|
|
|
294
255
|
Args:
|
|
295
256
|
queue(QueueItem): The queue item to process.
|
|
296
257
|
request(messages.ScanQueueMessage): The request message.
|
|
297
|
-
req_id(str): The request ID.
|
|
298
258
|
|
|
299
259
|
Returns:
|
|
300
260
|
bool: True if the scan is completed.
|
|
@@ -321,10 +281,9 @@ class IPythonLiveUpdates:
|
|
|
321
281
|
available_blocks = self._available_req_blocks(queue, request)
|
|
322
282
|
if not available_blocks:
|
|
323
283
|
return False
|
|
324
|
-
req_block = available_blocks[
|
|
284
|
+
req_block = available_blocks[0]
|
|
325
285
|
if req_block.msg.scan_type in [
|
|
326
|
-
"mv"
|
|
327
|
-
"_v4_mv",
|
|
286
|
+
"mv"
|
|
328
287
|
]: # TODO: make this more general for all scan types that don't have report instructions
|
|
329
288
|
return True
|
|
330
289
|
|
|
@@ -333,13 +292,6 @@ class IPythonLiveUpdates:
|
|
|
333
292
|
return False
|
|
334
293
|
self._process_report_instructions(report_instructions)
|
|
335
294
|
|
|
336
|
-
complete_rbl = len(available_blocks) == self._request_block_index[req_id] + 1
|
|
337
|
-
if self._active_callback and complete_rbl:
|
|
338
|
-
return True
|
|
339
|
-
|
|
340
|
-
if complete_rbl and self.client.scans._interactive_scan:
|
|
341
|
-
return True
|
|
342
|
-
|
|
343
295
|
if not queue.active_request_block:
|
|
344
296
|
return True
|
|
345
297
|
|
|
@@ -395,28 +347,16 @@ class IPythonLiveUpdates:
|
|
|
395
347
|
self._status_live.update(Panel(message, title="[yellow]Scan Status[/yellow]"))
|
|
396
348
|
return
|
|
397
349
|
|
|
398
|
-
def _reset(self
|
|
399
|
-
"""Reset the active request
|
|
400
|
-
|
|
401
|
-
Args:
|
|
402
|
-
forced(bool): If True, the reset is forced.
|
|
403
|
-
"""
|
|
350
|
+
def _reset(self):
|
|
351
|
+
"""Reset the active request."""
|
|
404
352
|
self._stop_status_live()
|
|
405
353
|
self._interrupted_request = None
|
|
406
354
|
|
|
407
355
|
self._current_queue = None
|
|
408
356
|
self._user_callback = None
|
|
409
357
|
self._processed_instructions = 0
|
|
410
|
-
scan_closed = forced or self._active_request is None
|
|
411
358
|
self._active_request = None
|
|
412
359
|
|
|
413
|
-
if self.client.scans._scan_def_id and not scan_closed:
|
|
414
|
-
self._request_block_index[self._request_block_id] += 1
|
|
415
|
-
return
|
|
416
|
-
|
|
417
|
-
if scan_closed:
|
|
418
|
-
self._active_callback = None
|
|
419
|
-
|
|
420
360
|
def continue_request(self):
|
|
421
361
|
"""Continue the interrupted request."""
|
|
422
362
|
if not self._interrupted_request:
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/live_table.py
RENAMED
|
@@ -97,8 +97,6 @@ class LiveUpdatesTable(LiveUpdatesBase):
|
|
|
97
97
|
"""wait for scan completion"""
|
|
98
98
|
while True:
|
|
99
99
|
if self.scan_item.end_time:
|
|
100
|
-
if self.scan_item.open_queue_group:
|
|
101
|
-
break
|
|
102
100
|
if self.scan_item.queue.queue_position is None:
|
|
103
101
|
break
|
|
104
102
|
self.check_alarms()
|
|
@@ -110,13 +108,6 @@ class LiveUpdatesTable(LiveUpdatesBase):
|
|
|
110
108
|
"""check for alarms"""
|
|
111
109
|
check_alarms(self.bec)
|
|
112
110
|
|
|
113
|
-
def resume(self, request: messages.ScanQueueMessage, report_instruction: str, callbacks):
|
|
114
|
-
"""resume the scan after a pause"""
|
|
115
|
-
super().__init__(
|
|
116
|
-
self.bec, request=request, report_instruction=report_instruction, callbacks=callbacks
|
|
117
|
-
)
|
|
118
|
-
self.process_request()
|
|
119
|
-
|
|
120
111
|
@property
|
|
121
112
|
def devices(self):
|
|
122
113
|
"""get the devices for the callback"""
|
|
@@ -145,13 +145,6 @@ scans.umv(dev.samx, 5, dev.samy, 20, relative=False)
|
|
|
145
145
|
# s = scans.line_scan(dev.samy, -5, 40, steps=10, exp_time=0.1)
|
|
146
146
|
# s = scans.round_roi_scan(dev.samx, 50, dev.samy, 20, dr=2, nth=3, exp_time=0.1)
|
|
147
147
|
|
|
148
|
-
# scan_def_id = str(uuid.uuid4())
|
|
149
|
-
# scans.open_interactive_scan(dev.samx, dev.samy, exp_time=0.1, md={"scan_def_id": scan_def_id})
|
|
150
|
-
# for ii in range(5):
|
|
151
|
-
# scans.mv(dev.samx, ii, dev.samy, ii + 3, md={"scan_def_id": scan_def_id})
|
|
152
|
-
# scans.interactive_scan_trigger(dev.samx, dev.samy, md={"scan_def_id": scan_def_id})
|
|
153
|
-
# scans.close_interactive_scan(md={"scan_def_id": scan_def_id})
|
|
154
|
-
|
|
155
148
|
|
|
156
149
|
# for ii in range(10):
|
|
157
150
|
# scans.umv(dev.samx, ii * 10)
|
|
@@ -164,15 +157,6 @@ scans.umv(dev.samx, 5, dev.samy, 20, relative=False)
|
|
|
164
157
|
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02)
|
|
165
158
|
|
|
166
159
|
|
|
167
|
-
# @scans.scan_group
|
|
168
|
-
# def scan_with_decorator():
|
|
169
|
-
# scans.umv(dev.samx, 5, relative=False)
|
|
170
|
-
# scans.line_scan(dev.samx, -5, 5, steps=100, exp_time=0.1, relative=True)
|
|
171
|
-
# scans.umv(dev.samx, 5, relative=False)
|
|
172
|
-
# scans.line_scan(dev.samx, -5, 5, steps=100, exp_time=0.1, relative=True)
|
|
173
|
-
# # scans.line_scan(dev.samx, -8, 8, steps=200, exp_time=0.1, relative=True)
|
|
174
|
-
|
|
175
|
-
|
|
176
160
|
# with scans.dataset_id_on_hold:
|
|
177
161
|
# scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.1, relative=True)
|
|
178
162
|
# scans.line_scan(dev.samx, -8, 8, steps=10, exp_time=0.1, relative=True)
|
|
@@ -187,22 +171,6 @@ scans.umv(dev.samx, 5, dev.samy, 20, relative=False)
|
|
|
187
171
|
# scans.umv(dev.samx, 1000)
|
|
188
172
|
|
|
189
173
|
|
|
190
|
-
# @scans.scan_group
|
|
191
|
-
# def alignment(*args, **kwargs):
|
|
192
|
-
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02)
|
|
193
|
-
# scans.umv(dev.samx, 10)
|
|
194
|
-
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02)
|
|
195
|
-
# scans.umv(dev.samx, 10)
|
|
196
|
-
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02)
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
# with scans.scan_group:
|
|
200
|
-
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02, relative=True)
|
|
201
|
-
# scans.umv(dev.samx, 10, relative=True)
|
|
202
|
-
|
|
203
|
-
# alignment()
|
|
204
|
-
|
|
205
|
-
|
|
206
174
|
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02, md={"queue_group": queue_group})
|
|
207
175
|
# scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.02, md={"queue_group": queue_group})
|
|
208
176
|
|
|
@@ -107,7 +107,7 @@ def test_live_updates_process_queue_pending(ipython_live_updates_with_mocked_liv
|
|
|
107
107
|
live_updates, "_available_req_blocks", return_value=[request_block]
|
|
108
108
|
):
|
|
109
109
|
with mock.patch.object(live_updates, "_process_report_instructions") as process:
|
|
110
|
-
res = live_updates._process_queue(queue, request_msg
|
|
110
|
+
res = live_updates._process_queue(queue, request_msg)
|
|
111
111
|
# Verify Live panel was created for showing queue status
|
|
112
112
|
mock_live.assert_called_once()
|
|
113
113
|
mock_live.return_value.start.assert_called_once()
|
|
@@ -141,7 +141,7 @@ def test_live_updates_process_queue_running(ipython_live_updates_with_mocked_liv
|
|
|
141
141
|
live_updates, "_available_req_blocks", return_value=[request_block]
|
|
142
142
|
):
|
|
143
143
|
with mock.patch.object(live_updates, "_process_instruction") as process:
|
|
144
|
-
res = live_updates._process_queue(queue, request_msg
|
|
144
|
+
res = live_updates._process_queue(queue, request_msg)
|
|
145
145
|
mock_live.assert_not_called()
|
|
146
146
|
process.assert_called_once_with({"wait_table": 10})
|
|
147
147
|
assert res is True
|
|
@@ -177,7 +177,7 @@ def test_live_updates_process_queue_waiting_for_device_locks(
|
|
|
177
177
|
):
|
|
178
178
|
queue_pos.return_value = 0
|
|
179
179
|
|
|
180
|
-
assert live_updates._process_queue(queue, request_msg
|
|
180
|
+
assert live_updates._process_queue(queue, request_msg) is False
|
|
181
181
|
|
|
182
182
|
process_pending.assert_called_once_with(queue)
|
|
183
183
|
|
|
@@ -214,7 +214,7 @@ def test_live_updates_process_queue_cancelled_pending_request_raises_interruptio
|
|
|
214
214
|
mock.patch("bec_lib.queue_items.QueueItem.queue_position", new_callable=mock.PropertyMock),
|
|
215
215
|
pytest.raises(ScanInterruption, match="Scan was cancelled."),
|
|
216
216
|
):
|
|
217
|
-
live_updates._process_queue(queue, request_msg
|
|
217
|
+
live_updates._process_queue(queue, request_msg)
|
|
218
218
|
|
|
219
219
|
|
|
220
220
|
def test_live_updates_process_queue_stopped_started_request_raises_interruption(bec_client_mock):
|
|
@@ -259,7 +259,7 @@ def test_live_updates_process_queue_stopped_started_request_raises_interruption(
|
|
|
259
259
|
mock.patch("bec_lib.queue_items.QueueItem.queue_position", new_callable=mock.PropertyMock),
|
|
260
260
|
pytest.raises(ScanInterruption, match="Scan 1 was aborted by user."),
|
|
261
261
|
):
|
|
262
|
-
live_updates._process_queue(queue, request_msg
|
|
262
|
+
live_updates._process_queue(queue, request_msg)
|
|
263
263
|
|
|
264
264
|
|
|
265
265
|
def test_live_updates_process_queue_stopped_restart_without_restart_message_waits_nonblocking(
|
|
@@ -300,7 +300,7 @@ def test_live_updates_process_queue_stopped_restart_without_restart_message_wait
|
|
|
300
300
|
return_value=mock.MagicMock(status="aborted", restarted_msg=None),
|
|
301
301
|
),
|
|
302
302
|
):
|
|
303
|
-
assert live_updates._process_queue(queue, request_msg
|
|
303
|
+
assert live_updates._process_queue(queue, request_msg) is False
|
|
304
304
|
|
|
305
305
|
|
|
306
306
|
def test_process_request_repeats_on_ScanRestart_error(
|
|
@@ -485,7 +485,7 @@ def test_process_request_keyboard_interrupt_pending_request_raises_scan_interrup
|
|
|
485
485
|
|
|
486
486
|
abort_pending.assert_called_once()
|
|
487
487
|
wait_for_cleanup.assert_called_once()
|
|
488
|
-
reset.assert_called_once_with(
|
|
488
|
+
reset.assert_called_once_with()
|
|
489
489
|
|
|
490
490
|
|
|
491
491
|
@pytest.mark.parametrize("queue_status", ["RUNNING", "LOCKED"])
|
|
@@ -515,7 +515,7 @@ def test_process_request_keyboard_interrupt_pending_request_aborts_local_request
|
|
|
515
515
|
|
|
516
516
|
request_abort.assert_called_once_with(request_id="something")
|
|
517
517
|
wait_for_cleanup.assert_called_once()
|
|
518
|
-
reset.assert_called_once_with(
|
|
518
|
+
reset.assert_called_once_with()
|
|
519
519
|
|
|
520
520
|
|
|
521
521
|
def test_process_request_keyboard_interrupt_non_pending_re_raises(
|
|
@@ -543,7 +543,7 @@ def test_process_request_keyboard_interrupt_non_pending_re_raises(
|
|
|
543
543
|
|
|
544
544
|
abort_pending.assert_called_once()
|
|
545
545
|
wait_for_cleanup.assert_not_called()
|
|
546
|
-
reset.assert_called_once_with(
|
|
546
|
+
reset.assert_called_once_with()
|
|
547
547
|
|
|
548
548
|
|
|
549
549
|
@pytest.mark.timeout(20)
|
|
@@ -552,7 +552,7 @@ def test_live_updates_process_queue_without_status(bec_client_mock, queue_elemen
|
|
|
552
552
|
live_updates = IPythonLiveUpdates(client)
|
|
553
553
|
queue, _, request_msg = queue_elements
|
|
554
554
|
with mock.patch.object(queue, "_update_with_buffer"):
|
|
555
|
-
assert live_updates._process_queue(queue, request_msg
|
|
555
|
+
assert live_updates._process_queue(queue, request_msg) is False
|
|
556
556
|
|
|
557
557
|
|
|
558
558
|
@pytest.mark.timeout(20)
|
|
@@ -574,7 +574,7 @@ def test_live_updates_process_queue_without_queue_number(bec_client_mock, queue_
|
|
|
574
574
|
)
|
|
575
575
|
queue_pos.return_value = None
|
|
576
576
|
with mock.patch.object(queue, "_update_with_buffer"):
|
|
577
|
-
assert live_updates._process_queue(queue, request_msg
|
|
577
|
+
assert live_updates._process_queue(queue, request_msg) is False
|
|
578
578
|
|
|
579
579
|
|
|
580
580
|
@pytest.mark.timeout(20)
|
|
@@ -12,6 +12,9 @@ from bec_lib.tests.utils import wait_for_empty_queue
|
|
|
12
12
|
from bec_lib.utils.user_acls_test import BECAccessDemo
|
|
13
13
|
from bec_server.bec_server_utils.service_handler import ServiceHandler
|
|
14
14
|
|
|
15
|
+
CLIENT_SHUTDOWN_TIMEOUT_S = 10
|
|
16
|
+
SERVICE_STOP_TIMEOUT_S = 20
|
|
17
|
+
|
|
15
18
|
|
|
16
19
|
@pytest.fixture
|
|
17
20
|
def acl_enabled_bec_services(
|
|
@@ -61,7 +64,7 @@ def acl_enabled_bec_services(
|
|
|
61
64
|
yield bec_services_config_file_path
|
|
62
65
|
finally:
|
|
63
66
|
if processes is not None:
|
|
64
|
-
service_handler.stop(processes)
|
|
67
|
+
service_handler.stop(processes, timeout_s=SERVICE_STOP_TIMEOUT_S)
|
|
65
68
|
restore_connector = RedisConnector(redis_url)
|
|
66
69
|
try:
|
|
67
70
|
BECAccessDemo(restore_connector).reset()
|
|
@@ -77,7 +80,7 @@ def test_acl_admin_server_allows_default_user_scan(acl_enabled_bec_services):
|
|
|
77
80
|
try:
|
|
78
81
|
admin_client.config.load_demo_config(force=True)
|
|
79
82
|
finally:
|
|
80
|
-
admin_client.shutdown()
|
|
83
|
+
admin_client.shutdown(per_thread_timeout_s=CLIENT_SHUTDOWN_TIMEOUT_S)
|
|
81
84
|
admin_client._client._reset_singleton()
|
|
82
85
|
|
|
83
86
|
user_config = ServiceConfig(acl_enabled_bec_services, acl={"env_file": "", "user": "user"})
|
|
@@ -97,7 +100,7 @@ def test_acl_admin_server_allows_default_user_scan(acl_enabled_bec_services):
|
|
|
97
100
|
|
|
98
101
|
assert status.scan.num_points == 3
|
|
99
102
|
finally:
|
|
100
|
-
user_client.shutdown()
|
|
103
|
+
user_client.shutdown(per_thread_timeout_s=CLIENT_SHUTDOWN_TIMEOUT_S)
|
|
101
104
|
user_client._client._reset_singleton()
|
|
102
105
|
|
|
103
106
|
|
|
@@ -136,5 +139,5 @@ def test_acl_account_endpoint_allows_user_read_but_admin_only_write(acl_enabled_
|
|
|
136
139
|
assert user_client.username == "user"
|
|
137
140
|
assert user_client.connector.get_last(account_endpoint, "data") == updated_account_msg
|
|
138
141
|
finally:
|
|
139
|
-
user_client.shutdown()
|
|
142
|
+
user_client.shutdown(per_thread_timeout_s=CLIENT_SHUTDOWN_TIMEOUT_S)
|
|
140
143
|
user_client._client._reset_singleton()
|
|
@@ -31,16 +31,13 @@ if TYPE_CHECKING: # pragma: no cover
|
|
|
31
31
|
|
|
32
32
|
|
|
33
33
|
@pytest.mark.timeout(100)
|
|
34
|
-
|
|
35
|
-
def test_grid_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
34
|
+
def test_grid_scan(capsys, bec_ipython_client_fixture):
|
|
36
35
|
bec = bec_ipython_client_fixture
|
|
37
36
|
scans = bec.scans
|
|
38
37
|
bec.metadata.update({"unit_test": "test_grid_scan"})
|
|
39
38
|
dev = bec.device_manager.devices
|
|
40
39
|
scans.umv(dev.samx, 0, dev.samy, 0, relative=False)
|
|
41
|
-
status =
|
|
42
|
-
dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True
|
|
43
|
-
)
|
|
40
|
+
status = scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True)
|
|
44
41
|
assert len(status.scan.live_data) == 100
|
|
45
42
|
assert status.scan.num_points == 100
|
|
46
43
|
captured = capsys.readouterr()
|
|
@@ -48,13 +45,12 @@ def test_grid_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
48
45
|
|
|
49
46
|
|
|
50
47
|
@pytest.mark.timeout(100)
|
|
51
|
-
|
|
52
|
-
def test_fermat_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
48
|
+
def test_fermat_scan(capsys, bec_ipython_client_fixture):
|
|
53
49
|
bec = bec_ipython_client_fixture
|
|
54
50
|
scans = bec.scans
|
|
55
51
|
bec.metadata.update({"unit_test": "test_fermat_scan"})
|
|
56
52
|
dev = bec.device_manager.devices
|
|
57
|
-
status =
|
|
53
|
+
status = scans.fermat_scan(
|
|
58
54
|
dev.samx,
|
|
59
55
|
-5,
|
|
60
56
|
5,
|
|
@@ -66,25 +62,19 @@ def test_fermat_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
66
62
|
relative=True,
|
|
67
63
|
optim_trajectory="corridor",
|
|
68
64
|
)
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
assert len(status.scan.live_data) == 400
|
|
72
|
-
assert status.scan.num_points == 400
|
|
73
|
-
else:
|
|
74
|
-
assert len(status.scan.live_data) == 393
|
|
75
|
-
assert status.scan.num_points == 393
|
|
65
|
+
assert len(status.scan.live_data) == 400
|
|
66
|
+
assert status.scan.num_points == 400
|
|
76
67
|
captured = capsys.readouterr()
|
|
77
68
|
assert "finished. Scan ID" in captured.out
|
|
78
69
|
|
|
79
70
|
|
|
80
71
|
@pytest.mark.timeout(100)
|
|
81
|
-
|
|
82
|
-
def test_line_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
72
|
+
def test_line_scan(capsys, bec_ipython_client_fixture):
|
|
83
73
|
bec = bec_ipython_client_fixture
|
|
84
74
|
scans = bec.scans
|
|
85
75
|
bec.metadata.update({"unit_test": "test_line_scan"})
|
|
86
76
|
dev = bec.device_manager.devices
|
|
87
|
-
status =
|
|
77
|
+
status = scans.line_scan(
|
|
88
78
|
dev.samx, -5, 5, dev.samy, -5, 5, steps=10, exp_time=0.01, relative=True
|
|
89
79
|
)
|
|
90
80
|
assert len(status.scan.live_data) == 10
|
|
@@ -95,13 +85,12 @@ def test_line_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
95
85
|
|
|
96
86
|
@pytest.mark.flaky # marked as flaky as the simulation might return a new readback value within the tolerance
|
|
97
87
|
@pytest.mark.timeout(100)
|
|
98
|
-
|
|
99
|
-
def test_mv_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
88
|
+
def test_mv_scan(capsys, bec_ipython_client_fixture):
|
|
100
89
|
bec = bec_ipython_client_fixture
|
|
101
90
|
scans = bec.scans
|
|
102
91
|
bec.metadata.update({"unit_test": "test_mv_scan"})
|
|
103
92
|
dev = bec.device_manager.devices
|
|
104
|
-
|
|
93
|
+
scans.mv(dev.samx, 10, dev.samy, 20, relative=False).wait()
|
|
105
94
|
current_pos_samx = dev.samx.read(cached=True)["samx"]["value"]
|
|
106
95
|
current_pos_samy = dev.samy.read(cached=True)["samy"]["value"]
|
|
107
96
|
assert np.isclose(
|
|
@@ -110,7 +99,7 @@ def test_mv_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
110
99
|
assert np.isclose(
|
|
111
100
|
current_pos_samy, 20, atol=dev.samy._config["deviceConfig"].get("tolerance", 0.05)
|
|
112
101
|
)
|
|
113
|
-
|
|
102
|
+
scans.umv(dev.samx, 10, dev.samy, 20, relative=False)
|
|
114
103
|
current_pos_samx = dev.samx.read(cached=True)["samx"]["value"]
|
|
115
104
|
current_pos_samy = dev.samy.read(cached=True)["samy"]["value"]
|
|
116
105
|
captured = capsys.readouterr()
|
|
@@ -122,13 +111,12 @@ def test_mv_scan(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
122
111
|
|
|
123
112
|
@pytest.mark.flaky # marked as flaky as the simulation might return a new readback value within the tolerance
|
|
124
113
|
@pytest.mark.timeout(100)
|
|
125
|
-
|
|
126
|
-
def test_mv_scan_nested_device(capsys, bec_ipython_client_fixture, scan_name):
|
|
114
|
+
def test_mv_scan_nested_device(capsys, bec_ipython_client_fixture):
|
|
127
115
|
bec = bec_ipython_client_fixture
|
|
128
116
|
scans = bec.scans
|
|
129
117
|
bec.metadata.update({"unit_test": "test_mv_scan_nested_device"})
|
|
130
118
|
dev = bec.device_manager.devices
|
|
131
|
-
|
|
119
|
+
scans.mv(dev.hexapod.x, 10, dev.hexapod.y, 20, relative=False).wait()
|
|
132
120
|
if not bec.connector._managed_connection._message_callbacks_queue.empty():
|
|
133
121
|
print("Waiting for messages to be processed")
|
|
134
122
|
time.sleep(0.5)
|
|
@@ -140,7 +128,7 @@ def test_mv_scan_nested_device(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
140
128
|
assert np.isclose(
|
|
141
129
|
current_pos_hexapod_y, 20, atol=dev.hexapod._config["deviceConfig"].get("tolerance", 0.5)
|
|
142
130
|
)
|
|
143
|
-
|
|
131
|
+
scans.umv(dev.hexapod.x, 10, dev.hexapod.y, 20, relative=False)
|
|
144
132
|
if not bec.connector._managed_connection._message_callbacks_queue.empty():
|
|
145
133
|
print("Waiting for messages to be processed")
|
|
146
134
|
time.sleep(0.5)
|
|
@@ -159,8 +147,7 @@ def test_mv_scan_nested_device(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
159
147
|
|
|
160
148
|
|
|
161
149
|
@pytest.mark.timeout(100)
|
|
162
|
-
|
|
163
|
-
def test_mv_scan_mv(bec_ipython_client_fixture, scan_name):
|
|
150
|
+
def test_mv_scan_mv(bec_ipython_client_fixture):
|
|
164
151
|
bec = bec_ipython_client_fixture
|
|
165
152
|
scans = bec.scans
|
|
166
153
|
bec.metadata.update({"unit_test": "test_mv_scan_mv"})
|
|
@@ -169,7 +156,7 @@ def test_mv_scan_mv(bec_ipython_client_fixture, scan_name):
|
|
|
169
156
|
|
|
170
157
|
dev.samx.limits = [-50, 50]
|
|
171
158
|
dev.samy.limits = [-50, 50]
|
|
172
|
-
|
|
159
|
+
scans.umv(dev.samx, 10, dev.samy, 20, relative=False)
|
|
173
160
|
tolerance_samx = dev.samx._config["deviceConfig"].get("tolerance", 0.05)
|
|
174
161
|
tolerance_samy = dev.samy._config["deviceConfig"].get("tolerance", 0.05)
|
|
175
162
|
current_pos_samx = dev.samx.read()["samx"]["value"]
|
|
@@ -179,9 +166,7 @@ def test_mv_scan_mv(bec_ipython_client_fixture, scan_name):
|
|
|
179
166
|
assert np.isclose(current_pos_samx, 10, atol=tolerance_samx)
|
|
180
167
|
assert np.isclose(current_pos_samy, 20, atol=tolerance_samy)
|
|
181
168
|
|
|
182
|
-
status =
|
|
183
|
-
dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True
|
|
184
|
-
)
|
|
169
|
+
status = scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True)
|
|
185
170
|
|
|
186
171
|
# make sure the scan completed the expected number of positions
|
|
187
172
|
assert len(status.scan.live_data) == 100
|
|
@@ -201,7 +186,7 @@ def test_mv_scan_mv(bec_ipython_client_fixture, scan_name):
|
|
|
201
186
|
assert np.isclose(current_pos_samx, 10, atol=tolerance_samx * 2)
|
|
202
187
|
assert np.isclose(current_pos_samy, 20, atol=tolerance_samy * 2)
|
|
203
188
|
|
|
204
|
-
|
|
189
|
+
scans.umv(dev.samx, 20, dev.samy, -20, relative=False)
|
|
205
190
|
current_pos_samx = dev.samx.read()["samx"]["value"]
|
|
206
191
|
current_pos_samy = dev.samy.read()["samy"]["value"]
|
|
207
192
|
|
|
@@ -209,7 +194,7 @@ def test_mv_scan_mv(bec_ipython_client_fixture, scan_name):
|
|
|
209
194
|
assert np.isclose(current_pos_samx, 20, atol=tolerance_samx)
|
|
210
195
|
assert np.isclose(current_pos_samy, -20, atol=tolerance_samy)
|
|
211
196
|
|
|
212
|
-
status =
|
|
197
|
+
status = scans.grid_scan(
|
|
213
198
|
dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=False
|
|
214
199
|
)
|
|
215
200
|
|
|
@@ -226,8 +211,7 @@ def test_mv_scan_mv(bec_ipython_client_fixture, scan_name):
|
|
|
226
211
|
|
|
227
212
|
|
|
228
213
|
@pytest.mark.timeout(100)
|
|
229
|
-
|
|
230
|
-
def test_scan_abort(bec_ipython_client_fixture: BECIPythonClient, scan_name: str):
|
|
214
|
+
def test_scan_abort(bec_ipython_client_fixture: BECIPythonClient):
|
|
231
215
|
def send_abort(bec):
|
|
232
216
|
while True:
|
|
233
217
|
current_scan_info = bec.queue.scan_storage.current_scan_info
|
|
@@ -256,7 +240,7 @@ def test_scan_abort(bec_ipython_client_fixture: BECIPythonClient, scan_name: str
|
|
|
256
240
|
aborted_scan = False
|
|
257
241
|
try:
|
|
258
242
|
threading.Thread(target=send_abort, args=(bec,), daemon=True).start()
|
|
259
|
-
|
|
243
|
+
scans.line_scan(dev.samx, -5, 5, steps=200, exp_time=0.1, relative=True)
|
|
260
244
|
except ScanInterruption:
|
|
261
245
|
logger.info("Raised ScanInterruption")
|
|
262
246
|
time.sleep(2)
|
|
@@ -273,7 +257,7 @@ def test_scan_abort(bec_ipython_client_fixture: BECIPythonClient, scan_name: str
|
|
|
273
257
|
|
|
274
258
|
assert len(bec.queue.scan_storage.storage[-1].live_data) < 200
|
|
275
259
|
|
|
276
|
-
|
|
260
|
+
scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.1, relative=True)
|
|
277
261
|
scan_number_end = bec.queue.next_scan_number
|
|
278
262
|
assert scan_number_end == scan_number_start + 2
|
|
279
263
|
|
|
@@ -319,8 +303,8 @@ def test_umv_ctrl_c_stops_motion(bec_ipython_client_fixture: BECIPythonClient):
|
|
|
319
303
|
dev.samx.velocity.set(original_velocity).wait()
|
|
320
304
|
|
|
321
305
|
|
|
322
|
-
@pytest.mark.
|
|
323
|
-
def test_limit_error(bec_ipython_client_fixture
|
|
306
|
+
@pytest.mark.timeout(100)
|
|
307
|
+
def test_limit_error(bec_ipython_client_fixture):
|
|
324
308
|
bec = bec_ipython_client_fixture
|
|
325
309
|
bec.metadata.update({"unit_test": "test_limit_error"})
|
|
326
310
|
scan_number_start = bec.queue.next_scan_number
|
|
@@ -329,7 +313,7 @@ def test_limit_error(bec_ipython_client_fixture, scan_name):
|
|
|
329
313
|
aborted_scan = False
|
|
330
314
|
dev.samx.limits = [-50, 50]
|
|
331
315
|
try:
|
|
332
|
-
|
|
316
|
+
scans.line_scan(dev.samx, -520, 5, steps=200, exp_time=0.1, relative=False)
|
|
333
317
|
except AlarmBase as alarm:
|
|
334
318
|
assert alarm.alarm_type == "LimitError"
|
|
335
319
|
aborted_scan = True
|
|
@@ -339,7 +323,7 @@ def test_limit_error(bec_ipython_client_fixture, scan_name):
|
|
|
339
323
|
aborted_scan = False
|
|
340
324
|
dev.samx.limits = [-50, 50]
|
|
341
325
|
try:
|
|
342
|
-
|
|
326
|
+
scans.umv(dev.samx, 500, relative=False)
|
|
343
327
|
except AlarmBase as alarm:
|
|
344
328
|
assert alarm.alarm_type == "LimitError"
|
|
345
329
|
aborted_scan = True
|
|
@@ -350,17 +334,16 @@ def test_limit_error(bec_ipython_client_fixture, scan_name):
|
|
|
350
334
|
|
|
351
335
|
|
|
352
336
|
@pytest.mark.timeout(100)
|
|
353
|
-
|
|
354
|
-
def test_queued_scan(bec_ipython_client_fixture, scan_name):
|
|
337
|
+
def test_queued_scan(bec_ipython_client_fixture):
|
|
355
338
|
bec = bec_ipython_client_fixture
|
|
356
339
|
bec.metadata.update({"unit_test": "test_queued_scan"})
|
|
357
340
|
scan_number_start = bec.queue.next_scan_number
|
|
358
341
|
scans = bec.scans
|
|
359
342
|
dev = bec.device_manager.devices
|
|
360
|
-
scan1 =
|
|
343
|
+
scan1 = scans.line_scan(
|
|
361
344
|
dev.samx, -5, 5, steps=100, exp_time=0.1, hide_report=True, relative=True
|
|
362
345
|
)
|
|
363
|
-
scan2 =
|
|
346
|
+
scan2 = scans.line_scan(
|
|
364
347
|
dev.samx, -5, 5, steps=50, exp_time=0.1, hide_report=True, relative=True
|
|
365
348
|
)
|
|
366
349
|
|
|
@@ -394,8 +377,7 @@ def test_fly_scan(bec_ipython_client_fixture):
|
|
|
394
377
|
|
|
395
378
|
|
|
396
379
|
@pytest.mark.timeout(100)
|
|
397
|
-
|
|
398
|
-
def test_scan_restart(bec_ipython_client_fixture, scan_name):
|
|
380
|
+
def test_scan_restart(bec_ipython_client_fixture):
|
|
399
381
|
bec = bec_ipython_client_fixture
|
|
400
382
|
bec.metadata.update({"unit_test": "test_scan_restart"})
|
|
401
383
|
scans = bec.scans
|
|
@@ -417,12 +399,10 @@ def test_scan_restart(bec_ipython_client_fixture, scan_name):
|
|
|
417
399
|
|
|
418
400
|
# We start two scans to ensure that the scan restart logic works correctly in a queued scenario
|
|
419
401
|
# The first scan is started without printout to allow us to submit the second scan immediately after
|
|
420
|
-
|
|
421
|
-
dev.samx, -5, 5, steps=50, exp_time=0.1, hide_report=True, relative=True
|
|
422
|
-
)
|
|
402
|
+
scans.line_scan(dev.samx, -5, 5, steps=50, exp_time=0.1, hide_report=True, relative=True)
|
|
423
403
|
|
|
424
404
|
# The second scan is using the live table printout. It should properly continue after the restart
|
|
425
|
-
scan2 =
|
|
405
|
+
scan2 = scans.line_scan(dev.samx, -5, 5, steps=50, exp_time=0.1, relative=True)
|
|
426
406
|
|
|
427
407
|
scan2.wait()
|
|
428
408
|
|
|
@@ -435,8 +415,7 @@ def test_scan_restart(bec_ipython_client_fixture, scan_name):
|
|
|
435
415
|
|
|
436
416
|
|
|
437
417
|
@pytest.mark.timeout(100)
|
|
438
|
-
|
|
439
|
-
def test_scan_observer_repeat_queued(bec_ipython_client_fixture: BECIPythonClient, scan_name):
|
|
418
|
+
def test_scan_observer_repeat_queued(bec_ipython_client_fixture: BECIPythonClient):
|
|
440
419
|
bec = bec_ipython_client_fixture
|
|
441
420
|
bec.metadata.update({"unit_test": "test_scan_observer_repeat_queued"})
|
|
442
421
|
scans = bec.scans
|
|
@@ -458,10 +437,10 @@ def test_scan_observer_repeat_queued(bec_ipython_client_fixture: BECIPythonClien
|
|
|
458
437
|
# start repeat thread
|
|
459
438
|
threading.Thread(target=send_repeat, args=(bec,), daemon=True).start()
|
|
460
439
|
# start scan
|
|
461
|
-
scan1 =
|
|
440
|
+
scan1 = scans.line_scan(
|
|
462
441
|
dev.samx, -5, 5, steps=100, exp_time=0.1, hide_report=True, relative=True
|
|
463
442
|
)
|
|
464
|
-
scan2 =
|
|
443
|
+
scan2 = scans.line_scan(
|
|
465
444
|
dev.samx, -5, 5, steps=100, exp_time=0.1, hide_report=True, relative=True
|
|
466
445
|
)
|
|
467
446
|
|
|
@@ -476,8 +455,7 @@ def test_scan_observer_repeat_queued(bec_ipython_client_fixture: BECIPythonClien
|
|
|
476
455
|
|
|
477
456
|
|
|
478
457
|
@pytest.mark.timeout(100)
|
|
479
|
-
|
|
480
|
-
def test_scan_observer_repeat(bec_ipython_client_fixture, scan_name):
|
|
458
|
+
def test_scan_observer_repeat(bec_ipython_client_fixture):
|
|
481
459
|
bec = bec_ipython_client_fixture
|
|
482
460
|
bec.metadata.update({"unit_test": "test_scan_observer_repeat"})
|
|
483
461
|
scans = bec.scans
|
|
@@ -497,7 +475,7 @@ def test_scan_observer_repeat(bec_ipython_client_fixture, scan_name):
|
|
|
497
475
|
threading.Thread(target=send_repeat, args=(bec,), daemon=True).start()
|
|
498
476
|
# start scan
|
|
499
477
|
with pytest.raises(ScanAbortion):
|
|
500
|
-
scan1 =
|
|
478
|
+
scan1 = scans.line_scan(
|
|
501
479
|
dev.samx, -5, 5, steps=50, exp_time=0.1, hide_report=True, relative=True
|
|
502
480
|
)
|
|
503
481
|
scan1.wait()
|
|
@@ -512,8 +490,7 @@ def test_scan_observer_repeat(bec_ipython_client_fixture, scan_name):
|
|
|
512
490
|
|
|
513
491
|
|
|
514
492
|
@pytest.mark.timeout(100)
|
|
515
|
-
|
|
516
|
-
def test_file_writer(bec_ipython_client_fixture, scan_name):
|
|
493
|
+
def test_file_writer(bec_ipython_client_fixture):
|
|
517
494
|
bec = bec_ipython_client_fixture
|
|
518
495
|
bec.metadata.update({"unit_test": "test_file_writer"})
|
|
519
496
|
scans = bec.scans
|
|
@@ -523,7 +500,7 @@ def test_file_writer(bec_ipython_client_fixture, scan_name):
|
|
|
523
500
|
dev.samx.velocity.set(98).wait()
|
|
524
501
|
dev.samy.velocity.set(101).wait()
|
|
525
502
|
|
|
526
|
-
scan =
|
|
503
|
+
scan = scans.grid_scan(
|
|
527
504
|
dev.samx,
|
|
528
505
|
-5,
|
|
529
506
|
5,
|
|
@@ -576,37 +553,21 @@ def test_file_writer(bec_ipython_client_fixture, scan_name):
|
|
|
576
553
|
|
|
577
554
|
|
|
578
555
|
@pytest.mark.timeout(100)
|
|
579
|
-
def
|
|
580
|
-
bec = bec_ipython_client_fixture
|
|
581
|
-
bec.metadata.update({"unit_test": "test_group_def"})
|
|
582
|
-
scans = bec.scans
|
|
583
|
-
dev = bec.device_manager.devices
|
|
584
|
-
scan_number = bec.queue.next_scan_number
|
|
585
|
-
with scans.scan_group:
|
|
586
|
-
scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.1, relative=False)
|
|
587
|
-
scans.umv(dev.samy, 5, relative=False)
|
|
588
|
-
scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.1, relative=False)
|
|
589
|
-
|
|
590
|
-
assert scan_number == bec.queue.next_scan_number - 2
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
@pytest.mark.timeout(100)
|
|
594
|
-
@pytest.mark.parametrize("scan_name", ["list_scan", "_v4_list_scan"])
|
|
595
|
-
def test_list_scan(bec_ipython_client_fixture, scan_name):
|
|
556
|
+
def test_list_scan(bec_ipython_client_fixture):
|
|
596
557
|
bec = bec_ipython_client_fixture
|
|
597
558
|
bec.metadata.update({"unit_test": "test_list_scan"})
|
|
598
559
|
scans = bec.scans
|
|
599
560
|
dev = bec.device_manager.devices
|
|
600
561
|
|
|
601
|
-
status =
|
|
562
|
+
status = scans.list_scan(
|
|
602
563
|
dev.samx, [0, 1, 2, 3, 4], dev.samy, [0, 1, 2, 3, 4], exp_time=0.1, relative=False
|
|
603
564
|
)
|
|
604
565
|
assert len(status.scan.live_data) == 5
|
|
605
566
|
|
|
606
|
-
status =
|
|
567
|
+
status = scans.list_scan(dev.samx, [0, 1, 2, 3, 4, 5], exp_time=0.1, relative=False)
|
|
607
568
|
assert len(status.scan.live_data) == 6
|
|
608
569
|
|
|
609
|
-
status =
|
|
570
|
+
status = scans.list_scan(
|
|
610
571
|
dev.samx,
|
|
611
572
|
[0, 1, 2, 3],
|
|
612
573
|
dev.samy,
|
|
@@ -624,7 +585,7 @@ def test_time_scan(bec_ipython_client_fixture):
|
|
|
624
585
|
bec = bec_ipython_client_fixture
|
|
625
586
|
bec.metadata.update({"unit_test": "test_time_scan"})
|
|
626
587
|
scans = bec.scans
|
|
627
|
-
status = scans.time_scan(points=5, interval=0.5, exp_time=0.1
|
|
588
|
+
status = scans.time_scan(points=5, interval=0.5, exp_time=0.1)
|
|
628
589
|
assert len(status.scan.live_data) == 5
|
|
629
590
|
|
|
630
591
|
|
|
@@ -881,8 +842,7 @@ def test_grid_scan_secondary_queue(capsys, bec_ipython_client_fixture):
|
|
|
881
842
|
|
|
882
843
|
|
|
883
844
|
@pytest.mark.timeout(100)
|
|
884
|
-
|
|
885
|
-
def test_scan_after_scan_lock(capsys, bec_ipython_client_fixture, scan_name):
|
|
845
|
+
def test_scan_after_scan_lock(capsys, bec_ipython_client_fixture):
|
|
886
846
|
"""
|
|
887
847
|
Test that pending scans are properly executed after a scan lock is released.
|
|
888
848
|
"""
|
|
@@ -891,10 +851,8 @@ def test_scan_after_scan_lock(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
891
851
|
bec.metadata.update({"unit_test": "test_scan_after_scan_lock"})
|
|
892
852
|
dev = bec.device_manager.devices
|
|
893
853
|
bec.queue.add_queue_lock(queue="primary", reason="unit_test_scan_lock", lock_id="test_lock")
|
|
894
|
-
|
|
895
|
-
|
|
896
|
-
)
|
|
897
|
-
scan2 = getattr(scans, scan_name)(
|
|
854
|
+
scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.01, relative=True, hide_report=True)
|
|
855
|
+
scan2 = scans.line_scan(
|
|
898
856
|
dev.samx, -5, 5, steps=10, exp_time=0.01, relative=True, hide_report=True
|
|
899
857
|
)
|
|
900
858
|
|
|
@@ -908,8 +866,7 @@ def test_scan_after_scan_lock(capsys, bec_ipython_client_fixture, scan_name):
|
|
|
908
866
|
|
|
909
867
|
|
|
910
868
|
@pytest.mark.timeout(100)
|
|
911
|
-
|
|
912
|
-
def test_scan_repeat_decorator(bec_ipython_client_fixture, scan_name):
|
|
869
|
+
def test_scan_repeat_decorator(bec_ipython_client_fixture):
|
|
913
870
|
"""
|
|
914
871
|
Test the scan_repeat decorator by simulating a communication failure during a scan.
|
|
915
872
|
The scan should be retried according to the specified max_repeats and exc_handler.
|
|
@@ -953,9 +910,7 @@ def test_scan_repeat_decorator(bec_ipython_client_fixture, scan_name):
|
|
|
953
910
|
|
|
954
911
|
@scan_repeat(max_repeats=2, exc_handler=exc_handler)
|
|
955
912
|
def my_scan():
|
|
956
|
-
|
|
957
|
-
dev.positioner_with_failure, -5, 5, steps=10, exp_time=0.01, relative=True
|
|
958
|
-
)
|
|
913
|
+
scans.line_scan(dev.positioner_with_failure, -5, 5, steps=10, exp_time=0.01, relative=True)
|
|
959
914
|
|
|
960
915
|
my_scan()
|
|
961
916
|
|
|
@@ -965,10 +920,7 @@ def test_scan_repeat_decorator(bec_ipython_client_fixture, scan_name):
|
|
|
965
920
|
|
|
966
921
|
|
|
967
922
|
@pytest.mark.timeout(100)
|
|
968
|
-
|
|
969
|
-
"scan_name", [("grid_scan", "line_scan"), ("_v4_grid_scan", "_v4_line_scan")]
|
|
970
|
-
)
|
|
971
|
-
def test_scan_set_completed(bec_ipython_client_fixture, scan_name):
|
|
923
|
+
def test_scan_set_completed(bec_ipython_client_fixture):
|
|
972
924
|
"""
|
|
973
925
|
Test that a scan can be manually set to completed.
|
|
974
926
|
"""
|
|
@@ -988,9 +940,7 @@ def test_scan_set_completed(bec_ipython_client_fixture, scan_name):
|
|
|
988
940
|
|
|
989
941
|
threading.Thread(target=_set_scan_completed, args=(bec,), daemon=True).start()
|
|
990
942
|
|
|
991
|
-
|
|
992
|
-
dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True
|
|
993
|
-
)
|
|
943
|
+
scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True)
|
|
994
944
|
|
|
995
945
|
# Now add a second scan to ensure scans can continue after setting completed
|
|
996
|
-
|
|
946
|
+
scans.line_scan(dev.samx, -5, 5, steps=10, exp_time=0.01, relative=True)
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_scans_lib_e2e.py
RENAMED
|
@@ -16,31 +16,25 @@ logger = bec_logger.logger
|
|
|
16
16
|
|
|
17
17
|
|
|
18
18
|
@pytest.mark.timeout(100)
|
|
19
|
-
|
|
20
|
-
def test_grid_scan_lib(bec_client_lib, scan_name):
|
|
19
|
+
def test_grid_scan_lib(bec_client_lib):
|
|
21
20
|
bec = bec_client_lib
|
|
22
21
|
scans = bec.scans
|
|
23
22
|
bec.metadata.update({"unit_test": "test_grid_scan_bec_client_lib"})
|
|
24
23
|
dev = bec.device_manager.devices
|
|
25
|
-
|
|
26
|
-
status =
|
|
27
|
-
dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True
|
|
28
|
-
)
|
|
24
|
+
scans.umv(dev.samx, 0, dev.samy, 0, relative=False)
|
|
25
|
+
status = scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=0.01, relative=True)
|
|
29
26
|
status.wait(num_points=True, file_written=True)
|
|
30
27
|
assert len(status.scan.live_data) == 100
|
|
31
28
|
assert status.scan.num_points == 100
|
|
32
29
|
|
|
33
30
|
|
|
34
31
|
@pytest.mark.timeout(100)
|
|
35
|
-
|
|
36
|
-
def test_grid_scan_lib_cancel(bec_client_lib, scan_name):
|
|
32
|
+
def test_grid_scan_lib_cancel(bec_client_lib):
|
|
37
33
|
bec = bec_client_lib
|
|
38
34
|
scans = bec.scans
|
|
39
35
|
bec.metadata.update({"unit_test": "test_grid_scan_bec_client_lib"})
|
|
40
36
|
dev = bec.device_manager.devices
|
|
41
|
-
status =
|
|
42
|
-
dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=1, relative=False
|
|
43
|
-
)
|
|
37
|
+
status = scans.grid_scan(dev.samx, -5, 5, 10, dev.samy, -5, 5, 10, exp_time=1, relative=False)
|
|
44
38
|
time.sleep(0.5)
|
|
45
39
|
status.cancel()
|
|
46
40
|
|
|
@@ -352,6 +346,7 @@ def test_dap_fit(bec_client_lib):
|
|
|
352
346
|
"invalid_device_class",
|
|
353
347
|
],
|
|
354
348
|
)
|
|
349
|
+
@pytest.mark.timeout(100)
|
|
355
350
|
def test_config_reload(
|
|
356
351
|
bec_test_config_file_path, bec_client_lib, config, raises_error, deletes_config, disabled_device
|
|
357
352
|
):
|
|
@@ -550,31 +545,6 @@ def test_cached_device_readout(bec_client_lib):
|
|
|
550
545
|
assert timestamp_3 == timestamp_2
|
|
551
546
|
|
|
552
547
|
|
|
553
|
-
@pytest.mark.timeout(100)
|
|
554
|
-
@pytest.mark.skip(reason="Interactive scans are currently not supported in v4 scans.")
|
|
555
|
-
def test_interactive_scan(bec_client_lib):
|
|
556
|
-
bec = bec_client_lib
|
|
557
|
-
bec.metadata.update({"unit_test": "test_interactive_scan"})
|
|
558
|
-
dev = bec.device_manager.devices
|
|
559
|
-
scans = bec.scans
|
|
560
|
-
|
|
561
|
-
with scans.interactive_scan(monitored=[dev.samx, dev.samy], exp_time=0.1) as scan:
|
|
562
|
-
for ii in range(10):
|
|
563
|
-
samx_status = dev.samx.set(ii)
|
|
564
|
-
samy_status = dev.samy.set(ii)
|
|
565
|
-
samx_status.wait()
|
|
566
|
-
samy_status.wait()
|
|
567
|
-
scan.trigger()
|
|
568
|
-
scan.read_monitored_devices(devices=[dev.samx, dev.samy])
|
|
569
|
-
report = scan.status
|
|
570
|
-
|
|
571
|
-
report.wait()
|
|
572
|
-
|
|
573
|
-
while len(report.scan.live_data) != 10:
|
|
574
|
-
time.sleep(0.1)
|
|
575
|
-
assert len(report.scan.live_data.samx.samx.val) == 10
|
|
576
|
-
|
|
577
|
-
|
|
578
548
|
@pytest.mark.timeout(100)
|
|
579
549
|
def test_bl_state(bec_client_lib):
|
|
580
550
|
bec = bec_client_lib
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_scans_v4_lib_e2e.py
RENAMED
|
@@ -16,7 +16,7 @@ from bec_server.scan_server.scans import position_generators
|
|
|
16
16
|
|
|
17
17
|
|
|
18
18
|
def _get_v4_scan_runner(bec, scan_name: str):
|
|
19
|
-
return getattr(bec.scans,
|
|
19
|
+
return getattr(bec.scans, scan_name)
|
|
20
20
|
|
|
21
21
|
|
|
22
22
|
def _run_v4_scan(
|
|
@@ -69,15 +69,6 @@ def _wait_for_live_data_count(bec, status, expected_count: int, timeout: float =
|
|
|
69
69
|
time.sleep(0.1)
|
|
70
70
|
|
|
71
71
|
|
|
72
|
-
def _wait_for_scan_status(status, expected_status: str, timeout: float = 10):
|
|
73
|
-
deadline = time.time() + timeout
|
|
74
|
-
while time.time() < deadline:
|
|
75
|
-
if status.status == expected_status:
|
|
76
|
-
return
|
|
77
|
-
time.sleep(0.1)
|
|
78
|
-
raise TimeoutError(f"Timed out waiting for scan status {expected_status!r}.")
|
|
79
|
-
|
|
80
|
-
|
|
81
72
|
def _wait_for_queue_status(bec, queue_name: str, expected_status: str, timeout: float = 10):
|
|
82
73
|
deadline = time.time() + timeout
|
|
83
74
|
while time.time() < deadline:
|
|
@@ -240,7 +231,7 @@ def test_v4_fixed_point_scans_lib(
|
|
|
240
231
|
|
|
241
232
|
|
|
242
233
|
@pytest.mark.timeout(120)
|
|
243
|
-
def
|
|
234
|
+
def test_mv_scan_lib(bec_client_lib):
|
|
244
235
|
bec = bec_client_lib
|
|
245
236
|
dev = bec.device_manager.devices
|
|
246
237
|
|
|
@@ -252,7 +243,7 @@ def test_v4_mv_scan_lib(bec_client_lib):
|
|
|
252
243
|
|
|
253
244
|
|
|
254
245
|
@pytest.mark.timeout(120)
|
|
255
|
-
def
|
|
246
|
+
def test_umv_scan_lib(bec_client_lib):
|
|
256
247
|
bec = bec_client_lib
|
|
257
248
|
dev = bec.device_manager.devices
|
|
258
249
|
|
|
@@ -264,7 +255,7 @@ def test_v4_umv_scan_lib(bec_client_lib):
|
|
|
264
255
|
|
|
265
256
|
|
|
266
257
|
@pytest.mark.timeout(120)
|
|
267
|
-
def
|
|
258
|
+
def test_cont_line_scan_lib(bec_client_lib):
|
|
268
259
|
bec = bec_client_lib
|
|
269
260
|
dev = bec.device_manager.devices
|
|
270
261
|
original_velocity = dev.samx.velocity.get()
|
|
@@ -282,7 +273,7 @@ def test_v4_cont_line_scan_lib(bec_client_lib):
|
|
|
282
273
|
|
|
283
274
|
|
|
284
275
|
@pytest.mark.timeout(120)
|
|
285
|
-
def
|
|
276
|
+
def test_line_sweep_scan_lib(bec_client_lib):
|
|
286
277
|
bec = bec_client_lib
|
|
287
278
|
dev = bec.device_manager.devices
|
|
288
279
|
scans = bec.scans
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/beamline_mixin.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/callbacks/utils.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/SLS/__init__.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/SLS/sls_info.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/bec_ipython_client/plugins/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_beamline_mixins.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_bec_client.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_device_progress.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_live_table.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_move_callback.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_pretty_table.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/client_tests/test_signals.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_actors_e2e.py
RENAMED
|
File without changes
|
{bec_ipython_client-3.161.0 → bec_ipython_client-3.162.0}/tests/end-2-end/test_procedures_e2e.py
RENAMED
|
File without changes
|