RabbitMQ五种模式

1. 简单模式

在这里插入图片描述
说明:
P:生产者 C:消费者
工作的流程:

  1. 当生产者生产消息后,将消息发往队列.
  2. 当队列中有消息时,消费者会实时的监听队列中的消息.如果有消息则会执行消息

public class TestRabbitMQ_1_simple {

private Connection connection = null;

//定义公共连接
/**
 * 1.定义rabbmq地址 ip:端口
 * 2.定义虚拟主机
 * 3.定义用户名和密码
 * @throws IOException 
 */
@Before
public void init() throws IOException{
	ConnectionFactory connectionFactory = new ConnectionFactory();
	connectionFactory.setHost("192.168.126.146");
	connectionFactory.setPort(5672);
	connectionFactory.setVirtualHost("/jt");
	connectionFactory.setUsername("jtadmin");
	connectionFactory.setPassword("jtadmin");
	
	//获取链接
	connection = connectionFactory.newConnection();
}


//定义生产者
@Test
public void proverder() throws IOException{
	//定义通道Chneel接口
	Channel channel = connection.createChannel();
	
	//定义队列
	/**
	 * queue:队列名称
	 * durable:是否持久化  true 和false
	 * exclusive: 如果为true 表示为生产者独有
	 * autoDelete:当消息消费完成后是否自动删除
	 * arguments:是否传递参数 一般为空
	 */
	channel.queueDeclare("queue_1", false, false, false, null);
	
	//定义发送的消息
	String msg = "我是单工模式";
	
	
	//发送消息
	/**
	 * exchange:交换机名称   如果没有交换机 添加""串
	 * routingKey:路由KEy 信息标识符,没有添加队列名称
	 * props 携带的参数
	 * body.传递信息的字节码文件
	 */
	channel.basicPublish("", "queue_1",null, msg.getBytes());
	
	channel.close();
	connection.close();
}

//定义消费者
@Test
public void consumer() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
	//获取通道
	Channel channel = connection.createChannel();
	//定义队列
	channel.queueDeclare("queue_1", false, false, false, null);
	//定义消费者对象
	QueueingConsumer consumer = new QueueingConsumer(channel);
	//将消费者与队列绑定
	channel.basicConsume("queue_1", true, consumer);
	//循环获取信息
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		
		String msg = new String(delivery.getBody());
		
		System.out.println("获取信息:"+msg);	
	}
	
}

2.工作模式

在这里插入图片描述
说明:
当生产者生产消息时,将消息写入队列中,多个消费者争抢执行,并且实现轮询执行方式.
业务场景:
抢红包的机制/秒杀业务

 public class TestRabbitMQ_2_work {

//工作模式:多个人一起消费一个队列消息.内部轮询机制


/**
 * 1.定义rabbmq地址 ip:端口
 * 2.定义虚拟主机
 * 3.定义用户名和密码
 * @throws IOException 
 */
private Connection connection = null;
@Before
public void init() throws IOException{
	ConnectionFactory connectionFactory = new ConnectionFactory();
	connectionFactory.setHost("192.168.126.146");
	connectionFactory.setPort(5672);
	connectionFactory.setVirtualHost("/jt");
	connectionFactory.setUsername("jtadmin");
	connectionFactory.setPassword("jtadmin");
	
	//获取链接
	connection = connectionFactory.newConnection();
}

@Test
public void provider() throws IOException{
	//定义通道对象
	Channel channel = connection.createChannel();
	
	//定义队列
	channel.queueDeclare("queue_work", false, false, false, null);
	
	//定义广播的消息
	String msg = "我是工作模式";
	
	//发送消息
	channel.basicPublish("", "queue_work", null, msg.getBytes());
	
	//关闭流文件
	channel.close();
	connection.close();
}


//定义消费者
@Test
public void consumer1() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
	//定义通道
	Channel channel = connection.createChannel();
	
	//定义队列
	channel.queueDeclare("queue_work", false, false, false, null);
	
	//定义消费数  每次只能消费一条记录.当消息执行后需要返回ack确认消息 才能执行下一条
	channel.basicQos(1);
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	
	//将队列和消费者绑定  false表示手动返回ack
	channel.basicConsume("queue_work", false, consumer);
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		String msg = new String(delivery.getBody());
		System.out.println("队列A获取消息:"+msg);
		//deliveryTag 队列下标位置
		//multiple是否批量返回
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), true);
	}
}


