PHP+RabbitMQ

1、下载和安装RabbitMQ

官网Messaging that just works — RabbitMQ

docker pull rabbitmq:3-management

docker run \
 -e RABBITMQ_DEFAULT_USER=用户名 \
 -e RABBITMQ_DEFAULT_PASS=密码 \
 --name mq \
 --hostname mq1 \
 -p 15672:15672 \
 -p 5672:5672 \
 -d \
 rabbitmq:3-management

15672是浏览器访问的端口

5672是应用访问的端口

安装好的界面

 登录后的界面

2、安装rabbitmq-c

wget https://github.com/alanxz/rabbitmq-c/archive/v0.10.0.zip
unzip v0.10.0.zip && cd rabbitmq-c-0.10.0

cmake -DCMAKE_INSTALL_PREFIX=/usr/local/rabbitmq-c

cmake --build . --target install

ln -s /usr/local/rabbitmq-c/lib64 /usr/local/rabbitmq-c/lib

3、安装amqp扩展

PECL :: Package :: amqp

根据PHP的版本来下载 

wget http://pecl.php.net/get/amqp-1.10.0.tgz

tar zxvf amqp-1.10.0.tgz && cd amqp-1.10.0

根据你的PHP版本对应的路径

/www/server/php/74/bin/phpize

./configure --with-php-config=/www/server/php/74/bin/php-config --with-amqp --with-librabbitmq-dir=/usr/local/rabbitmq-c

make && make install

配置php.ini  根据你的扩展安装的路径

extension=/www/server/php/74/lib/php/extensions/no-debug-non-zts-20190902/amqp.so

重启php-fpm或重载配置

查看phpinfo()是否有了amqp

4、PHP代码生产者

简单的一个方法

public function rabbitsend()
    {
        //配置信息 
        $conn_args = array( 
            'host' => 'IP地址',  
            'port' => '5672',  
            'login' => 'RabbitMQ安装时的用户名',  
            'password' => '密码', 
            'vhost'=>'/' 
        ); 
        $exchangeName = 'phpcs';
        $queueName = 'php_queue1';
      
        $routeKey = 'php_queue1';
        $connection = new \AMQPConnection($conn_args);
        $connection->connect() or die("Cannot connect to the broker!\n");
         
        # 连接服务 
        $channel = new \AMQPChannel($connection);
        #  创建交换器
        $exchange = new \AMQPExchange($channel);
        # 设置交换器的名称
        $exchange->setName($exchangeName);
        # 设置多个参数值[setArguments ( array $arguments )];
        # 获取该队列某个参数的信息 , getArgument ( string $key )
        # [如果无法将此交换机的消息路由,则将它们发送到这里指定的备用交换机。(设置“alternate-exchange”参数)。]
        # 设置交换器类型
        # AMQP_EX_TYPE_DIRECT[点对点],AMQP_EX_TYPE_FANOUT[广播],AMQP_EX_TYPE_TOPIC[模糊匹配],AMQP_EX_TYPE_HEADER[头匹配]
        $exchange->setType(AMQP_EX_TYPE_DIRECT);
        # 交换器持久化
        //$exchange->setFlags(AMQP_DURABLE);
        # 执行创建交换器
        $exchange->declareExchange();
        # 创建队列
        $queue = new \AMQPQueue($channel);
        $queue->setName($queueName);
        # 设置单个指定的参数键值,setArgument ( string $key , mixed $value )
        # 获取该队列某个参数的信息 , getArgument ( string $key )
        //$queue->setArgument();
        # [发布到队列中的消息可以在被丢弃之前生存多长时间(毫秒(设置x-message-ttl)参数。]
        # [在自动删除队列(毫秒)之前,该队列不能被使用多长时间。(设置“x-expires”参数)。]
        # [队列中有多少(准备好的)消息[个数],可以在它开始,从其头上删除之前包含。(设置x-max-length长度)参数]
        # [准备好的消息的总大小,队列可以在它开始从头上删除之前包含。(设置x-max-length-bytes 纵向字节)参数]
        # [如果拒绝或过期消息将被重新发布的Exchange的可选名称。(设置“x-dead-letter-exchange”参数,[交换器名,(string)])。]
        # [可选的替换路由密钥,当消息已被写入字母时使用。如果未设置此消息,将使用消息的原始路由密钥。(设置“x-dead-letter-routing-key”参数)。]
        # [支持队列的最大优先级数量;如果未设置,队列将不支持消息优先级。(设置x-max-priority)参数。]
        # [将队列设置为懒惰模式,尽可能保留磁盘上的尽可能多的消息以减少RAM的使用;如果没有设置,队列将保持内存中的缓存以尽可能快地传递消息。(设置“x-queue-mode”参数设置:lazy)。]
        # [将队列设置为主定位模式,确定在节点群集上声明队列主控器所处的规则。(设置x-queue-master-locator 参数。]
        # 设置多个参数值[setArguments ( array $arguments )];
        # 获取该队列所有参数的信息 , getArguments ( void )
        //$queue->setArguments();
        # 持久化队列
        # AMQP_DURABLE[队列持久], AMQP_PASSIVE[返回消息计数], AMQP_EXCLUSIVE[只被一个连接(connection)使用,而且当连接关闭后队列即被删除], AMQP_AUTODELETE[当最后一个消费者退订后即被删除].
        $queue->setFlags(AMQP_DURABLE);
        # 执行创建队列
        $queue->declareQueue();
        //队列绑定到交换器中
        $queue->bind($exchangeName, $routeKey);
        # 开启事务,确保数据真正不丢失
        $channel->startTransaction();
        # 将消息和标识绑定到交换器中
        # publish(message[消息],route_key,[ flags[ AMQP_MANDATORY,AMQP_IMMEDIATE],attributes[array] ]);
        # attributes 存有参数 => [content_type(用于描述MIME类型的编码。例如,对于经常使用的JSON编码,将此属性设置为 “application/json” 是一个很好的做法。),
        #content_encoding,message_id,user_id,app_id,delivery_mode[2 消息持久,1非持久],priority,timestamp,expiration,type,reply_to(主要用于命名一个回调队列 ) ]

        //一次生产100条
        for($i=1;$i<101;$i++)
        {
            
            $message = date("Y-m-d H:i:s") . "Hello PHP:".$i;
            $exchange->publish($message,$routeKey);
             echo $message."<br>";  
        }
        $channel->commitTransaction();
        
         
        # 关闭连接
        $connection->disconnect();

    }

