Skip to content
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 it possible to start a roscore using rospypi from Python code? #62

Open
jelledouwe opened this issue Feb 17, 2022 · 3 comments
Open

Comments

@jelledouwe
Copy link

First of all, I admire the project! I was wondering whether it is possible to start a roscore from code using rospypi.
This is possible using standard rospy (taken from https://answers.ros.org/question/215600/how-can-i-run-roscore-from-python/):

import roslaunch
uuid = roslaunch.rlutil.get_or_generate_uuid(options_runid=None, options_wait_for_master=False)
roslaunch.configure_logging(uuid)
launch = roslaunch.parent.ROSLaunchParent(uuid, roslaunch_files=[], is_core=True)
launch.start()
#  --- your code ---
launch.shutdown()

Is something similar also possible using rospypi?

@bonprosoft
Copy link
Member

It seems the code doesn't work with the current version of rospypi:

Traceback (most recent call last):
  File "hoge.py", line 5, in <module>
    launch.start()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/parent.py", line 305, in start
    self._start_infrastructure()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/parent.py", line 254, in _start_infrastructure
    self._load_config()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/parent.py", line 156, in _load_config
    self.config = roslaunch.config.load_config_default(self.roslaunch_files, self.port,
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/config.py", line 451, in load_config_default
    load_roscore(loader, config, verbose=verbose)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/config.py", line 92, in load_roscore
    f_roscore = get_roscore_filename()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/config.py", line 84, in get_roscore_filename
    return os.path.join(r.get_path('roslaunch'), 'resources', 'roscore.xml')
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/rospkg/rospack.py", line 207, in get_path
    raise ResourceNotFound(name, ros_paths=self._ros_paths)
rospkg.common.ResourceNotFound: roslaunch

This is because roslaunch/resources files, which are specified in CMakeLists.txt, are not included in our distributed files.
https://github.com/ros/ros_comm/tree/f5fa3a168760d62e9693f10dcb9adfffc6132d22/tools/roslaunch/resources

According to the original source code, you can avoid this eror by specifying ROS_ETC_DIR (src), although I encountered another error:

WARNING: cannot load logging configuration file, logging is disabled
... logging to /home/igarashi/.ros/log/675733be-9526-11ec-b01f-c79dd9cfc6e3/roslaunch-yinano-42878.log
Traceback (most recent call last):
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 271, in _param_tag
    value = self.param_value(verbose, name, ptype, *vals)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/loader.py", line 543, in param_value
    raise ValueError("Cannot load command parameter [%s]: command [%s] returned with code [%s]"%(name, command, p.returncode))
ValueError: Cannot load command parameter [rosversion]: command [['rosversion', 'roslaunch']] returned with code [1]

During handling of the above exception, another exception occurred:

Traceback (most recent call last):
  File "hoge.py", line 5, in <module>
    launch.start()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/parent.py", line 305, in start
    self._start_infrastructure()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/parent.py", line 254, in _start_infrastructure
    self._load_config()
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/parent.py", line 156, in _load_config
    self.config = roslaunch.config.load_config_default(self.roslaunch_files, self.port,
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/config.py", line 451, in load_config_default
    load_roscore(loader, config, verbose=verbose)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/config.py", line 94, in load_roscore
    loader.load(f_roscore, config, core=True, verbose=verbose)    
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 761, in load
    self._load_launch(launch, ros_config, is_core=core, filename=filename, argv=argv, verbose=verbose)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 733, in _load_launch
    self._recurse_load(ros_config, launch.childNodes, self.root_context, None, is_core, verbose)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 668, in _recurse_load
    self._recurse_load(ros_config, tag.childNodes, child_ns, \
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 679, in _recurse_load
    self._param_tag(tag, context, ros_config, verbose=verbose)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 96, in call
    return f(*args, **kwds)
  File "/home/igarashi/projects/simple/venv/lib/python3.8/site-packages/roslaunch/xmlloader.py", line 285, in _param_tag
    raise XmlParseException(
roslaunch.xmlloader.XmlParseException: Invalid <param> tag: Cannot load command parameter [rosversion]: command [['rosversion', 'roslaunch']] returned with code [1]. 

Param xml is <param name="rosversion" command="rosversion roslaunch"/>

(The error means rosversion roslaunch doesn't work as expected)

There may be some other errors to get it working, but let me think a workaround for those problems.

@bonprosoft
Copy link
Member

bonprosoft commented Feb 24, 2022

It seems rospkg, roslaunch and other tools tightly depend on the ROS package directory structure.
As installing the rospypi packages doesn't create that directory structure under the python package directory, IMO it seems difficult to work with the code you posted. cc: @otamachan

https://github.com/ros-infrastructure/rospkg/blob/dbed1cfb80ef42f8e982e729922002bcf3b801bf/src/rospkg/rospack.py#L61-L99

However, roscore was launched successfully by avoiding the configuration loader part.
The following code works in my environment:

import roslaunch
from roslaunch.config import ROSLaunchConfig
from roslaunch.core import Param
from roslaunch.parent import ROSLaunchParent
from roslaunch.rlutil import get_or_generate_uuid

uuid = get_or_generate_uuid(options_runid=None, options_wait_for_master=False)
roslaunch.configure_logging(uuid)

launch = ROSLaunchParent(uuid, roslaunch_files=[], is_core=True)

# Set ROSLaunchConfig to avoid using rospkg
config = ROSLaunchConfig()
# The following parameters are required as some processes use them:
# e.g. https://github.com/ros/ros_comm/blob/f5fa3a168760d62e9693f10dcb9adfffc6132d22/tools/roslaunch/src/roslaunch/parent.py#L194
config.params["/rosversion"] = Param("/rosversion", "1.15.13")
config.params["/rosdistro"] = Param("/rosdistro", "noetic")
config.assign_machines()
launch.config = config

launch.start()
input("Press Enter to shutdown")
launch.shutdown()

memo

  • To include resources files in our binaries, specify data_files for setuptools in patched_generate_distutils_setup, which hooks catkin_pkg.python_setup.generate_distutils_setup in our rospy-builder.
    • As the directory exists outside of the package directory, neither MANIFEST.in nor package_data work as expected.

@otamachan
Copy link
Contributor

I think roscore launches rosout node(c++ binary) as well, which is not distributed from this repository. So I think we need some workaround as @bonprosoft suggested.
But if you want to launch just a simple rosmater you can do with a simple script like

import sys
import rosmaster

rosmaster.rosmaster_main([sys.argv[0], "--core"])

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

No branches or pull requests

3 participants