Skip to main content
Version: 9

Migrate User Workspace From 8.x to 9.0

MoveIt Pro 9.0 introduces significant architectural and workflow improvements, and this migration guide is designed to help existing users update their systems smoothly and with confidence.

Environment Variable Changes

In version 9.0, we renamed the environment variables used by MoveIt Pro to better align with product naming. These included environment variables which were used in user workspaces such as:

  • STUDIO_USERNAMEMOVEIT_USERNAME
  • STUDIO_USER_UIDMOVEIT_USER_UID
  • STUDIO_USER_GIDMOVEIT_USER_GID
  • STUDIO_DOCKER_TAGMOVEIT_DOCKER_TAG
  • STUDIO_LICENSE_KEYMOVEIT_LICENSE_KEY

If you are using Linux, you can update your entire workspace with the following bash command inside your workspace:

sed -i 's/MOVEIT_STUDIO_BASE_IMAGE/MOVEIT_PRO_BASE_IMAGE/g' Dockerfile
for file in $(grep -r 'STUDIO_' -l); do
sed -i 's/STUDIO_/MOVEIT_/g' $file;
done

Host Hardware Access

We moved the responsibility for exposing host hardware from the MoveIt Pro Docker Compose file to the user workspace Docker Compose file. For any services which require host hardware access, you can map devices from the host into the container in your docker-compose.yaml file like the following example:

services:

base: {}

agent_bridge: {}

drivers: # most likely to need host hardware access
volumes:
- /dev/i2c-9:/dev/i2c-9
- /dev/ttyACM0:/dev/ttyACM0

web_ui: {}

dev:
volumes:
- /dev/i2c-9:/dev/i2c-9
- /dev/ttyACM0:/dev/ttyACM0

Include File Changes

  • The include path for MTC-related code has changed from moveit/task_constructor to moveit_pro/task_constructor. The following bash script will update your workspace:
for file in $(grep -r -l -E 'include ["|<]moveit\/task_constructor'); do
sed -i -E 's/include (["|<])moveit\/task_constructor/include \1moveit_pro\/task_constructor/g' $file
done

Package Name Changes

The following packages were renamed and bash scripts are included below which will automatically apply the renames to your user workspace when run inside of it:

moveit_studio_behavior_interface -> moveit_pro_behavior_interface (do before moveit_studio_behavior)

for file in $(grep -r -l 'moveit_studio_behavior_interface'); do
sed -i 's/moveit_studio_behavior_interface/moveit_pro_behavior_interface/g' $file
done

moveit_studio_behavior -> moveit_pro_behavior

for file in $(grep -r -l 'moveit_studio_behavior'); do
sed -i 's/moveit_studio_behavior/moveit_pro_behavior/g' $file
done

Namespace Changes

  • The C++ namespace moveit_studio::behaviors was changed to moveit_pro::behaviors. The following bash script will update your user workspace:
for file in $(grep -r -l 'moveit_studio::behaviors'); do
sed -i 's/moveit_studio::behaviors/moveit_pro::behaviors/g' $file
done
  • The C++ namespace moveit::task_constructor was changed to moveit_pro::task_constructor. The following bash script will update your user workspace:
for file in $(grep -r -l 'moveit::task_constructor'); do
sed -i 's/moveit::task_constructor/moveit_pro::task_constructor/g' $file
done

Default Value Changes

  • The default value for require_user_approval in the Move to Pose Objective has been changed from true to false. This means that by default, the Objective will execute trajectories without requiring user approval (No Preview mode). If you need the previous behavior where user approval is required, explicitly set require_user_approval="true" in your Objective configuration.

Removed Behaviors

