rabbitmq的使用
——Javee
RabbitMQ是一套开源(MPL)的消息队列服务软件,是由 LShift 提供的一个 Advanced Message Queuing Protocol (AMQP) 的开源实现,由以高性能、健壮以及可伸缩性出名的 Erlang 写成。
在linux虚拟机下安装好rabbitmq后,使用如下命令启动/关闭:
systemctl start rabbitmq-server
systemctl stop rabbitmq-server
创建rabbitmq用户:
rabbitmqctl add_user admin 123456
rabbitmqctl set_user_tags admin administrator
rabbitmqctl set_permissions -p "/" admin '.*' '.*' '.*'
(修改密码:rabbitmqctl change_password admin '123456'-- 修改pwd->123456)
然后在本机系统浏览器里输入虚拟机ip加端口号:
192.168.184.8:15672 (浏览器输入自己的ip)
登录刚才创建的用户,即可看见管理界面~~~
普通的发送和接收消息:
package com.seecen.rabbitmq.pack1;
import com.rabbitmq.client.*;
import java.io.IOException;
/**
* @Author Javee
* @Date 2019/11/12 13:17
* @Description
*/
/**
* 订阅方...
* 排他队列: 当前连接可用(不同频道也可用,前提是当前连接创建出来的频道)
* 当前连接一段, 就会自动删除的...(不论是否持久,是否自动删除)
*
*/
public class Subscriber {
public static void main(String[] args) throws Exception {
ConnectionFactory factory = new ConnectionFactory();
factory.setVirtualHost("/myhost");
factory.setHost("192.168.184.17");
factory.setUsername("admin");
factory.setPassword("yinwei");
factory.setPort(5672);
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
// 幂等性创建队列... 是否持久 是否排他 是否自动删除
channel.queueDeclare("myQueue", true, false, false, null);
// 设置负载均衡,一次直接收一个任务
channel.basicQos(1);
DefaultConsumer consumer = new DefaultConsumer(channel) {
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
String message = new String(body, "utf-8");
if("a".equals(message)){
try {
Thread.sleep(10 * 1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}else if("b".equals(message)){
try {
Thread.sleep(1 * 1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
System.out.println("收到消息队列中的消息内容为:" + message);
// 手动确认, true代表确认getDeliveryTag以前所有消息
channel.basicAck(envelope.getDeliveryTag(), false);
}
};
channel.basicConsume("myQueue", false, consumer);
}
}
package com.seecen.rabbitmq.pack1;
import com.rabbitmq.client.*;
/**
* @Author Javee
* @Date 2019/11/12 13:17
* @Description
*/
public class Publisher {
public static void main(String[] args) throws Exception {
ConnectionFactory factory = new ConnectionFactory();
factory.setVirtualHost("/myhost");
factory.setHost("192.168.184.17");
factory.setUsername("admin");
factory.setPassword("yinwei");
factory.setPort(5672);
Connection connection = factory.newConnection();
Channel channel = connection.createChannel();
// 幂等性创建队列... 是否持久 是否排他 是否自动删除
channel.queueDeclare("myQueue", true, false, false, null);
//发送消息到mq队列
String message1 = "a";
String message2 = "b";
channel.basicPublish("", "myQueue", null, message1.getBytes());
for (int i = 0; i < 8; i++) {
channel.basicPublish("", "myQueue", null, message2.getBytes());
}
channel.close();
connection.close();
System.out.println("已发送....");
}
}
稍微高级一点,加上exchange:
package com.seecen.rabbitmq;
import com.rabbitmq.client.*;
import org.junit.Before;
import java.io.IOException;
import java.util.concurrent.TimeoutException;
/**
* @Author Javee
* @Date 2019/11/12 14:57
* @Description
*/
public class ConnectMQ {
protected ConnectionFactory factory = new ConnectionFactory();
protected Connection connection = null;
protected Channel channel = null;
@Before
public void init() {
factory.setVirtualHost("/myhost");
factory.setHost("192.168.184.17");
factory.setUsername("admin");
factory.setPassword("yinwei");
factory.setPort(5672);
try{
connection = factory.newConnection();
channel = connection.createChannel();
} catch (TimeoutException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public Consumer myConsumer(){
DefaultConsumer consumer = new DefaultConsumer(channel) {
public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException {
String message = new String(body, "utf-8");
System.out.println(message);
channel.basicAck(envelope.getDeliveryTag(), false);
}
};
return consumer;
}
}
package com.seecen.rabbitmq.pack2;
import com.seecen.rabbitmq.ConnectMQ;
import org.junit.Test;
/**
* @Author Javee
* @Date 2019/11/12 14:56
* @Description 发送消息,有正确口令的接收方才能接受到
* direct:口令相同才收到
* fanout:所有人都可以收到
* topic:口令匹配才收到,类似于正则匹配
*/
public class Publisher extends ConnectMQ {
@Test
public void send() throws Exception{
//幂等性创建交换器
channel.exchangeDeclare("myTopic", "topic");
//发送消息
String message = "这是测试消息";
//设置口令为seecen
channel.basicPublish("myTopic","com.seecen.hello", null, message.getBytes());
channel.close();
connection.close();
}
}
package com.seecen.rabbitmq.pack2;
import com.rabbitmq.client.DefaultConsumer;
import com.seecen.rabbitmq.ConnectMQ;
import org.junit.Test;
/**
* @Author Javee
* @Date 2019/11/12 14:57
* @Description
*/
public class Subscriber extends ConnectMQ {
@Test
public void receive() throws Exception{
//幂等性创建交换器
channel.exchangeDeclare("myTopic", "topic");
//创建一个临时队列(名字是随机生成的类似uuid的不可重复),并返回该队列名称
String queue = channel.queueDeclare().getQueue();
//把该队列绑定到交换器上,并设置口令seecen
channel.queueBind(queue, "myTopic", "com.seecen.*");
//去临时队列中收取消息,有消息的时候执行myConsumer这个对象里面的handleDelivery
channel.basicConsume(queue, false, myConsumer());
//让程序不要结束
System.in.read();
}
}
最后,使用header:
package com.seecen.rabbitmq.pack3;
import com.rabbitmq.client.AMQP;
import com.rabbitmq.client.BuiltinExchangeType;
import com.seecen.rabbitmq.ConnectMQ;
import org.junit.Test;
import java.util.HashMap;
import java.util.Map;
/**
* @Author Javee
* @Date 2019/11/12 17:23
* @Description 用map匹配
*/
public class Publisher extends ConnectMQ {
@Test
public void testHeaderSend() throws Exception{
channel.exchangeDeclare("myHeader", BuiltinExchangeType.HEADERS);
Map<String, Object> map = new HashMap<>();
map.put("token", "yinwei");
AMQP.BasicProperties prop = new AMQP.BasicProperties.Builder()
.headers(map)
.build();
String msg = "这是一条header消息";
channel.basicPublish("myHeader", "", prop, msg.getBytes("utf-8"));
channel.close();
connection.close();
}
}
package com.seecen.rabbitmq.pack3;
import com.rabbitmq.client.BuiltinExchangeType;
import com.seecen.rabbitmq.ConnectMQ;
import org.junit.Test;
import java.util.HashMap;
import java.util.Map;
/**
* @Author Javee
* @Date 2019/11/12 17:23
* @Description
*/
public class Subscriber extends ConnectMQ {
@Test
public void reciveHeader() throws Exception {
channel.exchangeDeclare("myHeader", BuiltinExchangeType.HEADERS);
String queue = channel.queueDeclare().getQueue();
Map<String, Object> map = new HashMap<>();
map.put("token", "yinwei");
channel.queueBind(queue, "myHeader", "", map);
channel.basicConsume(queue, myConsumer());
System.out.println("开始接受header消息");
System.in.read();
}
}