我码的时候遇到一个坑,老是提示“AMQPConnection NOT FOUND”,  AMQPConnection这些方法前加了“\”就好了。此处的单个反斜杠就是表示在当前命名空间内调用全局的方法。

效果就是队列一次生成了100条消息

 RabbitMQ后台可以看到

5、PHP代码消费者

//消费者
    public function rabbituse()
    {
        //配置信息 
        $conn_args = array( 
            'host' => 'IP地址',  
            'port' => '5672',  
            'login' => 'RabbitMQ用户',  
            'password' => '密码', 
            'vhost'=>'/' 
        ); 
        $exchangeName = 'phpcs';
        $queueName = 'php_queue1';
        
        $routeKey = 'php_queue1';
        
        $connection = new \AMQPConnection($conn_args);
        $connection->connect() or die("Cannot connect to the broker!\n");
         
        # 连接服务
        $channel = new \AMQPChannel($connection);
        $exchange = new \AMQPExchange($channel);
        $exchange->setName($exchangeName);
        # 设置交换器类型
        $exchange->setType(AMQP_EX_TYPE_DIRECT);
        # 交换器持久化
        //$exchange->setFlags(AMQP_DURABLE);
        $exchange->declareExchange();
         
        $queue = new \AMQPQueue($channel);
        $queue->setName($queueName);
        $queue->setFlags(AMQP_DURABLE);
        $queue->declareQueue();
         
        # 队列根据routekey 装载消息
        $queue->bind($exchangeName,$routeKey);
        echo "Message:"."<br>";
        $res = $queue->get(AMQP_AUTOACK);
        if($res){
            echo $res->getbody();
        }else{
            echo "队列消息为空";
        }
        

    }

 其实上面2个方法可以整合成类,然后调用,这里为了方便观看和理解就直接写了。

运行效果是这样的

 

后台就被消费了1条消息。 

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值