Python
Last updated on June 17, 2026
You can run any Python function using the python parameter.
Let's start by creating a Python file in a new phases/ directory:
Then add a new phase referencing this module:
main:
- name: Test Functionality
python: phases.check_devicedef check_device():
pass # Your code hereTofuPilot will manage your Python Environment, run your function, and provide access to framework features through Function Parameters.
File
You can specify which Python file to execute using dot notation. Paths are resolved relative to your procedure .yaml file.
For example, for this file tree:
You can reference these files with:
main:
- name: Foo
python: phases.foo
- name: Bar
python: phases.nested.bar
- name: Baz
python: shared.bazFunction
You can specify which function to call using colon syntax: module:function.
TofuPilot defaults to the last component of the path as the function name.
main:
- name: Calibration
python: calibrate # Calls calibrate() function by default
- name: Custom Function
python: calibrate:run_calibration # Calls run_calibration() insteaddef calibrate():
pass # Default function - called by first phase
def run_calibration():
pass # Custom function - called by second phaseEnvironment
Overview
TofuPilot automatically manages Python virtual environments and runs your code in isolation, ensuring consistent behavior across development and production.
As soon as you add a Python phase to your procedure, TofuPilot automatically:
- Looks for an existing
venvdirectory in your procedure directory (or workspace root in a monorepo) - If found: Uses it as-is, unless your dependencies or Python version changed
- If not found: Creates a
venvdirectory with the specified Python version (defaults to 3.11) - Installs dependencies from
pyproject.tomlorrequirements.txtif either exists (the venv is created without dependencies if neither is present) - Re-syncs dependencies whenever
pyproject.toml,requirements.txt, or the Python version changes
Dependencies
Edit pyproject.toml in your procedure directory to manage dependencies:
[project]
name = "my-procedure"
version = "0.1.0"
requires-python = ">=3.11"
dependencies = [
"numpy>=1.24.0",
"pandas>=2.0.0",
]TofuPilot will automatically install these dependencies when you run your procedure.
Under the hood, TofuPilot uses UV, a Python package manager faster than pip, with full support for the PEP 508 dependency specification.
Python version
TofuPilot builds on the lowest supported Python that satisfies requires-python in your pyproject.toml. If you omit requires-python, the default is 3.12.
[project]
requires-python = ">=3.12">=3.12 builds on 3.12; >=3.13 builds on 3.13. The lowest satisfying version is chosen because packages drop support for older Python far more slowly than they add it for newer, so the floor maximizes dependency compatibility.
Selection happens at the minor level (3.12), not the patch (3.12.4). The station provisions a virtual environment on whichever compatible patch is available or fetchable, and the dependency wheels are compatible across patches of the same minor line.
Supported minor versions:
| Version | Notes |
|---|---|
| 3.10 | Oldest supported |
| 3.11 | |
| 3.12 | Default when requires-python is omitted |
| 3.13 | |
| 3.14 | Newest supported |
Use a range, not an exact pin. An exact pin like ==3.13 or requires-python = "==3.13.4" matches a single patch that the build may not ship, and the build fails with "no supported Python satisfies requires-python". Pin a lower bound (and optionally an upper bound) instead:
[project]
requires-python = ">=3.13,<3.14"If you must pin a single minor, use the wildcard form ==3.13.* (matches any 3.13 patch), not ==3.13.
For advanced use cases, you can configure private registries, local packages, Git dependencies, and platform-specific requirements directly in your pyproject.toml:
Function Parameters
TofuPilot automatically injects parameters based on your function signature. You can refer to each framework feature's documentation for Python function parameters usage.
Phase Outcome
Use phase to set phase outcome
Measurements
Use measurements to record test data
Logs
Use log to output messages
Operator UI
Use ui to update interface components
Attachments
Use attach to attach files and data to reports
Plugs
Use your plug methods from any phase
Unit Under Test
Use unit to set UUT metadata
Run
Use run to access the full test context
Previous Results
Use a completed phase's key to access its results
How is this guide?