Topic Exchange

此模式下交换机,在推送消息时, 会根据消息的主题词和队列的主题词决定将消息推送到哪个队列. 交换机只会为 Queue 分发符合其指定的主题的消息。

  1. 向交换机发送消息时,消息的 routing key 就是主题关键词,主题词不能随意设置,必须由 "." 联结多个主题词 (如:log.error、log.warn) .
  2. 必须将队列显示的绑定到指定的交换机上.
  3. 为队列指定队列主题词时,可以使用通配符: "#": 表示 0 或多个主题词; "*": 表示 1 个主题词.

示例

producer.php

header('Content-Type: text/html; charset=utf-8');
// 连接设置
$conConfig = [
'host' => '127.0.0.1',
'port' => 5672,
'login' => 'root',
'password' => 'root',
'vhost' => '/'
]; try
{
// RabbitMQ 连接实例
$con = new AMQPConnection($conConfig);
// 发起连接
$con->connect();
// 判断连接结果,true成功,false失败
if(!$con->isConnected())
{
echo '连接失败';die;
}
// 新建通道
$channel = new AMQPChannel($con);
// 在指定通道上新建交换机,如果新建的交换机与已存在交换机重名但属性不同,会产生406错误。如果新建交换机与已存在交换机完全相同,不会有任何影响
$exchange = new AMQPExchange($channel);
// 交换机名称
$exchange->setName('test.topic');
// 交换机类型:按主题分发消息
$exchange->setType('topic');
// 声明交换机
$exchange->declareExchange(); // 发送消息到交换机,通过routing key指定消息的主题词
$state = $exchange->publish('apple', 'fruit.red');
if($state) echo 'Success' . PHP_EOL;
else echo 'Fail' . PHP_EOL; $state = $exchange->publish('cat', 'animal.red');
if($state) echo 'Success' . PHP_EOL;
else echo 'Fail' . PHP_EOL; $con->disconnect();
}
catch(Exception $e)
{
echo $e->getMessage();
}

consumer.php

header('Content-Type: text/html; charset=utf-8');
// 连接设置
$conConfig = [
'host' => '127.0.0.1',
'port' => 5672,
'login' => 'root',
'password' => 'root',
'vhost' => '/'
]; try
{
$connect = new AMQPConnection($conConfig);
$connect->connect();
if(!$connect->isConnected())
{
echo '连接失败';die;
} $channel = new AMQPChannel($connect);
$exchange = new AMQPExchange($channel);
$exchange->setName('test.topic');
$exchange->setType('topic');
$exchange->declareExchange(); // 创建两个队列, 一个关联red主题词, 一个关联animal主题词
$queueRed = new AMQPQueue($channel);
$queueAnimal = new AMQPQueue($channel);
// 队列名称
$queueRed->setName('red.queue');
$queueAnimal->setName('animal.queue');
// 声明队列
$queueRed->declareQueue();
$queueAnimal->declareQueue();
// 为队列绑定主题词, *: 匹配0或多个任意主题词, #: 1个任意主题词. 绑定主题词时, 主题词出现的位置也要匹配
$queueRed->bind('test.topic', "*.red");
$queueAnimal->bind('test.topic', 'animal.#'); echo 'red queue: ' . PHP_EOL;
while($msgEnvelope = $queueRed->get(AMQP_AUTOACK))
{
$msg = $msgEnvelope->getBody();
echo $msg . PHP_EOL;
} echo 'animal queue: ' . PHP_EOL;
while($msgEnvelope = $queueAnimal->get(AMQP_AUTOACK))
{
$msg = $msgEnvelope->getBody();
echo $msg . PHP_EOL;
} $connect->disconnect();
}catch(Exception $e)
{
echo $e->getMessage();
}

运行结果:

red queue 获得了所有包含 red 主题词的消息, animal queue 仅获得包含 animal 主题的消息.

Fanout Exchange

该模式下的交换机是广播模式, 交换机会向所有绑定的队列分发消息, 不需要设置交换机和队列的 routing key. 即使设置了, 也会被忽略.

示例

producer.php

 header('Content-Type: text/html; charset=utf-8');
