Skip to content

Commit da3222f

Browse files
committed
Python tutorial
1 parent a5a491c commit da3222f

File tree

3 files changed

+337
-0
lines changed

3 files changed

+337
-0
lines changed

python/receive.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
#!/usr/bin/env python
2+
import pika
3+
4+
connection = pika.AsyncoreConnection(pika.ConnectionParameters(
5+
host='127.0.0.1',
6+
credentials=pika.PlainCredentials('guest', 'guest')))
7+
channel = connection.channel()
8+
9+
10+
channel.queue_declare(queue='test')
11+
12+
def callback(ch, method, header, body):
13+
print " [x] Received %.20r" % (body,)
14+
15+
channel.basic_consume(callback,
16+
queue='test',
17+
no_ack=True)
18+
19+
print ' [*] Waiting for messages. To exit press CTRL+C'
20+
pika.asyncore_loop()

python/send.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
#!/usr/bin/env python
2+
import pika
3+
4+
connection = pika.AsyncoreConnection(pika.ConnectionParameters(
5+
host='127.0.0.1',
6+
credentials=pika.PlainCredentials('guest', 'guest')))
7+
channel = connection.channel()
8+
9+
10+
channel.queue_declare(queue='test')
11+
12+
channel.basic_publish(exchange='',
13+
routing_key='test',
14+
body='Hello World!')
15+
print " [x] Sent 'Hello World!'"
16+

python/tutorial-one.md

