Skip to content

Commit 3d52fce

Browse files
Fix device types and params
1 parent 0293b71 commit 3d52fce

3 files changed

Lines changed: 106 additions & 26 deletions

File tree

src/mx_bluesky/beamlines/i02_1/i02_1_gridscan_plan.py

Lines changed: 49 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -7,15 +7,15 @@
77
from dodal.beamlines.i02_1 import ZebraFastGridScanTwoD
88
from dodal.common import inject
99
from dodal.devices.attenuator.attenuator import ReadOnlyAttenuator
10+
from dodal.devices.beamlines.i02_1.flux import Flux
1011
from dodal.devices.common_dcm import DoubleCrystalMonochromatorBase
1112
from dodal.devices.fast_grid_scan import (
1213
set_fast_grid_scan_params as set_flyscan_params_plan,
1314
)
14-
from dodal.devices.flux import Flux
15-
from dodal.devices.s4_slit_gaps import S4SlitGaps
15+
from dodal.devices.slits import Slits
1616
from dodal.devices.undulator import BaseUndulator
1717
from dodal.devices.zebra.zebra import Zebra
18-
from pydantic import BaseModel, PrivateAttr
18+
from pydantic import BaseModel
1919
from pydantic_extra_types.semantic_version import SemanticVersion
2020
from semver import Version
2121