// 连接设置
$conConfig = [
'host' => '127.0.0.1',
'port' => 5672,
'login' => 'root',
'password' => 'root',
'vhost' => '/'
]; try
{
// RabbitMQ 连接实例
$con = new AMQPConnection($conConfig);
// 发起连接
$con->connect();
// 判断连接结果,true成功,false失败
if(!$con->isConnected())
{
echo '连接失败';die;
}
// 新建通道
$channel = new AMQPChannel($con);
// 在指定通道上新建交换机,如果新建的交换机与已存在交换机重名但属性不同,会产生406错误。如果新建交换机与已存在交换机完全相同,不会有任何影响
$exchange = new AMQPExchange($channel);
// 交换机名称
$exchange->setName('test.fanout');
// 交换机类型:广播模式
$exchange->setType('fanout');
// 声明交换机
$exchange->declareExchange(); for($i = 0; $i < 3; $i++)
{
$msg = '消息';
// 发送消息到交换机,Fanout模式下不需要指定routing key。即使指定也会被忽略
$state = $exchange->publish($msg . $i);
if($state)
{
echo 'Success' . PHP_EOL;
}else
{
echo 'Fail' . PHP_EOL;
}
} $con->disconnect();
}
catch(Exception $e)
{
echo $e->getMessage();
}

consumer.php

 header('Content-Type: text/html; charset=utf-8');
// 连接设置
$conConfig = [
'host' => '127.0.0.1',
'port' => 5672,
'login' => 'root',
'password' => 'root',
'vhost' => '/'
]; try
{
$connect = new AMQPConnection($conConfig);
$connect->connect();
if(!$connect->isConnected())
{
echo '连接失败';die;
} $channel = new AMQPChannel($connect); $exchange = new AMQPExchange($channel);
$exchange->setName('test.fanout');
$exchange->setType('fanout');
$exchange->declareExchange(); // 创建队列
$queue1 = new AMQPQueue($channel);
$queue2 = new AMQPQueue($channel); // 队列名称
$queue1->setName('queue1');
$queue2->setName('queue2');
// 声明队列
$queue1->declareQueue();
$queue2->declareQueue();
// 绑定队列到交换机。Fanout模式下不需要指定routing key,即使指定也会被忽略
$queue1->bind('test.fanout');
echo '队列1: ' . PHP_EOL;
while($msgEnvelope = $queue1->get(AMQP_AUTOACK))
{
$msg = $msgEnvelope->getBody();
echo $msg . PHP_EOL;
} echo PHP_EOL . '队列2: ' . PHP_EOL;
$queue2->bind('test.fanout');
while($msgEnvelope = $queue2->get(AMQP_AUTOACK))
{
$msg = $msgEnvelope->getBody();
echo $msg . PHP_EOL;
}
$connect->disconnect();
}catch(Exception $e)
{
echo $e->getMessage();
}

运行结果:

两个队列获得相同的消息.

