Open-source project
opendr-eu/opendr avatar
opendr-eu/opendr

OpenDR ships four interfaces over one Python core, and its Makefile defaults to a dependency install rather than a build

A modular, open and non-proprietary toolkit for core robotic functionalities by harnessing deep learning

729 stars103 forksPythonApache-2.0

At a glance

What is it?
The EU funded robotics toolkit exposes Python, a C API, and two ROS workspaces, with three Dockerfiles and a build that compiles two control modules by hand. Its documented release tags stop in 2023 while the repository itself was pushed to in May 2026.
Who is it for?
OpenDR fits a research group that already speaks ROS and wants one perception stack rather than four. Two things to check before you commit a project to it.
Can I use it commercially?
Yes. Apache-2.0 is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
Is it still maintained?
Yes. The repository last received commits 153 days ago.
What is it written in?
Mainly Python, according to GitHub's language statistics.

Answers come from the project's GitHub data, last synced on October 11, 2026, and from our analysis. They are not legal advice.

Editorial analysis

Running make with no target installs dependencies and compiles two modules

The Makefile picks a default goal before doing anything else. When no target is named, MAKECMDGOALS is set to release, and release depends on install_compilation_dependencies. So a bare make is not a build, it is a dependency installation that runs four scripts in the dependencies directory, install.sh with the compilation argument, then install_onnx.sh, install_rapidjson.sh and install_torch_c_api.sh, and it finishes by recursing into two control modules:

code
@+make --silent -C src/opendr/control/mobile_manipulation $(TARGET) OPENDR_HOME="$(OPENDR_HOME)";
@+make --silent -C src/opendr/control/single_demo_grasp $(TARGET) OPENDR_HOME="$(OPENDR_HOME)";

The runtime dependency target is separate and is not part of release. It installs the runtime set and then builds RetinaFace inside the perception tree, which means an object detection component is compiled as a side effect of runtime setup rather than lazily on first use.

OPENDR_HOME is set from the current directory unless the caller exports it, and both recursion steps pass it down explicitly, since a relative path would break for anything that changes directory.

Three Dockerfiles, and the default one boots a notebook on port 8888

The tree carries Dockerfile, Dockerfile-cuda and Dockerfile-embedded, so the CUDA path is a separate file rather than a build stage you can switch with a flag. What the default file does is worth reading before using it anywhere shared. It starts from ubuntu:20.04 with two build arguments, branch defaulting to master and ros_distro defaulting to noetic, downloads Tini at a pinned v0.19.0 as the entrypoint, then clones the repository shallowly with submodules:

code
RUN git clone --depth 1 --recurse-submodules -j8 https://github.com/opendr-eu/opendr -b $branch

After install.sh runs and the cache is cleared, a start script is generated that activates the environment and launches Jupyter with no browser, bound to 0.0.0.0 on port 8888 and run with --allow-root. That combination serves a root-owned notebook to every interface on the container network, which is the normal shape for a personal development image and a real exposure on a shared or cloud host.

Four interface surfaces sit on top of one Python package

The toolkit presents itself through four entry points, and the relationship between them is hierarchical rather than equal. Python is the substrate, with the main interface living in the opendr package under src. The C API in src/c_api exists for performance critical application code and has its own set of C demos under projects/c_api. Two ROS workspaces sit alongside it, projects/opendr_ws for ROS1 and projects/opendr_ws_2 for ROS2, providing ready-to-use nodes rather than libraries. The document states that you may run as many tools as you wish simultaneously because there is no hardware limitation on tool count, then immediately qualifies it: hardware constraints such as GPU memory may restrict how many can actually run at once.

The qualification is the practical one. Several of the components in this toolkit are deep learning models, so the limit on concurrent tools is memory, not a licensing or a scheduler constraint in the framework. Interchange formats are named alongside ROS and the simulator: ONNX for model exchange and an OpenAI Gym interface for reinforcement learning work, with support built around the Webots Open Source Robot Simulator.

The pip route and the clone route do not cost the same

Three installation paths are offered and each has a different cost, written as three short lines with a support annotation attached to each. Cloning this repository supports CPU and GPU. Using pip supports CPU and GPU only. Using docker supports CPU and GPU. The repeated annotation is the interesting part, since the pip line is the one qualified with only, and the file listing explains why: the repository contains .gitmodules, and the Dockerfile clone step has to pass --recurse-submodules to get them. A pip install receives whatever has been packaged and uploaded, which does not necessarily carry the submodules the in-tree build expects.

That distinction matters for anyone needing the compilation step. The Makefile builds two control modules from source during install_compilation_dependencies, and installs a Torch C API, so the source path has machinery that a wheel may or may not carry. The installation details themselves are not in this file: the link for installation points at docs/reference/installation.md, and the per tool documentation starts from a tools index at docs/reference/index.md. The project wiki is named as the place for detailed documentation and for contribution instructions.

The example tree is grouped by robotics task rather than by interface

Inside projects/python, examples are arranged by what a robot is doing rather than by which API exposes them: perception, control, simulation, and a utils folder described as holding hyperparameter tuning tools. The C API examples live outside that tree in projects/c_api, and the ROS nodes are workspaces rather than example directories, so the same concept appears in up to three places depending on which surface you are reading. The README points at the right one of those three per interest: the ROS workspaces for ready-to-use nodes, the projects/python folder for examples and tutorials, and the C demos for the C interface.

