Migrate the Liquid Handling SDK
For breaking changes in unitelabs-sdk, see Migrate the SDK.
Liquid Handling SDK 0.42: lineage is recorded for you
What changed
In unitelabs-liquid-handling 0.41 and earlier, a workflow author had to record lineage with their own Audit.emit calls and write the deck's labware to ctx.state["labware_context"]. In 0.42 and later, the library records tip, liquid, gripper, and labware operations on a liquid handler by default, and describes the deck's labware itself. See Lineage from liquid handling.
unitelabs-liquid-handling 0.42 requires unitelabs-sdk 0.20 or later. The UniteLabs Platform must be at 0.34.0 or later to show the new events correctly.
Upgrade in this order
- Make sure your Platform is at 0.34.0 or later.
- Update
unitelabs-liquid-handlingto 0.42.0 or later in each workflow'spyproject.toml. - Remove your liquid-handling lineage code (see Code to change), or switch the library off (see Switch recording off during the transition).
- Run the workflow against a mock with
Audit.captureand compare the events with an earlier run. See Check the events locally.
Code to change
If your workflow emits its own lineage for liquid-handling operations, each operation is recorded twice after the upgrade. To find this code, search for Audit.emit, labware_context, and flush_workspace. Removing your own lineage events is the recommended upgrade path.
unitelabs-liquid-handling 0.41 and earlier | 0.42 and later |
|---|---|
Audit.emit(...) after a tip, aspirate, dispense, or gripper call | Remove it. The library records the operation. |
Deck labware written to ctx.state["labware_context"] | Remove it. The library describes the deck. |
Audit.flush_workspace() after filling labware_context | Remove it. The SDK sends the workspace at each phase boundary. |
load_carrier and unload_carrier steps emit one carrier event | The autoload records one move_labware between the loading tray and the deck. The plates on the carrier keep their history. |
Channel IDs channel:<n> | Channel IDs channel:<actor>:<module>:<n> |
One waste, Deck:<position>, <tool>:park | waste:<actor>:<name>, deck:<actor>:<position>, park:<actor>:<tool>, and loading_tray:<actor>:<track> for a carrier on the tray |
A failed carrier load or unload is still an error event, on move_labware.
Keep Audit.emit calls for devices that are not liquid handlers. See Emit lineage events.
Switch recording off during the transition
Alternatively, switch the library's automatic lineage off for selected operations, or entirely. The switch applies to everything called inside the with block, also inside phases and steps:
from unitelabs.liquid_handling import lineage
from unitelabs.sdk import Operation
# The library skips these operations. Your own events record them.
with lineage.disable(Operation.ASPIRATE, Operation.DISPENSE):
...
# The library records nothing.
with lineage.disable():
...
UNITELABS_LIQUID_HANDLING_LINEAGE=0 in the environment switches recording off for the whole Python process. Use it for a script, notebook, or test run. For a deployed workflow, use lineage.disable() in code.
lineage.disable and UNITELABS_LIQUID_HANDLING_LINEAGE are for the transition period only. They will be deprecated and removed in a later release. We recommend that you remove your own liquid-handling events and let the library record them.Code that reads channel IDs
If your code or an integration parses entity IDs, read the channel index from the last part of the ID, or from extras["channel"]. Do not read it from the second part, which is now the actor. The same goes for the deck, the loading tray, park sites and wastes: deck:star:7 is track 7 of the STAR's deck, not labware called deck. Read kind and the parts on each side instead of splitting the ID.
Last updated