Skip to content

feature: allow extending a python package in ament_python_install_package #587

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: rolling
Choose a base branch
from

Conversation

nadavelkabets
Copy link

@nadavelkabets nadavelkabets commented Jun 14, 2025

Closes #514.

The most ament_cmake way to do this is to change up the way that ament_python_install_package works. For most things that are part of ament_cmake, the way that they work is that the call (to e.g. ament_export_libraries) doesn't do much work, and instead sets up a bunch of cmake variables, along with a hook. When ament_package is eventually called, it calls all of the hooks, and at that point the hook does the work based on the cmake variables. This is done this way so that ament_package has a full view of the environment, and avoids problems exactly like this.

For whatever reason, ament_python_install_package does not work like this at the moment. We should change ament_python_install_package to work in the more ament_cmake way, which will resolve this bug.

Following the suggestion from @clalancette,
calling ament_python_install_package now registers an environment hook and sets the parameters in environment variables, moving installation to the ament_package stage.

This allows to extend an existing package and thus allows to utilize rosidl_generate_interfaces and ament_python_install_package at the same time.

Related:

@nadavelkabets nadavelkabets changed the title feature: allow extending a python package in ament_python_isntall_package feature: allow extending a python package in ament_python_install_package Jun 14, 2025
@nadavelkabets nadavelkabets force-pushed the feature/ament-python-extend-package branch from d83479d to 00311aa Compare June 14, 2025 15:35
@nadavelkabets nadavelkabets marked this pull request as ready for review June 14, 2025 15:39
Signed-off-by: Nadav Elkabets <[email protected]>
@nadavelkabets nadavelkabets force-pushed the feature/ament-python-extend-package branch from e2862ff to 0f9b36d Compare June 14, 2025 17:59
Signed-off-by: Nadav Elkabets <[email protected]>
@nadavelkabets nadavelkabets force-pushed the feature/ament-python-extend-package branch from 0f9b36d to a8419ae Compare June 14, 2025 17:59
pszenher added a commit to pszenher/Distributional_RL_Decision_and_Control that referenced this pull request Jun 20, 2025
While the monopackage pattern (containing both message interfaces and
behavioral nodes) isn't intentionally unsupported by ROS2, it
currently cannot support packages using `ament_cmake_python` to build
C++ and Python code alongside `rosidl` message generation.

This is a well-known and long-standing issue;  see:
  ros2/rosidl_python#141
  ament/ament_cmake#514
  ament/ament_cmake#587

Accordingly, to support well-integrated inclusion of Python code in
this package (i.e., by adding `run_vrx_experiments.py` to the CMake
build system flow), this commit splits `virelex_msgs` out into a
separate package.  An argument could be made for converting
`run_vrx_experiments.py` into a Python-syntax launch file, but it does
a bit too much (defines a class, etc.) for that to feel like the
correct option.

In addition, this commit integrates the `pretrained_models` folder
into the new `trained` subdirectory of `virelex`, providing a stable
filesystem path to access those models during node execution (via
`get_package_share_directory("virelex")`).
@rkent
Copy link

rkent commented Jun 26, 2025

I've done an initial check of the code, and it generally looks good, except for one issue. As far as I can tell, you are not supporting AMENT_CMAKE_SYMLINK_INSTALL. Symlink install is probably incompatible with the concept of merging together multiple same-named python packages, but this need to merge is really rather rare, and symlink_install makes sense in the vast majority of packages that do not need this merger. It seems to me that the correct thing to do is to disable symlink install with a warning when multiple same-named packages are detected. Or did I miss something about how you supported this?

I have not actually tested yet, but will soon.

@nadavelkabets
Copy link
Author

nadavelkabets commented Jun 27, 2025

I've done an initial check of the code, and it generally looks good, except for one issue. As far as I can tell, you are not supporting AMENT_CMAKE_SYMLINK_INSTALL. Symlink install is probably incompatible with the concept of merging together multiple same-named python packages, but this need to merge is really rather rare, and symlink_install makes sense in the vast majority of packages that do not need this merger. It seems to me that the correct thing to do is to disable symlink install with a warning when multiple same-named packages are detected. Or did I miss something about how you supported this?

I kept the original package installation code without changes. To my knowledge, colcon changes the behavior of the install command depending on the AMENT_CMAKE_SYMLINK_INSTALL flag.
It appears like merging works correctly even with symlink install, due to the install command symlinking each file in the package recursively.

@rkent
Copy link

rkent commented Jun 27, 2025

This is the code from the original that does not have an equivalent in your PR. (I matched every line of the old code with your new code, and this is the only difference that I found). I'll test it today though to confirm whether it works or not.

Copy link

@rkent rkent left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've thoroughly checked the old code vs the new code, and confirmed that all of the old code has corresponding functionality in the new code, with one exception. I've also tested using a very simple combined msg/ directory with a python package of the same name, and everything works as I expect.

Concerning the exception code, I've compared results of the new code with old code for --symlink-install, and find that the new code works fine with the same result. As @nadavelkabets points out, the modifications to the install command are taking care of the symlinks. The only difference I could find is that in the old code, a symlink is created in the build/ directory, that is not present in the new code. But the end result in the /install directory is the same in both cases, so it is not clear to me why this symlink is needed. Trying to add that symlink would lead to a conflict between duplicate python packages and --symlink-install, so it is good that it is not needed.

But as @hidmic points out in PR #326 that created these symlinks, "There should be a Here be dragons sign in ament_cmake root README..." I'm afraid that fighting those dragons here is beyond my expertise. AFAICT that code is not needed. But perhaps @nadavelkabets you could give your own defense of why.

So with one nit, I've reviewed as thoroughly as I can and find no issues, so here's my gray checkmark.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

ament_cmake_python: Update ament_python_install_package() to allow installing more files into an existing package.
2 participants