PHP 下基于 php-amqp 扩展的 RabbitMQ 简单用例 (二) -- Topic Exchange 和 Fanout Exchange的更多相关文章

  1. PHP 下基于 php-amqp 扩展的 RabbitMQ 简单用例 (一) -- 安装 AMQP 扩展和 Direct Exchange 模式

    Windows 安装 amqp 扩展 RabbitMQ 是基于 amqp(高级消息队列协议) 协议的.使用 RabbitMQ 前必须为 PHP 安装相应的 amqp 扩展. 下载相应版本的 amqp ...

  2. PHP 下基于 php-amqp 扩展的 RabbitMQ 简单用例 (三) -- Header Exchange

    此模式下,消息的routing key 和队列的 routing key 会被完全忽略,而是在交换机推送消息和队列绑定交换机时, 分别为消息和队列设置 headers 属性, 通过匹配消息和队列的 h ...

  3. PHP 下基于 php-amqp 扩展的 RabbitMQ 简单用例 (五) -- 自动 ACK、手动 ACK、NACK

    以 Direct 类型的 交换机和 Queue 的 get 方法为例. producer.php // 连接设置 $conConfig = [ 'host' => '127.0.0.1', 'p ...

  4. PHP 下基于 php-amqp 扩展的 RabbitMQ 简单用例 (四) -- Push API 和 Pull API

    RabbitMQ 中针对消息的分发提供了 Push API (订阅模式) 和 Pull API (主动获取) 两种模式. 在 PHP 中, 这两种模式分别通过 AMQPQueue 类中的 consum ...

  5. Windows下基于python3使用word2vec训练中文维基百科语料(二)

    在上一篇对中文维基百科语料处理将其转换成.txt的文本文档的基础上,我们要将为文本转换成向量,首先都要对文本进行预处理 步骤四:由于得到的中文维基百科中有许多繁体字,所以我们现在就是将繁体字转换成简体 ...

  6. flask框架----基于flask的扩展实现的简单的页面登录

    废话不多说,直接上代码 from flask import Flask,render_template,request,redirect,session app = Flask(__name__,te ...

  7. gtk+3.0的环境配置及基于gtk+3.0的python简单样例

    /*********************************************************************  * Author  : Samson  * Date   ...

  8. memcached学习——常用命令+基于java客户端的3种简单实现(二)

    常用命令: memcached设计的原则就是简单,所以支持的命令也不是特别多~ 1.查看memcached的状态,主要用于分析内存的使用状况.优化内存分配等 stats 查看memcached的运行状 ...

  9. php的amqp扩展 安装(windows) rabbitmq学习篇

    因为RabbitMQ是由erlang语言实现的,所以先要安装erlang环境erlang 下载安装 http://www.erlang.org/download.htmlrabbitmq 下载安装 h ...

随机推荐

  1. python3 + selenum 环境搭建

    一.安装python3 打开python3官网https://www.python.org/,选择下载相应平台版本. 下载完成之后,根绝需要安装.注意:在安装时需勾选左下角“add python to ...

  2. P5071 [Ynoi2015]此时此刻的光辉

    传送门 lxl大毒瘤 首先一个数的因子个数就是这个数的每个质因子的次数+1的积,然后考虑把每个数分解质因子,用莫队维护,然后我交上去就0分了 如果是上面那样的话,我们每一次移动指针的时间复杂度是O(这 ...

  3. 在ios Xcode10下小白都能解决library not found for -libstdc++.6.0.9

    写在前面 library not found for -libstdc++.6.0.9,今天做项目的时候碰到这个问题,解决的过程中遇到了目录路径不对的问题(不在通常的/Applications/Xco ...

  4. VI/VIM修改Tab为4个空格

    配置方法 在当前用户目录下创建或修改~/.vimrc Root用户下修改/etc/virc 和 /etc/vimrc set ts= set softtabstop= set expandtab se ...

  5. That Nice Euler Circuit UVALive - 3263 || 欧拉公式

    欧拉定理: 简单多面体的顶点数V.棱数E及面数F间有关系有著名的欧拉公式:V-E+F=2. 设G为任意的连通的平面图,则v-e+f=2,v是G的顶点数,e是G的边数,f是G的面数.(引) 证明(?) ...

  6. Class.getResourceAsStream()与ClassLoader.getResourceAsStream()获取资源时的路径说明

    Class.getResourceAsStream(): com.xusweeter.iot.ws.vodafone.config.VodafoneServiceConfig.class.getRes ...

  7. Palindromic Subsets 数学 + 线段树

    https://www.hackerrank.com/contests/101hack44/challenges/palindromic-subsets 如果有3个a.2个b.1个c. 每个a看成不同 ...

  8. cloudera-scm-server启动出现Error creating bean with name 'entityManagerFactoryBean'与HHH010003: JDBC Driver class not found: com.mysql.jdbc.Driver错误解决办法(图文详解)

    不多说,直接上干货! 问题详情 -- ::, INFO main:com.cloudera.server.cmf.Main: Starting SCM Server. JVM Args: [-Dlog ...

  9. HashMap和List遍历方法总结及如何遍历删除元素

    https://blog.csdn.net/demohui/article/details/77748809

  10. [POJ1509]Glass Beads 后缀自动机 最小循环串

    题目链接:http://poj.org/problem?id=1509 题目意思就是求循环字符串的最小表示. 我们用字符串S+S建立SAM,然后从root开始走n步,每次尽量选最小的. 由于 SAM ...