Behavior NameRecommended Replacement
ActivateControllersUse SwitchControllers
AddSubframeToObjectUse PoseStamped-related Behaviors
AddToolToSceneUse AddURDF
AppendOrientationConstraintOrientation constraints are now embedded as input ports in all planning Behaviors
AttachToolUse AttachURDF
DetachToolUse DetachURDF or RemoveURDFFromScene
GenerateObjectsInBoxObjects can be created directly in the simulated environment as needed
GetGraspAndTwistSubframesUse pose-manipulation Behaviors such as PlanCartesianPath or PlanMoveToPose
GetMoveAlongArcSubframesUse pose-manipulation Behaviors such as PlanCartesianPath or PlanMoveToPose
InitializeMotionConstraintsOrientation constraints are now embedded as input ports in all planning Behaviors
LoadObjectiveParametersAll Behavior parameters are now always set as input ports
RemoveToolFromSceneUse DetachURDF or RemoveURDFFromScene
ServoTowardsPoseUse PoseJog
SetupMTCApproachGraspUse SetupMTCMoveAlongFrameAxis
SetupMTCGenerateCuboidGraspsUse GenerateCuboidGraspPoses
SetupMTCGenerateVacuumGraspsUse GenerateVacuumGraspPoses
SetupMTCRetractFromGraspUse SetupMTCMoveAlongFrameAxis
TeleoperateTwistUse PoseJog
TransformPoseFromYamlUse LoadPoseStampedFromYaml with TransformPoseWithPose
WriteCalibratedPoseToYamlUse SaveToYaml

Configuring Joint Jog for Teleoperation

MoveIt Pro 9.0 introduces a new Joint Jog teleoperation mode, which allows users to directly control individual robot joints through the Web UI, with better performance and safety guarantees compared to the previous implementation. To enable this feature in your robot configuration package, you need to add three configuration elements:

Create Joint Jog Configuration File

Create a new file config/moveit/joint_jog.yaml in your robot configuration package:

# Planning groups to use in JointJog, and their corresponding JVC controllers.
# The number of elements in `planning_groups` and `controllers` must match.
planning_groups: ['manipulator']
controllers: ['joint_velocity_controller']

For multi-arm configurations, list all planning groups and their corresponding controllers:

planning_groups: ['left_manipulator', 'right_manipulator']
controllers: ['left_joint_velocity_controller', 'right_joint_velocity_controller']

Reference Joint Jog Config in Main Config

Add the joint_jog parameter to your config/config.yaml under moveit_params:

moveit_params:
# ... existing parameters ...
joint_jog:
package: "your_package_name"
path: "config/moveit/joint_jog.yaml"

Configure Joint Velocity Controller

Add a Joint Velocity Controller configuration to your ros2_control.yaml file. This controller handles the low-level joint command execution with safety limits:

controller_manager:
ros__parameters:
# ... existing controllers ...
joint_velocity_controller:
type: joint_velocity_controller/JointVelocityController

joint_velocity_controller:
ros__parameters:
# Joint group to control
planning_group_name: manipulator
# Maximum joint-space velocities (rad/s) - one value per joint
max_joint_velocity:
- 1.0
- 1.0
- 1.0
- 1.0
- 1.0
- 1.0
# Maximum joint-space accelerations (rad/s²) - one value per joint
max_joint_acceleration:
- 2.0
- 2.0
- 2.0
- 2.0
- 2.0
- 2.0
# Command interface type: "position" or "velocity"
command_interfaces: ["position"]
# Safety margin for joint position limits (radians)
joint_limit_position_tolerance: 0.02
# Timeout after which controller stops if no commands received (seconds)
command_timeout: 0.2
# Controller state publishing rate (Hz)
state_publish_rate: 20

Important: Adjust max_joint_velocity and max_joint_acceleration values based on your robot's capabilities and safety requirements. The values shown are conservative defaults.

Add Controller to Inactive Controllers List

Add the Joint Velocity Controller to controllers_inactive_at_startup in config/config.yaml:

ros2_control:
# ... existing configuration ...
controllers_inactive_at_startup:
- "servo_controller"
- "velocity_force_controller"
- "joint_velocity_controller" # Add this line

This ensures the controller is loaded but not active until teleoperation mode is engaged.

Update your Request Teleoperation Objective to use Joint Jog