//定义消费者
	@Test
	public void consumer2() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
		//定义通道
		Channel channel = connection.createChannel();
		
		//定义队列
		channel.queueDeclare("queue_work", false, false, false, null);
		
		//定义消费数  每次只能消费一条记录.当消息执行后需要返回ack确认消息 才能执行下一条
		channel.basicQos(1);
		
		//定义消费者
		QueueingConsumer consumer = new QueueingConsumer(channel);
		
		//将队列和消费者绑定  false表示手动返回ack
		channel.basicConsume("queue_work", false, consumer);
		
		while(true){
			QueueingConsumer.Delivery delivery = consumer.nextDelivery();
			String msg = new String(delivery.getBody());
			System.out.println("队列B获取消息:"+msg);
			//deliveryTag 队列下标位置
			//multiple是否批量返回
			channel.basicAck(delivery.getEnvelope().getDeliveryTag(), true);
		}
	}


	//定义消费者
			@Test
			public void consumer3() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
				//定义通道
				Channel channel = connection.createChannel();
				
				//定义队列
				channel.queueDeclare("queue_work", false, false, false, null);
				
				//定义消费数  每次只能消费一条记录.当消息执行后需要返回ack确认消息 才能执行下一条
				channel.basicQos(1);
				
				//定义消费者
				QueueingConsumer consumer = new QueueingConsumer(channel);
				
				//将队列和消费者绑定  false表示手动返回ack
				channel.basicConsume("queue_work", false, consumer);
				
				while(true){
					QueueingConsumer.Delivery delivery = consumer.nextDelivery();
					String msg = new String(delivery.getBody());
					System.out.println("队列C获取消息:"+msg);
					//deliveryTag 队列下标位置
					//multiple是否批量返回
					channel.basicAck(delivery.getEnvelope().getDeliveryTag(), true);
				}
			}
}

3.发布订阅模式

在这里插入图片描述
说明:
P:生产者
C:消费者
X:交换机
模式:
当采用了发布订阅模式时,当生产者发布了消息,经过交换机发往不同的队列.
这时不同的队列中有相同的消息.一个消息被执行多次
使用场景: 群发 微信公众号订阅

public class TestRabbitMQ_3_publish {

 //发布订阅模式
  private Connection connection = null;

//定义rabbit连接池
@Before
public void initConnection() throws IOException{
	//定义工厂对象
	ConnectionFactory connectionFactory = new ConnectionFactory();
	//设定参数
	connectionFactory.setHost("192.168.126.146");
	connectionFactory.setPort(5672);
	connectionFactory.setVirtualHost("/jt");
	connectionFactory.setUsername("jtadmin");
	connectionFactory.setPassword("jtadmin");
	
	//创建连接
	connection = connectionFactory.newConnection();	
}



//定义生产者
@Test
public void  proverder() throws IOException{
	//定义通道
	Channel channel = connection.createChannel();
	
	//定义交换机名称
	String exchange_name = "E1";
	
	
	//定义发布订阅模式    fanout    redirect 路由模式    topic 主题模式
	channel.exchangeDeclare(exchange_name, "fanout");
	
	for(int i=0;i<10; i++){
		String msg = "发布订阅模式"+i;
		channel.basicPublish(exchange_name, "", null, msg.getBytes());
	}
	
	channel.close();
	connection.close();
}


/**
 * 消费者需要定义队列名称  并且与交换机绑定
 * @throws IOException
 * @throws InterruptedException 
 * @throws ConsumerCancelledException 
 * @throws ShutdownSignalException 
 */
@Test
public void consumer1() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
	Channel channel = connection.createChannel();
	
	String exchange_name = "E1";
	String queue_name = "c_1";
	
	//定义交换机模式
	channel.exchangeDeclare(exchange_name, "fanout");
	
	//定义队列
	channel.queueDeclare(queue_name, false, false, false, null);
	
	//将队列和交换机绑定
	channel.queueBind(queue_name, exchange_name, "");
	
	//定义消费数量 
	channel.basicQos(1);
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	
	//将消费者和队列绑定,并且需要手动返回
	channel.basicConsume(queue_name, false, consumer);
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		
		String msg = "发布订阅模式-消费者1"+new String(delivery.getBody());
		System.out.println(msg);
		
