This guide helps you migrate your Python applications from machine-logic-sdk v2.2.0 to v3.0.0. The v3.0.0 release introduces significant changes to our robot programming SDK.
Table of Contents
Breaking Changes Overview
Category | Change Type | v2.2.0 | v3.0.0 |
|---|---|---|---|
Robot States | Breaking | Previous enums | New enums (different values) |
Teach Mode | Removed |
| Use |
Set Payload | Breaking |
|
|
Timestamp | Breaking | Custom | Standard Python |
Sequence Return | Breaking |
|
|
Wait for Motion | Breaking |
|
|
Digital I/O | Removed |
| Removed |
Velocity Limits | Deprecated | Returns actual limits | Returns default values (250.0 mm/s, 120.0 deg/s) |
Robot API Changes
Operational State Enum Changes
The RobotOperationalState enum has been completely redesigned. Both the names and values have changed.
v2.2.0
from machinelogic.ivention.irobot import RobotOperationalState
# Old enum values
RobotOperationalState.OFFLINE # = 0
RobotOperationalState.NON_OPERATIONAL # = 1
RobotOperationalState.FREEDRIVE # = 2
RobotOperationalState.NORMAL # = 3
RobotOperationalState.UNKNOWN # = 4
RobotOperationalState.NEED_MANUAL_INTERVENTION # = 5v3.0.0
from machinelogic.types import RobotOperationalState
# New enum values
RobotOperationalState.UNKNOWN # = 0 (value changed from 4)
RobotOperationalState.IDLE # = 1 ✨ NEW
RobotOperationalState.RUNNING # = 2 ✨ NEW
RobotOperationalState.JOGGING # = 3 ✨ NEW
RobotOperationalState.FREEDRIVE # = 4 (value changed from 2)
RobotOperationalState.STOPPING # = 5 ✨ NEW
RobotOperationalState.NON_OPERATIONAL # = 6 (value changed from 1)Migration Notes
Old State (v2.2.0) | New State (v3.0.0) | Action Required |
|---|---|---|
| ❌ Removed | Check for |
|
| Update value comparisons |
|
| Update value comparisons |
| ❌ Removed | Use |
|
| Update value comparisons |
| ❌ Removed | Handle via safety states |
- |
| Robot ready but not moving |
- |
| Robot executing trajectory |
- |
| Robot in jog mode |
- |
| Robot stopping motion |
Before (v2.2.0):
if robot.state.operational_state == RobotOperationalState.NORMAL:
print("Robot ready")After (v3.0.0):
if robot.state.operational_state == RobotOperationalState.IDLE:
print("Robot ready")
# Or check for running state
if robot.state.operational_state == RobotOperationalState.RUNNING:
print("Robot is executing a trajectory")Safety State Enum Changes
The RobotSafetyState enum has also been updated.
v2.2.0
RobotSafetyState.NORMAL # = 0
RobotSafetyState.EMERGENCY_STOP # = 2
RobotSafetyState.REDUCED_SPEED # = 3
RobotSafetyState.SAFEGUARD_STOP # = 4
RobotSafetyState.UNKNOWN # = 5v3.0.0
RobotSafetyState.UNKNOWN # = 0 (value changed from 5)
RobotSafetyState.NORMAL # = 1 (value changed from 0)
RobotSafetyState.EMERGENCY_STOP # = 2 (unchanged)
RobotSafetyState.REDUCED_SPEED # = 3 (unchanged)
RobotSafetyState.RECOVERABLE_FAULT # = 4 ✨ NEW (replaces SAFEGUARD_STOP)Migration Notes
Old State (v2.2.0) | New State (v3.0.0) | Action Required |
|---|---|---|
|
| Update value comparisons |
| ❌ Removed | Use |
|
| Update value comparisons |
- |
| Handle recoverable faults |
Removed Methods
The following methods have been removed in v3.0.0:
robot.teach_mode() - Context Manager for Freedrive
v2.2.0:
with my_robot.teach_mode():
print("Robot is in teach mode for 5 seconds")
time.sleep(5)
# Robot automatically returns to normal modev3.0.0:
my_robot.set_to_freedrive()
print("Robot is in freedrive mode for 5 seconds")
time.sleep(5)
my_robot.set_to_normal()robot.set_tool_digital_output(pin, value)
This method has been removed. Tool digital outputs are no longer managed through the Robot class.
v2.2.0:
my_robot.set_tool_digital_output(pin=1, value=1)v3.0.0:
This functionality is no longer available through the SDK.
robot.state.get_digital_input_value(pin)
v2.2.0:
value = my_robot.state.get_digital_input_value(pin=1)v3.0.0:
This method has been removed.
robot.state.cartesian_position and robot.state.joint_angles
These deprecated properties have been removed. Use cartesian_position_data and joint_angles_data instead.
v2.2.0:
# These were already deprecated in v1.14.0
position = my_robot.state.cartesian_position
angles = my_robot.state.joint_anglesv3.0.0:
position, timestamp = my_robot.state.cartesian_position_data
angles, timestamp = my_robot.state.joint_angles_dataChanged Method Signatures
robot.set_payload()
v2.2.0:
def set_payload(self, payload: Kilograms) -> bool:
...
# Usage
success = my_robot.set_payload(2.76)
if success:
print("Payload set")v3.0.0:
def set_payload(
self,
payload: Kilograms,
center_of_mass: Vector, # Required: [x, y, z] in mm
inertia: Inertia | None = None # Optional: [ixx, ixy, ixz, iyy, iyz, izz] in kg·mm²
) -> None:
...
# Usage
my_robot.set_payload(2.76, center_of_mass=[10, 10, 10])
print("Payload set")
# With inertia (optional)
my_robot.set_payload(
2.76,
center_of_mass=[10, 10, 10],
inertia=[100, 0, 0, 100, 0, 100]
)robot.execute_sequence() and robot.execute_sequence_async()
v2.2.0:
def execute_sequence(self, sequence: ISequenceBuilder) -> bool:
...
# Usage
success = my_robot.execute_sequence(seq)
if not success:
print("Sequence execution failed")v3.0.0:
def execute_sequence(self, sequence: IRobotMoveSequence) -> None:
...
# Usage - raises exception on failure
my_robot.execute_sequence(seq)robot.wait_for_motion_completion()
v2.2.0:
def wait_for_motion_completion(self, timeout: float | None = None) -> bool:
...
# Usage
success = my_robot.wait_for_motion_completion(timeout=30.0)v3.0.0:
def wait_for_motion_completion(self) -> None:
...
# Usage - timeout parameter removed
my_robot.wait_for_motion_completion()robot.reset() → robot.set_to_normal() (Deprecated)
v2.2.0:
success = my_robot.reset()v3.0.0:
# reset() is deprecated, use set_to_normal() instead
my_robot.set_to_normal()
# reset() still works but is deprecated
success = my_robot.reset() # DeprecatedNew Methods
robot.set_to_normal()
Sets the robot to normal operational state. This is the preferred replacement for reset().
my_robot.set_to_normal()robot.set_to_freedrive()
Puts the robot into freedrive mode. Use with set_to_normal() to replace the removed teach_mode() context manager.
my_robot.set_to_freedrive()
# Robot can be manually moved
time.sleep(5)
my_robot.set_to_normal()robot.remove_log_alarm_callback(callback_id)
Remove a previously registered log alarm callback.
callback_id = my_robot.on_log_alarm(my_callback)
# Later...
my_robot.remove_log_alarm_callback(callback_id)robot.remove_system_state_change_callback(callback_id)
Remove a previously registered system state change callback.
callback_id = my_robot.on_system_state_change(my_callback)
# Later...
my_robot.remove_system_state_change_callback(callback_id)RobotState Changes
Timestamp Type Change
The timestamp returned by cartesian_position_data and joint_angles_data has changed from a custom Timestamp namedtuple to a standard Python datetime object.
v2.2.0:
joint_angles, timestamp = my_robot.state.joint_angles_data
# timestamp was a custom Timestamp namedtuple with seconds and nanoseconds
print(f"Timestamp: {timestamp}") # Timestamp(seconds=..., nanoseconds=...)v3.0.0:
joint_angles, timestamp = my_robot.state.joint_angles_data
# timestamp is now a standard datetime object
print(f"Timestamp: {timestamp.isoformat()}") # 2026-02-12T10:30:00.123456Sequence Builder Changes
Blend Parameter Change
The blend parameter in append_movel and append_movej has changed from a blend_factor (0.0-1.0 scale factor) to a blend_radius (millimeters).
v2.2.0:
seq = my_robot.create_sequence()
seq.append_movel(target, velocity, acceleration, blend_factor=0.5) # Scale factor
seq.append_movej(target, velocity, acceleration, blend_factor=0.5)v3.0.0:
seq = my_robot.create_sequence()
seq.append_movel(target, velocity, acceleration, blend_radius=5.0) # Millimeters
seq.append_movej(target, velocity, acceleration, blend_radius=5.0)Context Manager Support
v3.0.0 adds context manager support for sequences with automatic execution:
# Synchronous execution with context manager
with my_robot.create_sequence() as seq:
seq.append_movej(joint_target, velocity=10.0, acceleration=10.0)
seq.append_movel(cartesian_target, velocity=100.0, acceleration=100.0)
# Sequence executes automatically on exit
# Async execution with context manager
with my_robot.create_sequence().execute_async_on_exit() as seq:
seq.append_movej(joint_target, velocity=10.0, acceleration=10.0)
# Sequence starts executing asynchronously on exitCallback Management Changes
on_system_state_change() Now Returns a Callback ID
v2.2.0:
my_robot.on_system_state_change(handle_state_change)
# No way to remove the callbackv3.0.0:
callback_id = my_robot.on_system_state_change(handle_state_change)
# Later, you can remove it:
my_robot.remove_system_state_change_callback(callback_id)Import Path for Types
v2.2.0:
from machinelogic.ivention.irobot import RobotOperationalState, RobotSafetyStatev3.0.0:
from machinelogic.types import RobotOperationalState, RobotSafetyStateMigration Examples
Example 1: Basic Robot State Monitoring
v2.2.0:
from machinelogic import Machine
from machinelogic.ivention.irobot import RobotOperationalState, RobotSafetyState
machine = Machine()
robot = machine.get_robot("Robot")
def handle_state(op_state: RobotOperationalState, safety_state: RobotSafetyState):
if op_state == RobotOperationalState.NORMAL:
print("Robot is in normal mode")
elif op_state == RobotOperationalState.FREEDRIVE:
print("Robot is in freedrive")
robot.on_system_state_change(handle_state)v3.0.0:
from machinelogic import Machine
from machinelogic.types import RobotOperationalState, RobotSafetyState
machine = Machine()
robot = machine.get_robot("Robot")
def handle_state(op_state: RobotOperationalState, safety_state: RobotSafetyState):
if op_state == RobotOperationalState.IDLE:
print("Robot is ready (idle)")
elif op_state == RobotOperationalState.RUNNING:
print("Robot is executing a trajectory")
elif op_state == RobotOperationalState.FREEDRIVE:
print("Robot is in freedrive")
callback_id = robot.on_system_state_change(handle_state)
# Store callback_id if you need to remove the callback laterExample 2: Teach Mode / Freedrive
v2.2.0:
import time
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
# Using context manager
with robot.teach_mode():
print("Teach mode active")
time.sleep(10)
# Automatically exits teach modev3.0.0:
import time
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
# Manual freedrive control
robot.set_to_freedrive()
print("Freedrive active")
time.sleep(10)
robot.set_to_normal()
print("Back to normal")Example 3: Setting Payload
v2.2.0:
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
success = robot.set_payload(2.5)
if success:
print("Payload configured")
else:
print("Failed to set payload")v3.0.0:
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
# center_of_mass is now required [x, y, z] in mm
robot.set_payload(
payload=2.5,
center_of_mass=[0, 0, 50], # 50mm above the flange
inertia=None # Optional
)
print("Payload configured")Example 4: Execute Sequence
v2.2.0:
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
joint_target = [10, 20, 30, 40, 50, 60]
seq = robot.create_sequence()
seq.append_movej(joint_target, 10.0, 10.0, 0.5) # blend_factor
success = robot.execute_sequence(seq)
if not success:
print("Sequence failed")
success = robot.wait_for_motion_completion(timeout=30.0)v3.0.0:
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
joint_target = [10, 20, 30, 40, 50, 60]
# Option 1: Manual execution
seq = robot.create_sequence()
seq.append_movej(joint_target, 10.0, 10.0, 5.0) # blend_radius in mm
robot.execute_sequence(seq) # Raises on failure, no return value
# Option 2: Context manager (cleaner)
with robot.create_sequence() as seq:
seq.append_movej(joint_target, velocity=10.0, acceleration=10.0, blend_radius=5.0)
# Automatically executes and waitsExample 5: Reading Position Data
v2.2.0:
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
angles, timestamp = robot.state.joint_angles_data
print(f"Joint angles: {angles}")
print(f"Timestamp seconds: {timestamp.seconds}, ns: {timestamp.nanoseconds}")v3.0.0:
from machinelogic import Machine
machine = Machine()
robot = machine.get_robot("Robot")
angles, timestamp = robot.state.joint_angles_data
print(f"Joint angles: {angles}")
print(f"Timestamp: {timestamp.isoformat()}") # Standard datetimeQuick Reference Table
Feature | v2.2.0 | v3.0.0 |
|---|---|---|
Import enums |
|
|
Check robot ready |
|
|
Check robot moving |
|
|
Freedrive mode |
|
|
Reset robot |
|
|
Set payload |
|
|
Execute sequence |
|
|
Wait for motion |
|
|
Blend parameter |
|
|
Timestamp type |
|
|
Remove callbacks | Not supported |
|
Deprecated Features
The following features are deprecated in v3.0.0 and will be removed in a future version:
Feature | Status | Replacement |
|---|---|---|
| Deprecated |
|
| Deprecated (since v2.2.0) |
|
| Deprecated | Returns default 250.0 mm/s |
| Deprecated | Returns default 120.0 deg/s |