Supporting infrastructure sits at the top level in the form of dependencies/, scripts/, tests/, include/, lib/ and bin/, plus a description.txt and a packages.txt that describe what the release contains. Two workflow files at the root, .clang-format and .flake8, tell you the C side and the Python side each have their own style gate, and CODEOWNERS indicates the work is split across owners. A styletest target in the Makefile installs tests/requirements.txt before running its checks, so the style rules execute from a pinned requirements list rather than from the ambient environment.

The citation is a 2022 paper marked to appear, and the newest tag is from 2023

The reference block points at an inproceedings entry for OpenDR: An Open Toolkit for Enabling High Performance, Low Footprint Deep Learning for Robotics, with seventeen named authors and a booktitle line for the 2022 IEEE/RSJ International Conference on Intelligent Robots and Systems carrying the note that it was to appear. Nothing in that block has been revised, so the citation still describes a forthcoming paper rather than a published one.

The release history sits well past that. Three tags are visible: v3.0.0 on 2023-12-04, v2.2.0 on 2023-07-03 and v2.1.0 on 2023-02-22, each labelled as an OpenDR toolkit release. The repository was last pushed on 2026-05-11, which is nearly three years after the newest tag. Both dates matter for a project that aims to be a shared reference implementation: the tags give you something stable to pin, and the newer commits mean the default branch has moved without a version marker. The CHANGELOG.md at the root is the file to read for that gap, and the DOI badge points at a Zenodo record for archival citation.

Windows gets its own branch of the same home directory variable

One detail in the Makefile handles a case most Linux instructions never mention. OPENDR_HOME defaults to the current working directory, except when uname contains MINGW, in which case it is derived differently:

code
export OPENDR_HOME:=`pwd -W | tr -s / '\\'`

The Windows branch asks the shell for a native path rather than the MSYS style path, which matters because native compilers and native Python builds on Windows do not understand the slash form. The Makefile also has a separate comment marking the case explicitly, so the exception was added on purpose rather than by accident. That single branch is the entire Windows accommodation visible in this file; the rest of the build assumes a POSIX shell, and the Dockerfile line for clearing caches after installation uses the same assumption.

For anyone running the build under Git Bash or WSL, the practical consequence is that this variable should be exported before invoking make, otherwise the native form is derived from whatever directory the shell happens to be in, and a later change of working directory inside the recursion leaves the compiled modules pointing at a path that no longer resolves.

Known issues and a review committee are documented separately from features

The link bar at the top of the file carries the governance documents alongside the installation ones: Known Issues at docs/reference/issues.md, a Toolkit Review Committee page at TRC.md, a Changelog at CHANGELOG.md and a License link. Separating known issues from the feature description is a deliberate choice for a project that has accumulated two ROS generations, three Dockerfiles and four interfaces, since the failure surface grows faster than the feature list.

The customization page at docs/reference/customize.md sits next to installation, which suggests the intended path is to take the toolkit and modify it rather than only call it. Two funding and citation anchors also point outward, a Zenodo DOI and the project website at opendr.eu. The acknowledgements record European Union Horizon 2020 funding under grant agreement No 871449, and the project describes itself as targeting healthcare, agri-food and agile production as its application areas, with sensing and actuation coupled to cognition named as the two core technologies beyond AI and cognition itself.

Editorial conclusion

OpenDR fits a research group that already speaks ROS and wants one perception stack rather than four. Two things to check before you commit a project to it. The newest tagged release is v3.0.0 from 2023-12-04, so anything you rely on should be pinned to a commit and read against CHANGELOG.md rather than a version number, since the last push on 2026-05-11 is not matched by any tag. And the default Docker path serves a Jupyter notebook on 0.0.0.0 port 8888 with --allow-root, which is fine for a laptop and not fine on a shared host. The C API is the piece worth evaluating first if you have performance limits, since the Python package is what everything else is built on.

Frequently asked questions

What does running make in the opendr repository do by default?

With no target named the Makefile sets MAKECMDGOALS to release, which runs install_compilation_dependencies: the four dependency install scripts plus silent sub-makes in the mobile_manipulation and single_demo_grasp control modules.

How do I install the OpenDR toolkit?

Three ways are given: cloning this repository, using pip, or using docker, and the detailed steps live in docs/reference/installation.md rather than in the README, with per tool documentation starting from the tools index at docs/reference/index.md.

What interfaces does OpenDR expose to other software?

A Python interface through the opendr package, a C API for performance critical code with demos under projects/c_api, and ready-to-use ROS nodes in the ROS1 and ROS2 workspaces, plus ONNX and OpenAI Gym interoperability.

Is the default OpenDR docker image safe to expose on a shared host?

The generated start script launches Jupyter with --no-browser bound to 0.0.0.0 on port 8888 and run with --allow-root, so it serves a root-owned notebook to every interface on the container network.

What is the newest tagged release of opendr?

v3.0.0 dated 2023-12-04, following v2.2.0 on 2023-07-03 and v2.1.0 on 2023-02-22, while the default branch was last pushed on 2026-05-11, so the branch has moved well past the newest tag.

Official sources

  1. Issues
  2. License: Apache-2.0
  3. opendr-eu/opendr on GitHub
  4. README
  5. Releases
Add this badge to your README

If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.

Add this badge to your README

markdown
[![Hysen Labs](https://hysenlabs.com/badge/opendr-eu-opendr.svg)](https://hysenlabs.com/projects/opendr-eu-opendr)