Table of Contents

Migrating to the catkinized version of KnowRob

Starting from ROS hydro/indigo, KnowRob has switched to the catkin buildsystem and the 'new' rosjava. This page explains the steps that are needed for transforming packages that have been built for the old version to the new KnowRob. This page is aimed at maintainers of KnowRob packages that would like to upgrade them from the rosbuild- to the catkin-based version.

Catkinization

As a first step, you can use the 'catkinize' scripts that generates something close to a valid catkin package from your rosbuild packages. The following manual steps are then

Converting Java packages

Rosjava uses the gradle buildsystem that is at the moment (12/2014) only loosely integrated with catkin. Therefore, some information such as dependencies needs to be specified multiple times. Make sure to read the official documentation in the ROS wiki as well as the rosjava_core Sphinx documentation carefully to understand the main concepts first.

Package structure

There is a one-to-many relation between catkin packages and “rosjava sub-projects” as described here. This structure has been adopted in KnowRob: In each KnowRob package that contains Java code, there is a folder with the same name containing the respective rosjava subproject. In case the package requires custom messages, there is another subfolder with the name of the message package. This structure can be created using the tools in rosjava_build_tools. For example, the json_prolog package (depending on the service defined in json_prolog_msgs) looks like this:

  json_prolog_msgs        <-- catkin package
    |- srv
    |- package.xml
    \- ...
    
  json_prolog             <-- catkin package
    |- gradle             <-- gradle wrapper needed for compiling the rosjava code
    |- json_prolog        <-- rosjava subproject
    |     |- src        
    |     \- build.gradle
    |
    |- json_prolog_msgs   <-- rosjava subproject for the custom service definitions
    |     \- build.gradle
    |
    |- build.gradle
    |- gradlew
    |- package.xml
    \- ...

JAR files and build dependencies

Rosjava is now based on Maven that maintains a central repository of jar files for dependencies. The following snippet explains how dependencies are specified in the build.gradle of the respective subproject:

    dependencies {
      /* Dependency on a rosjava project in the same catkin package */ 
      compile project(':json_prolog_msgs')
 
      /* Dependency on a rosjava project in another catkin package */
      compile 'org.ros.rosjava_core:rosjava:[0.1,)'
 
      /* Dependency on external jar files (will be downloaded from mavencentral */
      compile 'net.sf.json-lib:json-lib:2.4:jdk15'
    }

You can use the service at http://gradleplease.appspot.com/ to generate the lines to be put into the build.gradle

Run dependencies when calling Java from Prolog

In the 'normal' case, the classpath for a rosjava node only contains the dependencies of that program itself. With json_prolog, we however have a special case: It serves as launcher for other packages (e.g. knowrob_vis) that may also contain Java code. The classpath therefore needs to contain the Java dependencies of json_prolog itself AND the dependencies of the packages to be launched.

This is not easy with the existing tools: From json_prolog, we launch catkin packages, but the dependencies we need are specified by the rosjava subprojects inside those catkin packages. Since catkin is not aware of these subprojects, it cannot be used to collect the classpath elements from all dependencies. The current workaround is the following: During compilation, gradle creates a file 'classpath.txt' with the classpath elements of the respective package. At runtime, rosprolog and json_prolog collect these files and assemble the overall classpath from them. You need to add the following statement to the build.gradle of the respective (exporting) subproject:

    task writeClasspath << {
        buildDir.mkdirs()
        new File(buildDir, "classpath.txt").text = configurations.runtime.asPath +
                                                  ":" + buildDir + "/libs/" +
                                                  project.name + "-" +
                                                  project.version + ".jar" + "\n"
    }

… and add the writeClasspath task to the CMakeLists.txt:

  catkin_rosjava_setup(installApp publishMavenJavaPublicationToMavenRepository writeClasspath)

Adapting OWL and Prolog files to the new libraries

  owl_parse('package://<ros_pkg_name>/local/path/to/file.owl').
    <launch>
       <param name="initial_package" type="string" value="<pkg_name>" />
       <param name="initial_goal" type="string" value="owl_parse('package://<pkg_name>/owl/file.owl')" />
 
       <node name="json_prolog" pkg="json_prolog" type="json_prolog_node" cwd="node" output="screen" />
    </launch>
 
     $ rosrun rosprolog migrate_owl_iri
 

Changelog

The changes have been ticketed at the knowrob repository for Milestone 1. Please have a look here for a list of changes: https://github.com/knowrob/knowrob/issues?q=is%3Aissue+milestone%3A1.0+