-
Notifications
You must be signed in to change notification settings - Fork 132
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
Is ament_target_dependencies() still necessary? #292
Comments
Do you implicitly want to deprecate packages which use old-style standard CMake variable and instead only support packages which use modern CMake targets? |
Dirk has a point. At the same time, transitioning towards modern CMake would be good. Perhaps, we can keep |
I think any transition needs to happen from the bottom up (similar to the transition from Maybe an option would be to add a deprecation warning when the function is being used only with dependencies which do export modern CMake targets at which point the function could become a no-op. That way the deprecation warnings happen incrementally and its usage can be removed in each package as soon as it is not necessary anymore. |
That's an option, but wouldn't it create package clusters that can stick to the old ways by virtue of being inactive? Though I guess we have to deal with that in the long run. Maybe we should better document which one's the right way ™ of doing things before even considering deprecating the older (but vastly more common) ones. |
There would always be at least one package at the bottom of the dependency chain which would get the deprecation warning. That package would need to be updated in order to allow downstream packages to transition to the modern style. Obviously this incremental approach could take a long time. I just doubt that you can force all packages to transition within a single release cycle. |
Hmm I guess that is the implication. Switching to
What about something softer than a deprecation than - like recommending using
I think it's safe to update packages in the middle of a chain as long as it's dependencies using standard CMake variables aren't publicly exposed, so that they don't need to be propagated downstream.
That sounds like it might be useful as an experiment to see how much remaining standard variable usage there is. |
How does that work - a package not exposing standard CMake variables (and no CMake targets I assume) but somehow being used by that "package in the middle"? |
Hmm I don't understand the question - I wonder if we're talking about different cases. What case has a package neither providing CMake variables nor CMake targets? I was talking about a package using standard CMake variables from another package, but not needing to make that info available to downstream packages. Say |
Such a case means that there is no need to export anything.
Using |
I patched
The number of uses of
|
@sloretz What do I have to do to export the targets? I guess call
If I call it afterwards, it complains it should be called before
|
Hi, is there still interest on this work? |
For messages, I can't find any method that makes sense, other than this really long target name buried in the cmake export. I wouldn't consider that intuitive, and it's not documented, but it works. Using ament_target_dependencies, with ament_target_dependencies(
foo_node
"bar_package"
) If you switch to raw cmake, no luck. You get include errors, because includes aren't propogated by the same name. Maybe that's a target, maybe not. I'd have to add debug logic to check it's a target. target_link_libraries(
foo_node
PRIVATE
"bar_package"
) If you switch to modern cmake alias targets, which error out if the target doesn't exist, intuitively, I'd expect a target_link_libraries(
foo_node
bar_package::bar_package
)
Through some trial and error, this works. target_link_libraries(
foo_node
PRIVATE
bar_package::bar_package__rosidl_generator_cpp
) Are the ROS maintainers actually expecting users wanting to use modern CMake to use those long target names? If you want to play around yourself, see my example repo here: https://github.com/Ryanf55/ryan_ros_mvp/tree/bug-cmake-target-link-libraries-msgs |
Thanks, I didn't know about that one. The other workaround which works (and which we've been using in the core as we've been slowly converting it to modern cmake targets) is
We really do want to deprecate (and eventually remove) |
If you have some references to previous work, that would be great. I can take a look into it. |
I do have concern for how something like Consdering getting information about a package after you call Edit: The last post here shows a reasonable solution for getting all the targets: https://discourse.cmake.org/t/cmake-list-of-all-project-targets/1077/16 |
@sloretz was the one that mentioned using those targets here, and they are (now) part of the public API. The namespace export is shown here. I propose at least documenting them in the tutorials; although the name is long, it provides clear advantages over To remove the ALIAS targets, one would have to go through a deprecation process since it's ABI breaking to remove them, so it's not like they will disappear. |
As mentioned above, ROS 2 message packages are a little bit tricky to handle. I want to point out that the solution proposed by @Ryanf55 is not complete. Besides simplifying how to use messages, I think it's also important to easily allow targets to depend only on the message struct definitions (e.g. I may have a library that does some computations using a ROS message as data type, even if it does not have any other dependency on ROS and it does not create nodes, publishers, subscriptions, etc) |
Great info, I just summarized the discussion into an issue in |
I found another blocker for migration to
Current behavior for BTCPPBehaviorTreeCPP supports building a few different ways. Existing users are recommended to consume it with the following: https://github.com/BehaviorTree/btcpp_sample/blob/1dac26a573df205968da1505ece0ca00fec30884/CMakeLists.txt#L27 PROJECT_NAME: Unfortunately, ament_export_targets generates the following when called as macro(export_btcpp_package)
ament_export_targets(${PROJECT_NAME}Targets HAS_LIBRARY_TARGET)
ament_export_dependencies(ament_index_cpp)
ament_package()
endmacro() # Create imported target behaviortree_cpp::behaviortree_cpp
add_library(behaviortree_cpp::behaviortree_cpp SHARED IMPORTED) Desired behavior for BTCPPIn order to have the same workflow as existing CMake users, it should do the following: # Create imported target BT::behaviortree_cpp
add_library(BT::behaviortree_cpp SHARED IMPORTED) Proposed interface
|
I was going to open an issue to add the
PRIVATE
keyword toament_taret_dependencies()
, but instead I'm wondering if it is still necessary now that ROS 2 packages offer modern CMake targets.A lot of code uses
ament_target_dependencies()
to make a target in one package depend on everything offered by another package, whether that uses old-style standard CMake variables or modern CMake targets.ament_target_dependencies(${PROJECT_NAME} rcl_logging_interface rcpputils rcutils spdlog )
ament_target_dependencies()
propagates include directories, compiler definitions, compiler flags, etc. However,target_link_libraries()
with modern CMake targets should do all of that too. As far as I can tell, I can usetarget_link_library()
calls with the targets that are now being exported from those packages.If I wanted to link against every target in an
ament_cmake
package, it looks like I could do:If
ament_target_dependencies()
is around just for convenience, it seems like the standard CMake way is equally convenient. What other value doesament_target_dependencies()
provide? Can it be deprecated?The text was updated successfully, but these errors were encountered: