偶然發現了這個gearman,覺得這玩意兒挺好用,非常適合PHP運行一部分業務。
話不多說,安裝一下。
使用apt查找
sudo apt search gearman
找到了這個
gearman/bionic,bionic 1.1.18+ds-1 all Distributed job queue
好,開始安裝
sudo apt-get install gearman
好,安裝完成,然後查看是否運行
ps -ef |grep gearman
發現有在運行
$ ps -ef |grep gearman gearman 1660 1 0 02:54 ? 00:00:00 /usr/sbin/gearmand --pid-file=/run/gearman/gearmand.pid --listen=localhost --daemon --log-file=/var/log/gearman-job-server/gearmand.log vagrant 2310 1452 0 02:54 pts/0 00:00:00 grep --color=auto gearman
好,然後開始安裝php的擴展(因爲我PHP版本是7.4 所以這裏直接查7.4的對應版本擴展了)
$ sudo apt search php7.4-gearman Sorting... Done Full Text Search... Done php7.4-gearman/bionic 2.1.0+1.1.2-5+ubuntu18.04.1+deb.sury.org+1 amd64 PHP wrapper to libgearman
然後開始安裝這個擴展
sudo apt-get install php7.4-gearman
安裝完畢使用php -m過濾一下看看有沒有啓用
$ php -m |grep gearman gearman
發現好了,然後開始建兩個文件
add_job.php
<?php $client = new GearmanClient(); $client->addServer('127.0.0.1', 4730); $res1 = $client->doBackground('runLaterJob', json_encode(array( 'uid' => 'test user id', 'title' => '添加一個需要延時處異步執行的代碼標題', 'body' => '執行這個異步的具體內容', 'sleep_time' => 2, )));
再創建一個 work_job.php
<?php $worker = new GearmanWorker(); $worker->addServer('127.0.0.1', 4730); $worker->addFunction('runLaterJob', function($job) { $data = json_decode($job->workload(), true); if (isset($data['sleep_time']) && $data['sleep_time'] > 0) { sleep($data['sleep_time']);//如果需要延時 就延時處理 } echo "處理任務 uid:{$data['uid']}--title:{$data['title']}--body:{$data['body']} 成功\n"; }); //死循環等待job提交的任務 while($worker->work());
啓動 work_job.php
php work_job.php
屏幕無任何輸出,再啓動 add_job.php
php add_job.php
然後 add_job.php 迅速跑完了,然後看到 work_job.php 2秒後有輸出
處理任務 uid:test user id--title:添加一個需要延時處異步執行的代碼標題--body:執行這個異步的具體內容 成功
這裏我們可以看到,添加job的人投遞任務完畢後可以立刻幹別的事情,由work消費job的人來慢慢的處理業務,這就非常適合用來處理那種訂單延時關閉的處理業務。
比如說,創建訂單後20分鐘內不支付則自動釋放庫存,那麼就可以在創建訂單的時候投遞這樣一個job,然後後續的由消費job在設定的20分鐘後來處理訂單,決定它是否需要釋放庫存(如果需要支付了就不操作任何動作,如果還沒支付,就取消庫存,並把訂單設置爲過期未支付訂單)
以往我們在處理這種業務類型的時候用的是crontab來定時查哪些訂單需要被關閉,哪些訂單需要被釋放庫存,但這樣高度依賴了crontab設定的執行時間的頻率,總不能設定爲1分鐘跑一次吧?如果設定爲10分鐘一次,比如我們設定爲08:00,08:10,08:20等等,就會出現8:00剛跑完定時任務後就下單的用戶,他的訂單創建時間是08:01,那麼對於它而言,08:21分它才應該被關閉,可這個時候08:20的定時任務已經跑完了,那麼這個訂單就在08:30的定時任務被掃到,等於說它實際上等待了29分鐘,這就有了一定程度上的不合理。
而使用這個任務分發,就可以讓它的任務在後臺躺着被自動處理就可以了。