Python SDK for OpenFlex robotic arm control via CAN bus
Project description
OpenFlex Driver
Developed by Chengdu Changshu Robotics Co., Ltd.
OpenFlex Driver is the Python SDK for OpenFlex / OpenArmX full-body robot control over CAN bus. It provides high-level interfaces for dual arms, head, lift column, and swerve chassis, while also exposing lower-level motor, CAN, calibration, and teleoperation utilities for integration and research workflows.
The package is designed for Linux robots using SocketCAN-compatible CAN adapters and Robstride / CANopen motor controllers.
Features
- Dual-arm control through
ArmandRobot - Head control with yaw / pitch joints
- Lift column control over CANopen CiA402
- Four-wheel swerve chassis control with steering and driving modules
- MIT and CSP motor control modes
- Motor enable / disable, mode switching, status reading, zero calibration
- CAN interface discovery and setup helpers
- Automatic and passive zero calibration utilities
- VR teleoperation / IK interface based on Pinocchio
- Binary wheel build support with Cython-compiled internal modules
Supported Components
| Component | Interface | Default CAN | Notes |
|---|---|---|---|
| Right arm | Arm, Robot.right_arm |
can0 |
Robstride arm motors, IDs 1-8 |
| Left arm | Arm, Robot.left_arm |
can1 |
Robstride arm motors, IDs 1-8 |
| Head | Head, Robot.head |
can2 |
Yaw ID 1, pitch ID 2 |
| Lift column | Column, Robot.column |
can3 |
CANopen CiA402 node, default ID 16 |
| Chassis driving | Chassis |
can4 |
UM wheel motors, default IDs 1-4 |
| Chassis steering | Chassis |
can5 |
RS steering motors, default IDs 5-8 |
Installation
Install from PyPI:
pip install openflex-driver
For local development:
git clone <your-repository-url>
cd openflex_driver
python3 -m pip install -e .
Requirements
- Linux with SocketCAN support
- Python >= 3.9
python-can >= 4.0.0PyYAML >= 5.4.0numpy >= 1.21.0pin >= 2.6.0for teleoperation / IK functionality- Cython is required when building wheels from source
CAN Setup
The driver can try to enable CAN interfaces automatically when auto_enable_can=True. For manual setup, use standard SocketCAN commands:
sudo ip link set can0 up type can bitrate 1000000
sudo ip link set can1 up type can bitrate 1000000
sudo ip link set can2 up type can bitrate 1000000
sudo ip link set can3 up type can bitrate 1000000
sudo ip link set can4 up type can bitrate 1000000
sudo ip link set can5 up type can bitrate 1000000
Check available CAN interfaces:
from openflex_driver import get_available_can_interfaces, verify_can_interface
print(get_available_can_interfaces())
print(verify_can_interface("can0"))
Quick Start
Single Arm
from openflex_driver import Arm
arm = Arm(can_channel="can0", side="right")
try:
arm.enable_arm_motors()
arm.set_mode("mit")
arm.move_to_mit(
motor_id=1,
position=0.3,
velocity=0.0,
torque=0.0,
kp=20.0,
kd=1.0,
)
status = arm.get_motor_status(motor_id=1)
print(status)
finally:
arm.disable_arm_motors()
arm.close()
Dual Arms and Full Robot
from openflex_driver import Robot
robot = Robot(
right_arm_can="can0",
left_arm_can="can1",
)
try:
robot.enable_right_arm()
robot.enable_left_arm()
robot.right_arm.set_mode("mit")
robot.left_arm.set_mode("mit")
robot.move_to_mit_right_arm(
motor_id=2,
position=0.2,
kp=20.0,
kd=1.0,
)
robot.move_to_mit_left_arm(
motor_id=2,
position=0.2,
kp=20.0,
kd=1.0,
)
robot.show_arms_status()
finally:
robot.disable_right_arm()
robot.disable_left_arm()
robot.shutdown()
To manage optional full-body components from Robot, pass head_can, column_can, steering_can, and driving_can, then initialize each component according to your hardware startup sequence.
Component Examples
Head
from openflex_driver import Head, JOINT_YAW, JOINT_PITCH
head = Head(can_channel="can2")
try:
head.connect()
head.enable()
head.move_to_mit(motor_id=JOINT_YAW, position=0.2)
head.move_to_mit(motor_id=JOINT_PITCH, position=-0.1)
print(head.get_joint_status())
finally:
head.disable()
head.disconnect()
Lift Column
from openflex_driver import Column
column = Column(can_interface="can3", node_id=16)
try:
column.connect()
column.enable()
column.switch_to_position_mode()
column.move_to_user_position(0.15)
print(column.get_status())
column.stop_motion()
finally:
column.disable()
column.close()
Swerve Chassis
from openflex_driver import Chassis
chassis = Chassis(steering_can="can5", driving_can="can4")
try:
chassis.connect()
chassis.enable_all()
# vx: forward m/s, vy: left m/s, omega: counter-clockwise rad/s
chassis.set_chassis_velocity(vx=0.2, vy=0.0, omega=0.0)
chassis.stop_motion()
print(chassis.get_status_table())
finally:
chassis.disable_all()
chassis.close()
Motor Inventory
from openflex_driver import position_motors, velocity_motors
for motor in position_motors():
print(motor.component, motor.name, motor.can_channel, motor.motor_id)
for motor in velocity_motors():
print(motor.component, motor.name, motor.can_channel, motor.motor_id)
Public API Overview
Main classes:
Arm: one arm controllerRobot: full robot controller that owns left / right arms and optional head, column, chassisHead: two-axis head controllerColumn: lift column controllerChassis: swerve chassis controllerMotorConfigLoader: load motor configuration and limits
Common helper APIs:
- CAN utilities:
get_available_can_interfaces,verify_can_interface,enable_can_interface,disable_can_interface - Motor management:
enable_motor,disable_motor,set_control_mode,get_motor_status_readonly - Motor control:
mit_motion_control,csp_motion_control,csp_set_speed_limits - Calibration:
auto_calibrate_zero,move_to_limit,move_to_position_smooth - Chassis kinematics:
ChassisSpeeds,SwerveDriveKinematics,default_module_positions - Teleoperation:
TeleopConfig,TeleopInputFrame,OpenArmTeleopController,PinocchioTeleopCore
Build From Source
The package compiles internal _lib modules into .so files during wheel / source distribution builds.
For local builds on a machine that already has build dependencies installed:
python3 -m build --no-isolation
For a clean isolated build, network access is required so Python can install build dependencies declared in pyproject.toml:
python3 -m build
Inspect generated wheels:
unzip -l dist/openflex_driver-*.whl
The helper scripts build_so.py and clean_so.py are local build tools and are excluded from the published source distribution.
Publishing
This repository includes GitHub Actions workflow support under .github/workflows/build.yml.
- Push to
main,master, orlinux_*: build wheels and publish to TestPyPI whenTEST_PYPI_API_TOKENis configured. - Push a tag like
v1.2.0: build wheels and publish to PyPI whenPYPI_API_TOKENis configured. - Supported build matrix: Python 3.9, 3.10, 3.11, 3.12 on
x86_64andaarch64.
Before a release:
# Update version in pyproject.toml and src/openflex_driver/__init__.py
git add .
git commit -m "Release v1.2.0"
git tag -a v1.2.0 -m "Release version 1.2.0"
git push
git push origin v1.2.0
Safety Notes
- Always verify CAN interfaces and motor IDs before enabling motors.
- Start with low velocity, low torque, and conservative
kp/kdvalues. - Keep the robot clear of people and obstacles during calibration and first motion tests.
- Run active zero calibration only when mechanical limits and emergency stop behavior are verified.
- Disable motors and close CAN connections when control is finished.
License
This project is licensed under the Creative Commons Attribution-NonCommercial-ShareAlike 4.0 International License.
Commercial use requires a separate license from Chengdu Changshu Robotics Co., Ltd. See LICENSE for details.
Contact Us
Chengdu Changshu Robotics Co., Ltd.
| Contact | Information |
|---|---|
| wangxunyue1@163.com openarmrobot@gmail.com |
|
| 📱 Phone/WeChat | +86-17746530375 |
| 🌐 Website | https://openarmx.com/ |
| 🌐 Documentation | http://docs.openarmx.com/ |
| 📍 Address | Xiqing District, Tianjin・Daochao Robotics Experience Center (Tomorrow City)・Tianjin Humanoid Robot Center |
| 👤 Contact Person | Mr. Wang |
Copyright © 2025 Chengdu Changshu Robotics Co., Ltd. All Rights Reserved.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distributions
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file openflex_driver-1.0.0.tar.gz.
File metadata
- Download URL: openflex_driver-1.0.0.tar.gz
- Upload date:
- Size: 5.1 MB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
03316069d39408ccfd9770dd55a790535e98a474473bfa1a2f88821179d656d2
|
|
| MD5 |
357549acd792c89a2758c60e98f54d35
|
|
| BLAKE2b-256 |
eb8d3613515f209562e733eb127872c4b0603a5de225fcd3e32b7ffd26416580
|
File details
Details for the file openflex_driver-1.0.0-cp312-cp312-manylinux_2_17_x86_64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp312-cp312-manylinux_2_17_x86_64.whl
- Upload date:
- Size: 5.4 MB
- Tags: CPython 3.12, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b187471c80bc16452b466d64b1f01dec7bb3d106ae4df70a0a48f28b9fc135a6
|
|
| MD5 |
9e2ba1e833d0e9db10bc96a446536eb1
|
|
| BLAKE2b-256 |
40dc1de34cd4e454c6ffe13f6d6d9e013a427a8a17c4784da782eb31f82a34d0
|
File details
Details for the file openflex_driver-1.0.0-cp312-cp312-manylinux_2_17_aarch64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp312-cp312-manylinux_2_17_aarch64.whl
- Upload date:
- Size: 5.4 MB
- Tags: CPython 3.12, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
eab641cb2d9a12d98ffa8740e136eac02e45b1e25de71af12f40f9663700bc57
|
|
| MD5 |
2ccb43070c7a5619bbad3b0a3c1e873a
|
|
| BLAKE2b-256 |
756c5f0b555f5b45d4e836225fa8d4680911368f83a4912d192c1edbe158c082
|
File details
Details for the file openflex_driver-1.0.0-cp311-cp311-manylinux_2_17_x86_64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp311-cp311-manylinux_2_17_x86_64.whl
- Upload date:
- Size: 5.4 MB
- Tags: CPython 3.11, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
0d4a0cde83d17b436753f10241497503077678ff928041dde21e5822fd2f3368
|
|
| MD5 |
036377b2496ac86eb23e5803d2c4f590
|
|
| BLAKE2b-256 |
90a58a116169f296c55a1210fbe2c4c9d5a1c7ae5d94f0b27e0233214742f0ce
|
File details
Details for the file openflex_driver-1.0.0-cp311-cp311-manylinux_2_17_aarch64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp311-cp311-manylinux_2_17_aarch64.whl
- Upload date:
- Size: 5.4 MB
- Tags: CPython 3.11, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
69167a969d61c3dbadc3d9a27a446ec5d4e3648193874b99b0967ecbb1723a89
|
|
| MD5 |
675b768c2b01740ac841ac1e821e511e
|
|
| BLAKE2b-256 |
059ead0dfed24776e308f8645d8c00289a32772465cd93e960a8271365d82ed1
|
File details
Details for the file openflex_driver-1.0.0-cp310-cp310-manylinux_2_17_x86_64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp310-cp310-manylinux_2_17_x86_64.whl
- Upload date:
- Size: 5.1 MB
- Tags: CPython 3.10, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
3db895a92a1181e6a3bb01f84ec2534b052a1e8b70ed78fb5fbf0f16cac971c7
|
|
| MD5 |
fb47f31918bea56120d3499027068651
|
|
| BLAKE2b-256 |
eaae5db9d5a0a591ee7d44483362bac36ffb7366647ab9cc6e49dc9904a08bcb
|
File details
Details for the file openflex_driver-1.0.0-cp310-cp310-manylinux_2_17_aarch64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp310-cp310-manylinux_2_17_aarch64.whl
- Upload date:
- Size: 5.1 MB
- Tags: CPython 3.10, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
ef70c073c25c86f0529a33a5906e3713daea7c4281825789f007aa548fdbdac8
|
|
| MD5 |
03971c349c8fe57e699b2d7fe4497ebf
|
|
| BLAKE2b-256 |
000ea7c9f5e3537b31b68f5f4977191d1cc186716869c4b6679db75e90c95e2d
|
File details
Details for the file openflex_driver-1.0.0-cp39-cp39-manylinux_2_17_x86_64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp39-cp39-manylinux_2_17_x86_64.whl
- Upload date:
- Size: 5.1 MB
- Tags: CPython 3.9, manylinux: glibc 2.17+ x86-64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
98cee2d0f2d44ad42407f4919b91e0156181885092a29764345e3916cd458934
|
|
| MD5 |
dbd23502fd6d15da7b08ebab1d7d57e8
|
|
| BLAKE2b-256 |
a7e7a178843d57527cbd503c272c33fd1cd372c7209e1e1bdf13be07baf01afe
|
File details
Details for the file openflex_driver-1.0.0-cp39-cp39-manylinux_2_17_aarch64.whl.
File metadata
- Download URL: openflex_driver-1.0.0-cp39-cp39-manylinux_2_17_aarch64.whl
- Upload date:
- Size: 5.1 MB
- Tags: CPython 3.9, manylinux: glibc 2.17+ ARM64
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.10.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
b1a9c7c8facc319e62c8c7e8ecfcfa5fd2d5577b91570914c04f8ed2ac3a76d4
|
|
| MD5 |
681f17285aae46711c52871c9e74dada
|
|
| BLAKE2b-256 |
47f0ff5306d136a58de0a72c27c8040406a52b76af1dc8da85ec91b97beab3ea
|