什麼是訊息佇列,百度百科說,···訊息隊列····是在訊息的傳輸過程中保存訊息的容器。
看著網上林林總總的文章,都說是為了應對高並發,處理數據量超級大的一種數據容器,也可以說是利用各種方式,先把數據存儲在一個···容器·····中,然後,再慢慢從這個容器中取得數據,實現·····非同步操作資料庫·····的方式,以便降低資料庫的壓力。
不管訊息隊列是什麼,個人姑且認為它就是一種儲存資料的···容器···,就這麼簡單明了,呵呵,因為本人對訊息隊列這東西研究的比較膚淺。
不過,在這裡,我還是要賣弄一下一個個人的小實驗代碼,呵呵,假若下面的東西與消息隊列相離太遠,那麼請看官可別見怪哦,因為我上面已經聲明的很清楚了,本人對這東西還是不甚了解,只不過是工作之餘賣弄一下'文采'而已,所以,假如真有誤解消息隊列這個東西,我只能說聲,請你指正我的錯誤,讓筆者迷途知返。
先給出連接mysql資料庫設定檔mysql.ini的內容:
<span style="color: #800000; font-weight: bold">[</span><span style="color: #800000">database</span><span style="color: #800000; font-weight: bold">]</span><span style="color: #000000"> driver </span>=<span style="color: #000000"> mysql host </span>= 127.0.0.1<span style="color: #000000"> port </span>= 3306<span style="color: #000000"> dbname </span>=<span style="color: #000000"> mysql username </span>=<span style="color: #000000"> root password </span>= 1234 <span style="color: #800000; font-weight: bold">[</span><span style="color: #800000">options</span><span style="color: #800000; font-weight: bold">]</span><span style="color: #000000"> PDO::MYSQL_ATTR_INIT_COMMAND </span>= set names utf8
資料表檔案queue.sql的內容:
<span style="color: #008080">--</span><span style="color: #008080"> 消息队列测试</span><span style="color: #008080"> --</span><span style="color: #008080"> 商品表</span> <span style="color: #0000ff">create</span> <span style="color: #0000ff">table</span><span style="color: #000000"> goods( id </span><span style="color: #0000ff">int</span> unsigned <span style="color: #0000ff">primary</span> <span style="color: #0000ff">key</span><span style="color: #000000"> auto_increment, goodsname </span><span style="color: #0000ff">varchar</span>(<span style="color: #800000; font-weight: bold">40</span>) <span style="color: #808080">not</span> <span style="color: #0000ff">null</span> comment <span style="color: #ff0000">'</span><span style="color: #ff0000">商品名</span><span style="color: #ff0000">'</span><span style="color: #000000">, price </span><span style="color: #0000ff">decimal</span>(<span style="color: #800000; font-weight: bold">9</span>,<span style="color: #800000; font-weight: bold">2</span>) <span style="color: #808080">not</span> <span style="color: #0000ff">null</span> comment <span style="color: #ff0000">'</span><span style="color: #ff0000">价格</span><span style="color: #ff0000">'</span><span style="color: #000000">, category_id </span><span style="color: #0000ff">tinyint</span> unsigned <span style="color: #808080">not</span> <span style="color: #0000ff">null</span> comment <span style="color: #ff0000">'</span><span style="color: #ff0000">商品类别id</span><span style="color: #ff0000">'</span><span style="color: #000000">, sort </span><span style="color: #0000ff">tinyint</span> comment <span style="color: #ff0000">'</span><span style="color: #ff0000">商品排序</span><span style="color: #ff0000">'</span><span style="color: #000000">, description </span><span style="color: #0000ff">varchar</span>(<span style="color: #800000; font-weight: bold">255</span>) comment <span style="color: #ff0000">'</span><span style="color: #ff0000">商品描述</span><span style="color: #ff0000">'</span><span style="color: #000000">, remark </span><span style="color: #0000ff">varchar</span>(<span style="color: #800000; font-weight: bold">255</span>) comment <span style="color: #ff0000">'</span><span style="color: #ff0000">备注</span><span style="color: #ff0000">'</span><span style="color: #000000"> )engine InnoDB </span><span style="color: #0000ff">default</span> charset<span style="color: #808080">=</span><span style="color: #000000">utf8; </span><span style="color: #0000ff">insert</span> <span style="color: #0000ff">into</span> goods <span style="color: #0000ff">values</span>(<span style="color: #0000ff">default</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">iPhone5s</span><span style="color: #ff0000">'</span>,<span style="color: #800000; font-weight: bold">5999</span>,<span style="color: #800000; font-weight: bold">1</span>,<span style="color: #800000; font-weight: bold">1</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">美国入口贵重电子产品</span><span style="color: #ff0000">'</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">请多多销售</span><span style="color: #ff0000">'</span>),(<span style="color: #0000ff">default</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">宏基手提电脑1</span><span style="color: #ff0000">'</span>,<span style="color: #800000; font-weight: bold">4888</span>,<span style="color: #800000; font-weight: bold">3</span>,<span style="color: #800000; font-weight: bold">1</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">价格划算好电脑</span><span style="color: #ff0000">'</span>,<span style="color: #0000ff">null</span>),(<span style="color: #0000ff">default</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">f-30绒衣</span><span style="color: #ff0000">'</span>,<span style="color: #800000; font-weight: bold">200</span>,<span style="color: #800000; font-weight: bold">2</span>,<span style="color: #800000; font-weight: bold">1</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">以纯白色厚皮羽绒服</span><span style="color: #ff0000">'</span>,<span style="color: #0000ff">null</span>),(<span style="color: #0000ff">default</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">n-100鞋子</span><span style="color: #ff0000">'</span>,<span style="color: #800000; font-weight: bold">300</span>,<span style="color: #800000; font-weight: bold">4</span>,<span style="color: #800000; font-weight: bold">1</span>,<span style="color: #ff0000">'</span><span style="color: #ff0000">Nick品牌</span><span style="color: #ff0000">'</span>,<span style="color: #0000ff">null</span>);
以下是簡單的訊息佇列實作PDO商品入庫的程式碼:
鄭重提醒:請認真看我的註釋,請認真看我的註釋,請認真看我的註釋。重要的訊息要說三遍,呵呵!
<?<span style="color: #000000">php namespace Home; </span><span style="color: #008080">header</span>('content-type:text/html;charset=utf-8;'<span style="color: #000000">); </span><span style="color: #008000">//</span><span style="color: #008000">引入PDO类</span> <span style="color: #0000ff">use</span><span style="color: #000000"> \PDO; </span><span style="color: #0000ff">use</span><span style="color: #000000"> \PDOStatement; </span><span style="color: #0000ff">use</span><span style="color: #000000"> \PDOException; </span><span style="color: #008000">/*</span><span style="color: #008000">简单消息队列</span><span style="color: #008000">*/</span> <span style="color: #0000ff">class</span><span style="color: #000000"> Queue{ </span><span style="color: #008000">//</span><span style="color: #008000">容器可以是私有,最好是公有</span> <span style="color: #0000ff">static</span> <span style="color: #0000ff">public</span> <span style="color: #800080">$container</span>=<span style="color: #0000ff">array</span><span style="color: #000000">(); </span><span style="color: #008000">//</span><span style="color: #008000">把PDO对象存放到属性中是为了跨方法使用</span> <span style="color: #0000ff">static</span> <span style="color: #0000ff">private</span> <span style="color: #800080">$pdo</span><span style="color: #000000">; </span><span style="color: #008000">//</span><span style="color: #008000">构造函数实现初始化PDO连接数据库</span> <span style="color: #0000ff">public</span> <span style="color: #0000ff">function</span> __construct(<span style="color: #800080">$file</span> = './mysql.ini'){<span style="color: #008000">//</span><span style="color: #008000">mysql数据库的配置文件,./mysql.ini与这个类是同一个目录 //parse_ini_file函数作用,解析并获取ini文件的参数,加true是二维数组</span> <span style="color: #800080">$dbini</span> = <span style="color: #008080">parse_ini_file</span>(<span style="color: #800080">$file</span>,<span style="color: #0000ff">true</span><span style="color: #000000">); </span><span style="color: #800080">$driver</span> = <span style="color: #800080">$dbini</span>['database']['driver'<span style="color: #000000">]; </span><span style="color: #008000">//</span><span style="color: #008000">这里的数据库是mysql的总数据库</span> <span style="color: #800080">$dbname</span> = <span style="color: #800080">$dbini</span>['database']['dbname'<span style="color: #000000">]; </span><span style="color: #800080">$host</span> = <span style="color: #800080">$dbini</span>['database']['host'<span style="color: #000000">]; </span><span style="color: #800080">$port</span> = <span style="color: #800080">$dbini</span>['database']['port'<span style="color: #000000">]; </span><span style="color: #008000">//</span><span style="color: #008000">构造PDO连接数据库的第一个参数,这个参数这么设置纯属是PDO类的语法,不懂的可以百度一下,这里就不做详解了</span> <span style="color: #800080">$dsn</span> = <span style="color: #800080">$driver</span>.':'.'dbname='.<span style="color: #800080">$dbname</span>.';host='.<span style="color: #800080">$host</span>.';port='.<span style="color: #800080">$port</span><span style="color: #000000">; </span><span style="color: #008000">//</span><span style="color: #008000">其他连接数据库参数</span> <span style="color: #800080">$username</span> = <span style="color: #800080">$dbini</span>['database']['username'<span style="color: #000000">]; </span><span style="color: #800080">$password</span> = <span style="color: #800080">$dbini</span>['database']['password'<span style="color: #000000">]; </span><span style="color: #800080">$options</span> = <span style="color: #800080">$dbini</span>['options'];<span style="color: #008000">//</span><span style="color: #008000">初始化设置PDO选项</span> <span style="color: #0000ff">try</span><span style="color: #000000">{ self</span>::<span style="color: #800080">$pdo</span> = <span style="color: #0000ff">new</span> PDO(<span style="color: #800080">$dsn</span>,<span style="color: #800080">$username</span>,<span style="color: #800080">$password</span>,<span style="color: #800080">$options</span><span style="color: #000000">); </span><span style="color: #008000">//</span><span style="color: #008000">设置PDO属性。抛出错误报告</span> self::<span style="color: #800080">$pdo</span>->setAttribute(PDO::ATTR_ERRMODE,PDO::<span style="color: #000000">ERRMODE_EXCEPTION); </span><span style="color: #0000ff">try</span><span style="color: #000000">{ </span><span style="color: #008000">//</span><span style="color: #008000">选择商品数据表所在的数据库</span> self::<span style="color: #800080">$pdo</span>-><span style="color: #008080">exec</span>('use queue'<span style="color: #000000">); }</span><span style="color: #0000ff">catch</span>(PDOException <span style="color: #800080">$e</span><span style="color: #000000">){ </span><span style="color: #0000ff">echo</span> <span style="color: #800080">$e</span>-><span style="color: #000000">getMessage(); } }</span><span style="color: #0000ff">catch</span>(PDOException <span style="color: #800080">$e</span><span style="color: #000000">){ </span><span style="color: #0000ff">echo</span> <span style="color: #800080">$e</span>-><span style="color: #000000">getMessage(); } } </span><span style="color: #008000">/*</span><span style="color: #008000"> *入列 *$data数组 *成功返回1,失败返回false,或者null </span><span style="color: #008000">*/</span> <span style="color: #0000ff">public</span> <span style="color: #0000ff">function</span> _unshift(<span style="color: #800080">$data</span> =<span style="color: #0000ff">array</span><span style="color: #000000">()){ </span><span style="color: #0000ff">if</span>(!<span style="color: #008080">is_array</span>(<span style="color: #800080">$data</span>) || <span style="color: #0000ff">empty</span>(<span style="color: #800080">$data</span>)){<span style="color: #0000ff">return</span> <span style="color: #0000ff">false</span><span style="color: #000000">;} </span><span style="color: #800080">$sql</span> = 'default'<span style="color: #000000">; </span><span style="color: #0000ff">foreach</span>(<span style="color: #800080">$data</span> <span style="color: #0000ff">as</span> <span style="color: #800080">$k</span>=><span style="color: #800080">$v</span><span style="color: #000000">){ </span><span style="color: #800080">$sql</span> .= ',"'.<span style="color: #800080">$v</span>.'"'<span style="color: #000000">; } </span><span style="color: #008000">//</span><span style="color: #008000">把$data转为sql语句,添加到队列容器contain中</span> <span style="color: #800080">$sql</span> = 'insert into goods values('.<span style="color: #800080">$sql</span>.')'<span style="color: #000000">; </span><span style="color: #0000ff">return</span> @<span style="color: #008080">array_unshift</span>(self::<span style="color: #800080">$container</span>,<span style="color: #800080">$sql</span><span style="color: #000000">); } </span><span style="color: #008000">/*</span><span style="color: #008000"> *出列 *成功返回最后插入的数据id *失败返回失败信息 </span><span style="color: #008000">*/</span> <span style="color: #0000ff">private</span> <span style="color: #0000ff">static</span> <span style="color: #0000ff">function</span><span style="color: #000000"> _pop(){ </span><span style="color: #0000ff">try</span>{<span style="color: #008000">//</span><span style="color: #008000">获取尾部的sql语句,出列</span> <span style="color: #800080">$sql</span> = <span style="color: #008080">array_pop</span>(self::<span style="color: #800080">$container</span><span style="color: #000000">); self</span>::<span style="color: #800080">$pdo</span>-><span style="color: #008080">exec</span>(<span style="color: #800080">$sql</span><span style="color: #000000">); </span><span style="color: #008000">//</span><span style="color: #008000">把剩余的容器值赋给中间变量</span> <span style="color: #800080">$middle</span> = self::<span style="color: #800080">$container</span><span style="color: #000000">; </span><span style="color: #008000">//</span><span style="color: #008000">判断中间变量是否为空,不为空则继续获取容器尾部的数据,继续出列</span> <span style="color: #0000ff">while</span>(<span style="color: #800080">$middle</span><span style="color: #000000">){ </span><span style="color: #800080">$sql</span> = <span style="color: #008080">array_pop</span>(<span style="color: #800080">$middle</span><span style="color: #000000">); self</span>::<span style="color: #800080">$pdo</span>-><span style="color: #008080">exec</span>(<span style="color: #800080">$sql</span><span style="color: #000000">); </span><span style="color: #008000">//</span><span style="color: #008000">把数据再转给容器,也就是转给while循环外面的$middle,这样才能实现循环,让容器里面的数据全部出列,插入到数据库中</span> self::<span style="color: #800080">$container</span> = <span style="color: #800080">$middle</span><span style="color: #000000">; } </span><span style="color: #008000">//</span><span style="color: #008000">返回的是,最后插入的id,失败是null</span> <span style="color: #0000ff">return</span> self::<span style="color: #800080">$pdo</span>-><span style="color: #000000">lastInsertId(); }</span><span style="color: #0000ff">catch</span>(PDOException <span style="color: #800080">$e</span><span style="color: #000000">){ </span><span style="color: #0000ff">return</span> <span style="color: #800080">$e</span>-><span style="color: #000000">getMessage(); } } </span><span style="color: #008000">//</span><span style="color: #008000">析构函数,对象回收时调用,通过它实现自动让容器数据入库</span> <span style="color: #0000ff">public</span> <span style="color: #0000ff">function</span><span style="color: #000000"> __destruct(){ </span><span style="color: #008000">//</span><span style="color: #008000">当对象被回收时,判断容器是否存在消息,假如存在,则调用_pop方法,把消息出列</span> <span style="color: #0000ff">if</span>(self::<span style="color: #800080">$container</span><span style="color: #000000">){ self</span>::<span style="color: #000000">_pop(); } } }</span>
下面是同一級目錄下呼叫這個類別的檔案的內容,當然,你也可以在上面那個queue類別的下面呼叫_unshift方法實作訊息佇列的操作
<?<span style="color: #000000">php </span><span style="color: #0000ff">include</span> './queue.php'<span style="color: #000000">; </span><span style="color: #0000ff">use</span> Home\Queue;<span style="color: #008000">//</span><span style="color: #008000">引入命名空间的Queue类</span> <span style="color: #800080">$ob</span> = <span style="color: #0000ff">new</span><span style="color: #000000"> Queue; </span><span style="color: #008000">//</span><span style="color: #008000">消息入列</span> <span style="color: #800080">$ob</span>->_unshift(<span style="color: #0000ff">array</span>('goodsname'=>'vivo手机8888','price'=>1120,'category_id'=>1,'sort'=>1,'description'=>'vivo品牌','remark'=>'好用'<span style="color: #000000">)); </span><span style="color: #800080">$ob</span>->_unshift(<span style="color: #0000ff">array</span>('goodsname'=>'小米手机888','price'=>1998,'category_id'=>1,'sort'=>1,'description'=>'小米品牌手机','remark'=>'国产好货'<span style="color: #000000">)); </span><span style="color: #008000">//</span><span style="color: #008000">之所以打印出来,完成是为了看看效果,至于,有没有实现商品入库,你得去看看你的数据库了,呵呵</span> <span style="color: #008080">var_dump</span>(Queue::<span style="color: #800080">$container</span>);