RabbitMQインストールからPub/Sub機能チュートリアルまで

## RabbitMQとは

> RabbitMQ(ラビットエムキュー)は、Advanced Message Queuing Protocol(AMQP)を使用した、オープンソースのメッセージ指向ミドルウェアである。
RabbitMQ Serverは、Erlang言語で記述されており、クラスタリングとフェイルオーバーのためにOpen Telecom Platformフレームワークで構築されている。(https://ja.wikipedia.org/wiki/RabbitMQ)

## GitHub

https://github.com/rabbitmq/rabbitmq-server

## Install Erlang
RabbitMQはErlangが使われているため、まずErlangをインストールする。

```zsh
$ wget http://packages.erlang-solutions.com/erlang-solutions-1.0-1.noarch.rpm
$ rpm -Uvh erlang-solutions-1.0-1.noarch.rpm
$ yum install erlang
# Verify your installation of Erlang
$ erl
Erlang/OTP 20 [RELEASE CANDIDATE 2] [erts-9.0] [source] [64-bit] [smp:1:1] [ds:1:1:10] [async-threads:10] [hipe] [kernel-poll:false]

Eshell V9.0  (abort with ^G)
1>
```

## Install RabbitMQ

```zsh
$ wget http://www.rabbitmq.com/releases/rabbitmq-server/v3.6.10/rabbitmq-server-3.6.10-1.el7.noarch.rpm
$ rpm --import https://www.rabbitmq.com/rabbitmq-signing-key-public.asc
$ yum install rabbitmq-server-3.6.10-1.el7.noarch.rpm
```

## start the RabbitMQ server

```zsh
$ systemctl start rabbitmq-server.service
$ systemctl enable rabbitmq-server.service

# check the status of RabbitMQ
$ rabbitmqctl status

# Enable and use the RabbitMQ management console
$ rabbitmq-plugins enable rabbitmq_management
$ chown -R rabbitmq:rabbitmq /var/lib/rabbitmq/
```

## add an user

* {username}: new user's name
* {pw} : the new user's password

```zsh
$ rabbitmqctl add_user #{username} #{pw}
$ rabbitmqctl set_user_tags #{username} administrator
$ rabbitmqctl set_permissions -p / #{username} ".*" ".*" ".*"
```

## visit the RabbitMQ Management tool via web browser

http://[your-rabbitMQ-server-IP]:15672/

問題なければ以下のログイン画面が表示される。

![20170626183636.png](https://qiita-image-store.s3.amazonaws.com/0/33166/a3862eff-a550-0b39-24af-441773cdcb80.png)

先ほど作成したusername, passwordの組み合わせでログインすることができる。

## ここからTutorial

rubyで Pub/Sub を試す。以下の流れ。

1. クライアント(Subscriber)1, 2は、"logs" チャネルをSubscribeする。
1. クライアント3(Publisher)から"logs" チャネルへメッセージをpublishする。
1. クライアント1,2 でクライアント3から発信されたメッセージを受信できることを確認する。

### install bunny via gem

```zsh
$ yum install rubygems
$ gem install bunny --version ">= 2.6.4"
```

### create a receive_logs.rb

```ruby
#!/usr/bin/env ruby
# encoding: utf-8

require "bunny"

conn = Bunny.new(:automatically_recover => false)
conn.start

ch  = conn.create_channel
x   = ch.fanout("logs")
q   = ch.queue("", :exclusive => true)

q.bind(x)

puts " [*] Waiting for logs. To exit press CTRL+C"

begin
  q.subscribe(:block => true) do |delivery_info, properties, body|
    puts " [x] #{body}"
  end
rescue Interrupt => _
  ch.close
  conn.close

  exit(0)
end
```

### create emit_log.rb

```ruby
#!/usr/bin/env ruby
# encoding: utf-8

require "bunny"

conn = Bunny.new(:automatically_recover => false)
conn.start

ch   = conn.create_channel
x    = ch.fanout("logs")

msg  = ARGV.empty? ? "Hello World!" : ARGV.join(" ")

x.publish(msg)
puts " [x] Sent #{msg}"

conn.close
```

### クライアント1, 2それぞれを購読状態にする

```zsh
$ ruby receive_logs.rb
 [*] Waiting for logs. To exit press CTRL+C
```

### クライアント3(Publisher) からメッセージを送信する

```zsh
$ ruby emit_log.rb
 [x] Sent Hello World!
$ ruby emit_log.rb 'this is test message!'
 [x] Sent this is test message!
```

すると、クライアント2, 3の画面上に、メッセージが表示(受信)される

```zsh
$ ruby receive_logs.rb
 [*] Waiting for logs. To exit press CTRL+C
 [x] Hello World!
 [x] this is test message!
```


## references

* [https://www.vultr.com/docs/how-to-install-rabbitmq-on-centos-7:title]
* [http://www.rabbitmq.com/getstarted.html:title]
* tutorial 関連
  * php: http://www.rabbitmq.com/tutorials/tutorial-one-php.html
  * ruby: http://www.rabbitmq.com/tutorials/tutorial-one-ruby.html
  * github(sample code): https://github.com/rabbitmq/rabbitmq-tutorials