ROS1 (Deprecated)

This is deprecated, however I first learned this while following Madhur Behl’s F1TENTH course.

Why the upgrade to ROS2?

To understand why, check out But the spiel is that everything with ROS1 was developed in-house: discovery, message definition, serialization, and transport. With ROS2, we now have things such as DDS (which are developed by 3rd parties.)

The main worry was that ROS1 was not very secure. ROS2 is built using off-the-shelf open source libraries.


Service calls are bidirectional.

Ros launch files exist to lunch a bunch of nodes, so you don’t have to manually launch it every time. Server

#!/usr/bin/env python
import roslib; roslib.load_manifest('beginner_tutorials')
from beginner_tutorials.srv import *
import rospy
def handle_add_two_ints(req):
    print "Returning [%s + %s = %s]"%(req.a, req.b, (req.a + req.b))
    return AddTwoIntsResponse(req.a + req.b)
def add_two_ints_server():
    s = rospy.Service('add_two_ints', AddTwoInts, handle_add_two_ints)
    print "Ready to add two ints."
if __name__ == "__main__":


#!/usr/bin/env python
import roslib; roslib.load_manifest('beginner_tutorials')
import sys
import rospy
from beginner_tutorials.srv import *
def add_two_ints_client(x, y):
        add_two_ints = rospy.ServiceProxy('add_two_ints', AddTwoInts)
        resp1 = add_two_ints(x, y)
        return resp1.sum
    except rospy.ServiceException, e:
        print "Service call failed: %s"%e
def usage():
    return "%s [x y]"%sys.argv[0]
if __name__ == "__main__":
    if len(sys.argv) == 3:
        x = int(sys.argv[1])
        y = int(sys.argv[2])
        print usage()
    print "Requesting %s+%s"%(x, y)
    print "%s + %s = %s"%(x, y, add_two_ints_client(x, y))

Names most be unique in ROS. use queue_size=1 if you always want the freshest data, queue_size=0 actually means infinite queue size, which is really bad.


import rospy
from std_msgs.msg import String
def talker():
	pub = rospy.Publisher('chatter', String, queue_size=10) # 'chatter' is the topic name
	rospy.init_node('talker', anonymous=True)
	rate = rospy.Rate(10) # 10 Hz
	while not rospy.is_shutdown():
		hello_str = "hello world %s" % rospy.get_time()
		rate.sleep() # To ensure that we maintain 10hz
if __name__ == '__main__':
	except rospy.ROSInterruptException:


import rospy
from std_msgs.msg import String
def callback(data):
def listener():
	rospy.init_node('listener', anonymous=True)
	rospy.Subscriber('chatter', String, callback)
	rospy.spin() # Keeps Python from exiting until this node is stopped
if __name__ == '__main__':

Catkin is the ROS build system

  • The set of tools that ROS uses to generate executable programs, libraries and interfaces

catkin = CMake + X

Two mandatory files:

  • package.xml
  • CMAKEList.txt
mkdir ~/catkin_ws/src
cd ~/catkin_ws/src
cd ~/catkin_ws
catkin_make # Build the workspace and all the packages within it, ALWAYS do it in ~/
source ./devel/
catkin clean # Clean the entire build and devel space
# Afterwards, for ros, super useful commands
rospack find roscpp # get the directory
rospack depends turtlesim # print the dependencies
roscd turtlesim/
rosls turtlesim/

Ros code is grouped at two different levels:

  • Packages
  • Stacks
    • Stack = collection of packages (ex: Perception Stack)
  • Distribution = Collection of stacks
Give permissions
cd ~/catkin_ws
find . -name “*.py” -exec chmod +x {} \; # This DOESNT WORK
source ~/catkin_ws/devel/setup.bash
Basic Commands
roscore # Start ROS and create the Master
# rosrun package_name node_name
rosrun turtlesim turtlesim_node
rosnode list
rosnode info /turtlesim # Learn more about a particular node
rostopic list -v # List of topics
rostopic info /turtle1/pose 
rostopic type /turtle1/pose 
rosmsg show turtlesim/Pose 
rostopic echo /turtle1/pose # show the messages of a particular topic
rostopic pub -1 /turtle1/cmd_vel geometry_msgs/Twist # Publishing to a topic manually
rosservice call /reset
rosservice call /turtle1/teleport_absolute 1 1 0
rosrun rqt_graph rqt_graph
rosnode kill /node_name # This is better than Ctrl-C, there might be dead nodes, 
rosnode cleanup