If your config overrides the default Request Teleoperation Objective, update it to use the new Joint Jog Behavior instead of the deprecated Servo-based Behavior. For that, replace any instance of TeleoperateJointJog with JointJog, and use SwitchControllers to enable thejoint_velocity_controller when starting teleoperation. Take a look at the default Request Teleoperation Objective for reference.

Notes

  • For general one-arm robots, check out our lab_sim example for reference.
  • For robots with mobile bases, configure command_joints to include platform joints and set command_interfaces: ["velocity"]. See our hangar_sim example for reference.
  • For dual-arm or multi-arm systems, create separate controller instances for each arm with unique names (e.g., left_joint_velocity_controller, right_joint_velocity_controller). See our dual_arm_sim example for reference.
  • The Joint Velocity Controller includes built-in safety features such as joint limit checking, collision avoidance (when enabled), and automatic stopping on command timeout.
  • Once the migration is complete, remove any servo.yaml configurations and references from your robot configuration package, since those are no longer needed.

Migrating GetContourFromPointCloudSlice Parameter

The GetContourFromPointCloudSlice Behavior has renamed its input port from desired_pose_spacing to max_pose_spacing to better reflect its actual behavior. This parameter sets an upper limit on the distance between consecutive waypoints—it adds interpolated waypoints when gaps are too large but preserves existing waypoints that are closer together to maintain contour accuracy.

If you have custom Objectives using this Behavior, update the port name in your XML files:

Replace:

<Action
ID="GetContourFromPointCloudSlice"
desired_pose_spacing="0.1"
...other ports...
/>

With:

<Action
ID="GetContourFromPointCloudSlice"
max_pose_spacing="0.1"
...other ports...
/>

The semantics and default value (0.1 meters) remain unchanged—only the port name has been updated for clarity.

Migrating GetImage, GetCameraInfo, GetPointCloud Parameter

If you have custom Objectives using GetImage, GetCameraInfo, or GetPointCloud Behaviors, rename the timeout_sec port to message_timeout_sec in your XML files.

MPC Name Changes

MPC behaviors (which currently include point cloud clearance, pose tracking, and sphere clearance), along with their header, cpp, and test files are now located under their own mpc folder. To use these behaviors, add the following line to your configuration file:

moveit_pro::behaviors::MPCBehaviorsLoader

Controller Name Changes

We have removed the artificial prepending of slashes in controller names, meaning all controller names should be written as they are defined in the ros2_control config. For example, if your controller is defined as joint_velocity_controller, you should use that exact name in any Behavior taking a controller name, instead of /joint_velocity_controller.

Docker Image Name Changes

  • Docker images specific to the NVIDIA Jetson Orin have changed tags from X.Y.Z-arm64-jetson36.4 to X.Y.Z-jetson-cuda12.6-cudnn9. If you use platform-specific Docker image names in your user workspace, please update accordingly.
  • All Docker image names now include the ROS distribution which they target after the version or branch (e.g. main becomes main-humble). If you manually supply Docker image names in your user workspace (not recommended), please update accordingly.

JTAC as Default Execution Pipeline

MoveIt Pro now uses the Joint Trajectory Admittance Controller (JTAC) as the default execution pipeline for motion objectives. This provides improved force-sensitive trajectory execution capabilities out of the box, while still supporting non-admittance trajectory execution.

Behavior Consolidation

ExecuteTrajectory Behavior

The ExecuteFollowJointTrajectory and ExecuteTrajectoryWithAdmittance Behaviors have been consolidated into a single ExecuteTrajectory Behavior that supports both standard FollowJointTrajectory action servers (JTC) and Joint Trajectory Admittance Controller (JTAC) action servers via an execution_pipeline input port. The default has been changed to "jtac".

Execute MTC Solution Subtree

A new reusable subtree Execute MTC Solution has been introduced to encapsulate controller switching and MTC solution execution. This provides a unified interface for both JTAC and JTC-like controller execution pipelines and exposes all ExecuteMTCSolution behavior parameters for fine-grained control. ExecuteMTCTask is now deprecated in favor of this new subtree.