@@ -45,6 +45,10 @@
4545
from mx_bluesky.common.external_interaction.callbacks.grid.utils import (
4646
generate_start_info_from_num_grids,
4747
)
48+
from mx_bluesky.common.parameters.components import (
49+
IspybExperimentType,
50+
get_param_version,
51+
)
4852
from mx_bluesky.common.parameters.constants import (
4953
EnvironmentConstants,
5054
PlanNameConstants,
@@ -82,7 +86,7 @@ class FlyScanXRayCentreComposite(FlyScanEssentialDevices[GonioWithOmegaType]):
8286
attenuator: ReadOnlyAttenuator
8387
flux: Flux
8488
undulator: BaseUndulator
85-
s4_slit_gaps: S4SlitGaps
89+
s4_slit_gaps: Slits
8690

8791

8892
def construct_i02_1_specific_features(
@@ -139,35 +143,65 @@ def get_internal_param_version() -> SemanticVersion:
139143

140144

141145
class ExternalGridScanParams(BaseModel):
142-
gda_parameter_version: SemanticVersion
143146
visit: str
144147
file_name: str
145-
storage_directory: Path
148+
storage_directory: str
146149
exposure_time_s: float
147150
snapshot_directory: Path
148151
x_start_um: float
149152
y_start_um: float
150153
z_start_um: float
151154
x_steps: int
152155
y_steps: int
153-
sample_id: int | None = None
154-
155-
# Internal parameter version compatible with this external model
156-
_internal_param_version: str = PrivateAttr(default="6.0.0")
156+
beam_size_x: float
157+
beam_size_y: float
158+
microns_per_pixel_x: float
159+
microns_per_pixel_y: float
160+
upper_left_x: int
161+
upper_left_y: int
162+
detector_distance_mm: float
163+
sample_id: int
164+
165+
166+
def get_internal_params(params: ExternalGridScanParams) -> I02_1FgsParams:
167+
return I02_1FgsParams(
168+
y_starts_um=[params.y_start_um],
169+
x_start_um=params.x_start_um,
170+
z_starts_um=[params.z_start_um],
171+
omega_starts_deg=[0],
172+
sample_id=params.sample_id,
173+
visit=params.visit,
174+
parameter_model_version=get_param_version(),
175+
file_name=params.file_name,
176+
storage_directory=params.storage_directory,
177+
x_steps=params.x_steps,
178+
y_steps=[params.y_steps],
179+
path_to_xtal_snapshot=params.snapshot_directory,
180+
beam_size_x=params.beam_size_x,
181+
beam_size_y=params.beam_size_y,
182+
microns_per_pixel_x=params.microns_per_pixel_x,
183+
microns_per_pixel_y=params.microns_per_pixel_y,
184+
upper_left_x=params.upper_left_x,
185+
upper_left_y=params.upper_left_y,
186+
detector_distance_mm=params.detector_distance_mm,
187+
ispyb_experiment_type=IspybExperimentType.GRIDSCAN_2D,
188+
)
157189

158190

159191
def i02_1_gridscan_plan(
160-
parameters: I02_1FgsParams,
192+
parameters: ExternalGridScanParams,
161193
composite: FlyScanXRayCentreComposite = inject(""),
162194
) -> MsgGenerator:
163195
"""BlueAPI entry point for i02-1 grid scans"""
164196

165-
beamline_specific = construct_i02_1_specific_features(composite, parameters)
166-
callbacks = create_gridscan_callbacks(parameters)
197+
params = get_internal_params(parameters)
198+
199+
beamline_specific = construct_i02_1_specific_features(composite, params)
200+
callbacks = create_gridscan_callbacks(params)
167201

168202
@bpp.subs_decorator(callbacks)
169-
@ispyb_activation_decorator(parameters)
203+
@ispyb_activation_decorator(params)
170204
def decorated_flyscan_plan():
171-
yield from common_flyscan_xray_centre(composite, parameters, beamline_specific)
205+
yield from common_flyscan_xray_centre(composite, params, beamline_specific)
172206

173207
yield from decorated_flyscan_plan()

tests/unit_tests/beamlines/i02_1/test_i02_1_gridscan_plan.py

Lines changed: 55 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -5,17 +5,18 @@
55
from dodal.beamlines import i02_1
66
from dodal.beamlines.i02_1 import ZebraFastGridScanTwoD
77
from dodal.devices.attenuator.attenuator import ReadOnlyAttenuator
8+
from dodal.devices.beamlines.i02_1.flux import Flux
89
from dodal.devices.common_dcm import DoubleCrystalMonochromatorBase
910
from dodal.devices.eiger import EigerDetector
10-
from dodal.devices.flux import Flux
11-
from dodal.devices.s4_slit_gaps import S4SlitGaps
11+
from dodal.devices.slits import Slits
1212
from dodal.devices.synchrotron import Synchrotron
1313
from dodal.devices.undulator import BaseUndulator
1414
from dodal.devices.zebra.zebra import Zebra
1515
from pydantic import ValidationError
1616

1717
from mx_bluesky.beamlines.i02_1.composites import I02_1FgsParams
1818
from mx_bluesky.beamlines.i02_1.i02_1_gridscan_plan import (
19+
ExternalGridScanParams,
1920
FlyScanXRayCentreComposite,
2021
construct_i02_1_specific_features,
2122
i02_1_gridscan_plan,
@@ -42,6 +43,44 @@ def zebra_fgs_two_d() -> ZebraFastGridScanTwoD:
4243
return device
4344

4445

46+
@pytest.fixture
47+
def entry_params(tmp_path) -> ExternalGridScanParams:
48+
return ExternalGridScanParams(
49+
visit="visit",
50+
file_name="file_name",
51+
storage_directory=str(tmp_path),
52+
exposure_time_s=0.004,
53+
snapshot_directory=tmp_path,
54+
x_start_um=0,
55+
y_start_um=0,
56+
z_start_um=0,
57+
x_steps=5,
58+
y_steps=5,
59+
beam_size_x=5,
60+
beam_size_y=5,
61+
microns_per_pixel_x=1,
62+
microns_per_pixel_y=1,
63+
upper_left_x=1,
64+
upper_left_y=2,
65+
detector_distance_mm=100,
66+
sample_id=1,
67+
)
68+
69+
70+
@pytest.fixture
71+
def slits() -> Slits:
72+
device = i02_1.s4_slit_gaps.build(connect_immediately=True, mock=True)
73+
74+
return device
75+
76+
77+
@pytest.fixture
78+
def flux() -> Flux:
79+
device = i02_1.flux.build(connect_immediately=True, mock=True)
80+
81+
return device
82+
83+
4584
@pytest.fixture
4685
def fgs_composite(
4786
eiger: EigerDetector,
@@ -52,7 +91,7 @@ def fgs_composite(
5291
attenuator: ReadOnlyAttenuator,
5392
flux: Flux,
5493
undulator: BaseUndulator,
55-
s4_slit_gaps: S4SlitGaps,
94+
slits: Slits,
5695
zebra: Zebra,
5796
) -> FlyScanXRayCentreComposite:
5897
return FlyScanXRayCentreComposite(
@@ -65,7 +104,7 @@ def fgs_composite(
65104
attenuator,
66105
flux,
67106
undulator,
68-
s4_slit_gaps,
107+
slits,
69108
)
70109

71110

@@ -132,36 +171,43 @@ def test_i02_1_flyscan_xray_centre_in_re(
132171
run_engine: RunEngine,
133172
fgs_params_two_d: I02_1FgsParams,
134173
fgs_composite: FlyScanXRayCentreComposite,
174+
entry_params: ExternalGridScanParams,
135175
):
136176
expected_features = construct_i02_1_specific_features(
137177
fgs_composite, fgs_params_two_d
138178
)
139179

140180
mock_create_features.return_value = expected_features
141-
run_engine(i02_1_gridscan_plan(fgs_params_two_d, fgs_composite))
181+
run_engine(i02_1_gridscan_plan(entry_params, fgs_composite))
142182
mock_common_scan.assert_called_once_with(
143183
fgs_composite, fgs_params_two_d, expected_features
144184
)
145185

146186

147-
@patch(
148-
"mx_bluesky.beamlines.i02_1.i02_1_gridscan_plan.construct_i02_1_specific_features",
149-
)
150187
@patch(
151188
"mx_bluesky.beamlines.i02_1.i02_1_gridscan_plan.common_flyscan_xray_centre",
152189
new=MagicMock(),
153190
)
191+
@patch(
192+
"mx_bluesky.beamlines.i02_1.i02_1_gridscan_plan.get_internal_params",
193+
)
194+
@patch(
195+
"mx_bluesky.beamlines.i02_1.i02_1_gridscan_plan.construct_i02_1_specific_features",
196+
)
154197
@patch(
155198
"mx_bluesky.common.external_interaction.callbacks.grid.gridscan.ispyb_callback.StoreInIspyb"
156199
)
157200
def test_ispyb_activated_correct_params(
158201
mock_store_ispyb: MagicMock,
159202
mock_create_features: MagicMock,
203+
mock_get_internal_params: MagicMock,
160204
run_engine: RunEngine,
161205
fgs_params_two_d: I02_1FgsParams,
162206
fgs_composite: FlyScanXRayCentreComposite,
207+
entry_params: ExternalGridScanParams,
163208
):
164209
mock_ispyb = MagicMock()
210+
mock_get_internal_params.return_value = fgs_params_two_d
165211

166212
mock_store_ispyb.return_value = mock_ispyb
167213
expected_features = construct_i02_1_specific_features(
@@ -171,7 +217,7 @@ def test_ispyb_activated_correct_params(
171217

172218
mock_create_features.return_value = expected_features
173219

174-
run_engine(i02_1_gridscan_plan(fgs_params_two_d, fgs_composite))
220+
run_engine(i02_1_gridscan_plan(entry_params, fgs_composite))
175221
initial_group_info = populate_data_collection_group(fgs_params_two_d)
176222
initial_group_info.comments = f"Diffraction grid scan of {fgs_params_two_d.x_steps} by {fgs_params_two_d.y_steps[0]}.Zocalo processing took 0.00 s."
177223
initial_scan_info = ScanDataInfo(

uv.lock

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)