		//false表示一个一个返回
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);
	}
}


/**
 * 消费者需要定义队列名称  并且与交换机绑定
 * @throws IOException
 * @throws InterruptedException 
 * @throws ConsumerCancelledException 
 * @throws ShutdownSignalException 
 */
@Test
public void consumer2() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
	Channel channel = connection.createChannel();
	
	String exchange_name = "E1";
	String queue_name = "c_2";
	
	//定义交换机模式
	channel.exchangeDeclare(exchange_name, "fanout");
	
	//定义队列
	channel.queueDeclare(queue_name, false, false, false, null);
	
	//将队列和交换机绑定
	channel.queueBind(queue_name, exchange_name, "");
	
	channel.basicQos(1);
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	
	//定义回复方式
	channel.basicConsume(queue_name, false, consumer);
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		
		String msg = "发布订阅模式-消费者2"+new String(delivery.getBody());
		System.out.println(msg);
		
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);
	}

}

}

路由模式

在这里插入图片描述
说明:路由模式是发布订阅模式的升级版.根据不同的路由key实现消息的发送.
作用:
可以根据功能模块的业务不同,发往不同的队列中.

代码:
public class TestRabbitMQ_4_redirect {
//发布订阅模式
private Connection connection = null;

//定义rabbit连接池
@Before
public void initConnection() throws IOException{
	//定义工厂对象
	ConnectionFactory connectionFactory = new ConnectionFactory();
	//设定参数
	connectionFactory.setHost("192.168.126.146");
	connectionFactory.setPort(5672);
	connectionFactory.setVirtualHost("/jt");
	connectionFactory.setUsername("jtadmin");
	connectionFactory.setPassword("jtadmin");
	//创建连接
	connection = connectionFactory.newConnection();	
}



//定义生产者
@Test
public void  proverder() throws IOException{
	Channel channel = connection.createChannel();
	
	//定义交换机名称
	String exchange_name = "redirect";
	
	
	//定义发布订阅模式    fanout    direct 路由模式    topic 主题模式
	channel.exchangeDeclare(exchange_name, "direct");
	
	for(int i=0;i<10; i++){
		String msg = "生产者发送消息"+i;
		String rontKey = "1707B";
		
		/**
		 * exchange:交换机名称
		 * routingKey:路由key
		 * props:参数
		 * body:发送消息
		 */
		channel.basicPublish(exchange_name, rontKey, null, msg.getBytes());
	}
	
	channel.close();
	connection.close();
}

/**
 * 消费者需要定义队列名称  并且与交换机绑定
 * @throws IOException
 * @throws InterruptedException 
 * @throws ConsumerCancelledException 
 * @throws ShutdownSignalException 
 */
@Test
public void consumer1() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
	
	//定义通道
	Channel channel = connection.createChannel();
	
	//定义交换机名称
	String exchange_name = "redirect";
	
	//定义队列名称
	String queue_name = "c_r_1";
	
	//定义交换机模式
	channel.exchangeDeclare(exchange_name, "direct");
	
	//定义队列
	channel.queueDeclare(queue_name, false, false, false, null);
	
	//将队列和交换机绑定
	/**
	 * 参数介绍:
	 * 	queue:队列名称
	 *  exchange:交换机名称
	 *  routingKey:路由key
	 */
	//channel.queueBind(queue, exchange, routingKey)
	channel.queueBind(queue_name, exchange_name, "1707A");
	
	//定义消费个数
	channel.basicQos(1);
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	
	//绑定消息与消费者
	channel.basicConsume(queue_name, false, consumer);
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		
		String msg = "路由模式-消费者1"+new String(delivery.getBody());
		System.out.println(msg);
		
		//手动回复 一个一个回复
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);
	}

}


/**
 * 消费者需要定义队列名称  并且与交换机绑定
 * @throws IOException
 * @throws InterruptedException 
 * @throws ConsumerCancelledException 
 * @throws ShutdownSignalException 
 */
@Test
public void consumer2() throws IOException, ShutdownSignalException, ConsumerCancelledException, InterruptedException{
	Channel channel = connection.createChannel();
	
	String exchange_name = "redirect";
	String queue_name = "c_r_2";
	
	//定义交换机模式
	channel.exchangeDeclare(exchange_name, "direct");
	
	//定义队列
	channel.queueDeclare(queue_name, false, false, false, null);
	
	//将队列和交换机绑定
	channel.queueBind(queue_name, exchange_name, "1707B");
	
	channel.basicQos(1);
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	
	//定义回复方式
	channel.basicConsume(queue_name, false, consumer);
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		
		String msg = "路由模式-消费者2"+new String(delivery.getBody());
		System.out.println(msg);
		
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);
	}
}

}

主题模式

在这里插入图片描述
说明:
主题模式是路由模式的升级版,只要满足条件的路由key,都可以接收消息.
通配符的格式:
号:匹配一个或一组字符(以.分割)
#号.能够匹配任意的字符.
例子:
Item.update.aabb item.# 可以匹配
Item.update item.# item.
都可以匹配
代码:
//主题模式
public class TestRabbitMQ_5_topic {

private Connection connection = null;

@Before
public void initConnection() throws IOException{
	//1.定义ConnectionFactory对象
	ConnectionFactory connectionFactory = new ConnectionFactory();
	connectionFactory.setHost("192.168.126.146");
	connectionFactory.setPort(5672);
	connectionFactory.setVirtualHost("/jt");
	connectionFactory.setUsername("jtadmin");
	connectionFactory.setPassword("jtadmin");	
	//获取连接
	connection = connectionFactory.newConnection();	
}

//定义生产者
@Test
public void proverder() throws Exception{
	//获取通道
	Channel channel = connection.createChannel();
	
	//定义交换机的名称
	String exchange_name = "TOP";
	
	//创建交换机队列   
	//exchange  交换机名称
	//type 定义类型 fanout 发布订阅模式   direct-路由模式    topic-主题模式
	channel.exchangeDeclare(exchange_name, "topic");  //主题模式
	
	for (int i = 0; i < 100; i++) {
		
		String msg = "主题模式"+i;
		
		/**
		 * 参数说明:
		 * 	exchange:交换机名称
		 *  routingKey:路由key
		 *  props:参数
		 *  body:数据字节码
		 */
		//channel.basicPublish(exchange, routingKey, props, body);
		channel.basicPublish(exchange_name,"item.update", null, msg.getBytes());
	}
	channel.close();
	connection.close();
}

@Test
public  void consumer1() throws Exception{
	
	//定义通道
	Channel channel = connection.createChannel();
	
	//定义交换机名称
	String exchange_name = "TOP";
	
	//定义队列名称
	String queue_name = "TOP1";
	
	//声明交换机名称以及主题模式
	channel.exchangeDeclare(exchange_name, "topic");
	
	//定义队列
	channel.queueDeclare(queue_name, false, false, false, null);
	
	//将交换机和队列进行绑定   
	//参数1.队列名称     参数2交换机名称   参数3 路由key  #号匹配多个字符
	channel.queueBind(queue_name, exchange_name, "item.#");
	
	channel.basicQos(1);  //定义消费数量  1
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	
	//将队列和消费者绑定
	channel.basicConsume(queue_name, false, consumer);  //定义手动回复
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		//获取消息队列中的数据
		String msg = new String(delivery.getBody());
		System.out.println("item.#消费者1:"+msg);
		
		//手动回复
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);	
	}
}


@Test
public  void consumer2() throws Exception{
	Channel channel = connection.createChannel();
	String exchange_name = "TOP";
	String queue_name = "TOP2";
	//生命交换机模式
	channel.exchangeDeclare(exchange_name, "topic");
	//定义队列
	channel.queueDeclare(queue_name, false, false, false, null);
	//将交换机和队列进行绑定   
	//参数1.队列名称     参数2交换机名称     参数3定义路由key
	channel.queueBind(queue_name, exchange_name, "item.*");
	
	channel.basicQos(1);  //定义消费数量  1
	
	//定义消费者
	QueueingConsumer consumer = new QueueingConsumer(channel);
	channel.basicConsume(queue_name, false, consumer);  //定义手动回复
	
	while(true){
		QueueingConsumer.Delivery delivery = consumer.nextDelivery();
		//获取消息队列中的数据
		String msg = new String(delivery.getBody());
		System.out.println("item.*消费者2:"+msg);
		//定义回执
		channel.basicAck(delivery.getEnvelope().getDeliveryTag(), false);	
	}
}

}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值