For convenience, an Execute MTC Solution (JTC) subtree is also available that wraps Execute MTC Solution with execution_pipeline set to "jtc" and appropriate JTC default controller values.

Modified Core Objectives

The following core Objectives have been updated to use JTAC as the default execution pipeline:

Move to Pose

  • Now uses ExecuteMTCSolution behavior instead of ExecuteMTCTask
  • Internally uses the new Execute MTC Solution subtree
  • New input ports: execution_pipeline and controller_action_name
  • Default execution_pipeline set to "jtac"
  • Default controller_action_name set to "/joint_trajectory_admittance_controller/follow_joint_trajectory"
  • Default controller_names set to "joint_trajectory_controller"
  • For convenience, a Move to Pose (JTC) Objective is also available that wraps Move to Pose with execution_pipeline set to "jtc" and appropriate JTC default controller values

Move to Joint State

  • Uses ExecuteTrajectory behavior
  • New input port: execution_pipeline with default value "jtac"
  • Default controller_names set to "joint_trajectory_admittance_controller"
  • Default controller_action_server set to "/joint_trajectory_admittance_controller/follow_joint_trajectory"

Interpolate to Joint State

  • Uses ExecuteTrajectory behavior
  • New input port: execution_pipeline with default value "jtac"
  • Default controller_names set to "joint_trajectory_admittance_controller"
  • Default controller_action_server set to "/joint_trajectory_admittance_controller/follow_joint_trajectory"

Move to Waypoint

  • Uses Move to Joint State subtree internally
  • New input port: execution_pipeline with default value "jtac"
  • Default controller_names set to "joint_trajectory_admittance_controller"
  • Default controller_action_server set to "/joint_trajectory_admittance_controller/follow_joint_trajectory"
  • For convenience, a Move to Waypoint (JTC) Objective is also available that wraps Move to Waypoint with execution_pipeline set to "jtc" and appropriate JTC default controller values

Request Teleoperation

  • Updated to support JTAC execution pipeline
  • New input port: execution_pipeline with default value "jtac"
  • Default controller_action_server set to "/joint_trajectory_admittance_controller/follow_joint_trajectory"
  • Default joint_trajectory_controller_name set to "joint_trajectory_admittance_controller"

Migration for Users Continuing with JTC-like Controllers

If your application still needs to use the ros2_control Joint Trajectory Controller (JTC), or another controller adhering to the ROS2 FollowJointTrajectory action interface, you need to update your custom Objectives as follows:

Migrating ExecuteFollowJointTrajectory

Replace:

<Action
ID="ExecuteFollowJointTrajectory"
execute_follow_joint_trajectory_action_name="{controller_action_server}"
joint_trajectory_msg="{joint_trajectory_msg}"
/>

With:

<Action
ID="ExecuteTrajectory"
execution_pipeline="jtc"
controller_action_name="{controller_action_server}"
joint_trajectory_msg="{joint_trajectory_msg}"
/>

Key changes:

  • Use the new ExecuteTrajectory behavior
  • Set execution_pipeline to "jtc" for standard JTC-like controllers
  • Rename execute_follow_joint_trajectory_action_name to controller_action_name

Migrating ExecuteMTCTask

Replace:

<Action
ID="ExecuteMTCTask"
solution="{solution}"
goal_duration_tolerance="-1.0"
/>

With:

<SubTree
ID="Execute MTC Solution"
solution="{solution}"
execution_pipeline="jtc"
controller_names="joint_trajectory_controller"
controller_action_name="/joint_trajectory_controller/follow_joint_trajectory"
<!-- ... other parameters ... -->
/>

Key changes:

  • Use the new Execute MTC Solution subtree instead of the ExecuteMTCTask behavior
  • Set execution_pipeline to "jtc"
  • Specify appropriate controller names and action name

Overriding Core Objective Defaults

When calling core Objectives, override the following input ports to use JTC instead of JTAC:

Move to Pose:

<SubTree
ID="Move to Pose"
execution_pipeline="jtc"
controller_action_name="/joint_trajectory_controller/follow_joint_trajectory"
controller_names="joint_trajectory_controller"
<!-- ... other parameters ... -->
/>

Move to Joint State:

<SubTree
ID="Move to Joint State"
execution_pipeline="jtc"
controller_action_server="/joint_trajectory_controller/follow_joint_trajectory"
controller_names="joint_trajectory_controller"
<!-- ... other parameters ... -->
/>

Interpolate to Joint State:

<SubTree
ID="Interpolate to Joint State"
execution_pipeline="jtc"
controller_action_server="/joint_trajectory_controller/follow_joint_trajectory"
controller_names="joint_trajectory_controller"
<!-- ... other parameters ... -->
/>

Move to Waypoint:

<SubTree
ID="Move to Waypoint"
execution_pipeline="jtc"
controller_action_server="/joint_trajectory_controller/follow_joint_trajectory"
controller_names="joint_trajectory_controller"
<!-- ... other parameters ... -->
/>

Request Teleoperation:

<SubTree
ID="Request Teleoperation"
execution_pipeline="jtc"
controller_action_server="/joint_trajectory_controller/follow_joint_trajectory"
joint_trajectory_controller_name="joint_trajectory_controller"
<!-- ... other parameters ... -->
/>

Migration for Users Adopting JTAC

To use JTAC, you must first configure a Joint Trajectory Admittance Controller in your robot configuration package. See the Configure Admittance Controller documentation for detailed setup instructions.

Once the JTAC controller is configured, you can use the default values in the core Objectives that you use, or update the controller names and action server names as needed.

Migrating ExecuteTrajectoryWithAdmittance

If you have custom Objectives using ExecuteTrajectoryWithAdmittance, replace:

<Action
ID="ExecuteTrajectoryWithAdmittance"
execute_trajectory_with_admittance_action_name="{controller_action_server}"
joint_trajectory_msg="{joint_trajectory_msg}"
admittance_parameters_msg="{admittance_parameters}"
/>

With:

<Action
ID="ExecuteTrajectory"
execution_pipeline="jtac"
controller_action_name="{controller_action_server}"
joint_trajectory_msg="{joint_trajectory_msg}"
admittance_parameters_msg="{admittance_parameters}"
/>

Key changes:

  • Use the new ExecuteTrajectory behavior
  • Set execution_pipeline to "jtac" for JTAC controllers
  • Rename execute_trajectory_with_admittance_action_name to controller_action_name

Customizing Admittance Parameters

To customize admittance behavior, you can pass additional parameters to the Execute MTC Solution subtree or ExecuteTrajectory behavior:

<SubTree
ID="Execute MTC Solution"
solution="{your_mtc_solution}"
execution_pipeline="jtac"
controller_names="joint_trajectory_admittance_controller"
controller_action_name="/joint_trajectory_admittance_controller/follow_joint_trajectory"
admittance_parameters_msg="{your_admittance_params}"
goal_position_tolerance="0.01"
path_position_tolerance="0.02"
absolute_force_torque_threshold="{your_force_limits}"
<!-- ... other parameters ... -->
/>

Controller Configuration Update

The joints and base_frame parameters have been removed from joint_trajectory_admittance_controller and velocity_force_controller. These are now derived automatically from the planning_group_name parameter.

Steps:

  1. Remove the joints parameter and its list of joint names
  2. Remove the base_frame parameter
  3. Add planning_group_name set to your robot's planning group

The controller will now automatically determine the joints and base frame from the planning group configuration.

For example: Before joint_trajectory_admittance_controller: ros__parameters: joints:

  • shoulder_pan_joint
  • shoulder_lift_joint
  • elbow_joint

other joints

base_frame: base_link sensor_frame: tool0 ee_frame: tool0

... other parameters

After joint_trajectory_admittance_controller: ros__parameters: planning_group_name: manipulator sensor_frame: tool0 ee_frame: tool0

... other parameters