Lines changed: 301 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,301 @@
1+
<!---
2+
title: Learning RabbitMQ, part 1 (Hello world!)
3+
layout: post
4+
--->
5+
6+
Learning RabbitMQ, part 1 ("Hello world!")
7+
==========================================
8+
9+
<!--
10+
{% dot -Gsize="10,1.3" -Grankdir=LR %}
11+
digraph G {
12+
P1 [label="P", {{ site.dotstyle.producer }}];
13+
Q1 [label="{<s>||||<e>}", {{ site.dotstyle.queue }}];
14+
C1 [label="C", {{ site.dotstyle.consumer }}];
15+
16+
P1 -> Q1 -> C1;
17+
}
18+
{% enddot %}
19+
-->
20+
21+
22+
Throughout this tutorial, we'll teach you the basic concepts required for
23+
creating RabbitMQ applications. The tutorial will be illustrated with
24+
code snippets written in [Python](http://www.python.org/). But don't worry if
25+
you don't know this language - the core ideas are the same for other languages.
26+
27+
This tutorial consists of three parts:
28+
29+
* First we're going to write the simplest possible "Hello World" example.
30+
* Next we'll try to use Rabbit as a simple "Work queue" server.
31+
* Finally, we'll discuss the "Publish-subscribe" pattern.
32+
33+
You need to have RabbitMQ server installed to go throught this tutorial.
34+
If you haven't installed it yet you can follow the [installation instructions](http://www.rabbitmq.com/install.html). You can tell RabbitMQ is installed by checking if the tcp/ip port 5672 is opened. For example if you have installed RabbitMQ you should see something like:
35+
36+
$ nc -vz localhost 5672
37+
localhost [127.0.0.1] 5672 (tcp/amqp) open
38+
39+
40+
<!--
41+
<div class="info" markdown="1">
42+
-->
43+
44+
#### Where to get help
45+
46+
If you’re having trouble going through this tutorial you can post a message to
47+
[rabbitmq-discuss mailing list](https://lists.rabbitmq.com/cgi-bin/mailman/listinfo/rabbitmq-discuss).
48+
49+
<!--
50+
</div>
51+
-->
52+
53+
Introduction
54+
------------
55+
56+
RabbitMQ is a message broker. The principle idea is pretty simple: it accepts
57+
and forwards messages. You can think about it as a post office: when you send
58+
mail to the post box and you're pretty sure that mr postman will eventually
59+
deliver the mail to your recipient. Using this metaphor RabbitMQ is a post box,
60+
post office and a mailman.
61+
62+
The major difference between RabbitMQ and the post office is the fact that it
63+
doesn't deal with the paper, instead it accepts, stores and forwards binary
64+
blobs of data - _messages_.
65+
66+
RabbitMQ uses a weird jargon, but it's simple once you'll get it. For example:
67+
68+
* _Producing_ means nothing more than sending. A program that sends messages
69+
is a _producer_.
70+
<!--
71+
{% dot -Gsize="10,0.3" -Grankdir=LR%}
72+
digraph G {
73+
P1 [label="P", {{ site.dotstyle.producer }}];
74+
}
75+
{% enddot %}
76+
-->
77+
* _A queue_ is the name for a mailbox. It lives inside RabbitMQ.
78+
{% dot -Gsize="10,0.3" -Grankdir=LR%}
79+
<!--
80+
digraph G {
81+
Q1 [label="{<s>||||<e>}", {{ site.dotstyle.queue }}];
82+
}
83+
{% enddot %}
84+
-->
85+
* _Consuming_ has a simmilar meaning to receiving. _Consumer_ is a program
86+
that mostly waits to receive messages.
87+
<!--
88+
{% dot -Gsize="10,0.3" -Grankdir=LR %}
89+
digraph G {
90+
C1 [label="C", {{ site.dotstyle.consumer }}];
91+
}
92+
{% enddot %}
93+
-->
94+
95+
Hello World!
96+
------------
97+
98+
Our first "Hello world" won't be too complex - let's send a message, receive
99+
it and print it on the screen. To do so we need two programs, well, one that
100+
sends a message and one that receives and prints it.
101+
102+
<!--
103+
Our overall design will look like:
104+
{% dot -Gsize="10,0.8" -Grankdir=LR %}
105+
digraph G {
106+
P1 [label="P", {{ site.dotstyle.producer }}];
107+
Q1 [label="{<s>||||<e>}", {{ site.dotstyle.queue }}];
108+
C1 [label="C", {{ site.dotstyle.consumer }}];
109+
110+
P1 -> Q1 -> C1;
111+
}
112+
{% enddot %}
113+
-->
114+
115+
116+
Creating a program
117+
------------------
118+
119+
<!--
120+
<div class="info" markdown="1">
121+
-->
122+
#### RabbitMQ libraries
123+
124+
RabbitMQ speaks AMQP protocol. To use Rabbit you'll need a library that
125+
understands the same protocol as Rabbit. There is a choice of libraries
126+
for almost every programming language. Python it's not different and there is
127+
a bunch of libraries to choose from:
128+
* [py-amqplib](http://barryp.org/software/py-amqplib/)
129+
* [txAMQP](https://launchpad.net/txamqp)
130+
* [pika](http://github.com/tonyg/pika)
131+
132+
In this tutorial we're going to use `pika`. To install it you can use [`pip`](http://pip.openplans.org/) package management tool:
133+
134+
$ sudo pip install -e git://github.com/tonyg/pika.git#egg=pika
135+
136+
If you don't have `pip`, you may want to install it.
137+
138+
* On Ubuntu:
139+
140+
$ sudo apt-get install python-pip
141+
142+
* On Debian:
143+
144+
$ sudo apt-get install python-setuptools
145+
$ sudo easy_install pip
146+
147+
<!--
148+
</div>
149+
-->
150+
151+
### Sending
152+
153+
154+
<!--
155+
{% dot -Gsize="10,0.5" -Grankdir=LR %}
156+
digraph G {
157+
P1 [label="P", {{ site.dotstyle.producer }}];
158+
Q1 [label="{<s>||||<e>}", {{ site.dotstyle.queue }}];
159+
160+
P1 -> Q1;
161+
}
162+
{% enddot %}
163+
-->
164+
165+
Our first program `send.py` will send a single message to the queue.
166+
The first thing we need to do is to connect to RabbitMQ server.
167+
<!--
168+
{% highlight python linenos=true linenostart=1 %}
169+
-->
170+
171+
#!/usr/bin/env python
172+
import pika
173+
174+
connection = pika.AsyncoreConnection(pika.ConnectionParameters(
175+
'127.0.0.1',
176+
credentials = pika.PlainCredentials('guest', 'guest'))
177+
channel = connection.channel()
178+
<!--
179+
{% endhighlight %}
180+
-->
181+
182+
Whenever we send a message we need to make sure the recipient queue exists.
183+
RabbitMQ will just trash the message if can't deliver it. So, we need to
184+
create a queue to which the message will be delivered. Let's name this queue
185+
_test_:
186+
<!--
187+
{% highlight python linenos=true linenostart=8 %}
188+
-->
189+
190+
channel.queue_declare(queue='test')
191+
<!--
192+
{% endhighlight %}
193+
-->
194+
195+
At that point we're ready to send a message. Our first message will contain
196+
a string _Hello World!_. We are going to send it to our _test_ queue:
197+
<!--
198+
{% highlight python linenos=true linenostart=9 %}
199+
-->
200+
201+
channel.basic_publish(exchange='',
202+
routing_key='test',
203+
body='Hello World!')
204+
print " [x] Sent 'Hello World!'"
205+
<!--
206+
{% endhighlight %}
207+
-->
208+
209+
[(full send.py source)](http://github.com/rabbitmq/rabbitmq-tutorials/blob/master/python/send.py)
210+
211+
### Receiving
212+
213+
<!--
214+
{% dot -Gsize="10,0.5" -Grankdir=LR %}
215+
digraph G {
216+
rankdir=LR;
217+
218+
Q1 [label="{<s>||||<e>}", {{ site.dotstyle.queue }}];
219+
C1 [label="C", {{ site.dotstyle.consumer }}];
220+
221+
Q1 -> C1;
222+
}
223+
{% enddot %}
224+
-->
225+
226+
Our second program `receive.py` will receive messages from the queue and print
227+
them on the screen.
228+
229+
The code responsible for connecting to Rabbit is the same as in previous example.
230+
You can copy the first 7 lines.
231+
232+
# ... connection code is the same, copy first 7 lines from send.py ...
233+
234+
Just like before, in the beginning we must make sure that the
235+
queue exists. Creating a queue using `queue_declare` is idempotent - you can
236+
run the command as many times you'd like, and only one queue will be created.
237+
<!--
238+
{% highlight python linenos=true linenostart=8 %}
239+
-->
240+
241+
channel.queue_declare(queue='test')
242+
<!--
243+
{% endhighlight %}
244+
-->
245+
246+
Receiving messages from the queue is a bit more complex. Whenever we receive
247+
a message, a `callback` function is called. In our case
248+
this function will print on the screen the contents of the message.
249+
<!--
250+
{% highlight python linenos=true linenostart=9 %}
251+
-->
252+
253+
def callback(ch, method, header, body):
254+
print " [x] Received %.20r" % (body,)
255+
<!--
256+
{% endhighlight %}
257+
-->
258+
259+
Next, we need to tell RabbitMQ that this particular callback function is
260+
interested in messages from our _test_ queue:
261+
<!--
262+
{% highlight python linenos=true linenostart=11 %}
263+
-->
264+
265+
channel.basic_consume(callback,
266+
queue='test',
267+
no_ack=True)
268+
<!--
269+
{% endhighlight %}
270+
-->
271+
272+
And finally, we enter never-ending loop that waits for data and runs callbacks
273+
whenever necessary.
274+
<!--
275+
{% highlight python linenos=true linenostart=14 %}
276+
-->
277+
278+
print ' [*] Waiting for messages. To exit press CTRL+C'
279+
pika.asyncore_loop()
280+
<!--
281+
{% endhighlight %}
282+
-->
283+
[(full receive.py source)](http://github.com/rabbitmq/rabbitmq-tutorials/blob/master/python/receive.py)
284+
285+
### Putting it all together
286+
287+
Now we can try out our programs. First, let's send
288+
a message using our `send.py` program:
289+
290+
$ python send.py
291+
[x] Sent 'Hello World!'
292+
293+
Let's receive it:
294+
295+
$ python receive.py
296+
[*] Waiting for messages. To exit press CTRL+C
297+
[x] Received 'Hello World!'
298+
299+
Hurray! We were able to send our first message through RabbitMQ. As you might
300+
have noticed, the `receive.py` program haven't exited. It will stay ready to
301+
receive further messages. Try to run `send.py` in new terminal!

0 commit comments

Comments
 (0)