思考:通常咱們的數據都是存儲在數據庫裏面,對於常規的CRUD操做都是用代碼實現,好比使用PHP作項目,全部的數據處理都須要主動操做代碼實現。若是咱們如今有一項目,業務須要在用戶下單後,對用戶的訂單進行分潤處理,好比在每月的21號,對上個月全部的訂單按設置的規則進行分潤處理,固然shll腳本也能夠實現,可是今天咱們說的是如何經過數據庫「存儲過程」和「事件」來實現。html
1、以下圖,是MySQL官網所介紹的https://dev.mysql.com/doc/refman/5.5/en/stored-objects.htmlmysql
一、簡單的理解「存儲過程」就是咱們平時寫的SQL的集合,裏面可能包含IF判斷或者posLoop:LOOP循環和咱們平時寫PHP代碼差很少,就是爲了實現某個操做(CRUD);sql
「事件」,就是咱們設置的一個自動開關,能夠按照咱們設置的時間,好比天天12:00或者每分鐘處理一次(調用你寫的存儲過程)。數據庫
二、好比咱們經常使用的Navicat的數據庫管理工具,第一個欄目是咱們經常使用的「表」,第三個和第四個就是咱們所說的「存儲過程」和「事件」。數組
2、簡單的需求。工具
一、好比咱們有一張表 t_user,須要每2分鐘處理一下,若是 type 字段值爲 1,則把 num 的值修改成 500。oop
二、新建一個過程spa
三、具體SQL代碼。代碼大體說明一下:code
:SQL裏面全部須要用到的變量,都須要先定義,全部咱們先定義了一下三個變量。htm
:而後建立遊標,至關於咱們代碼裏面先獲取數據,獲取一個二維數組的 List ,而且把它放在 cur_test 裏面,若是遊標內容執行完成,就將 done的值設置爲 1 。
:打開遊標,至關於開始獲取到這個變量。開始循環,至關於咱們常常作的 foreach 循環數組操做,先判斷下,而後取出遊標中的值,賦值給 定義好的變量。至關於咱們key 和 value 鍵名 鍵值,而後判斷知足即修改。
:最後結束循環的標示和釋放遊標。
:能夠點擊運行,若是沒有問題就能夠查看是否更改數據,有問題會有提示錯誤。
BEGIN #處理t_user若是type = 1,則將num修改成200 #定義變量 DECLARE done int;#定義遊標標記 DECLARE t_id int;#定義須要處理的id值 DECLARE t_type int;#定義記錄值類型 #建立遊標,並存儲數據 DECLARE cur_test CURSOR FOR SELECT id,type FROM t_user LIMIT 500; #遊標中的內容執行完後將done設置爲1 DECLARE CONTINUE HANDLER FOR NOT FOUND SET done = 1; #打開遊標 OPEN cur_test; #執行循環 posLoop:LOOP #判斷是否結束循環 IF done = 1 THEN LEAVE posLoop; END IF; #取遊標中的值 FETCH cur_test INTO t_id,t_type; #若是type = 1,則將num修改成200 IF t_type = 1 THEN #執行更新操做 UPDATE t_user SET num = 200 WHERE id = t_id; END IF; #結束循環 END LOOP posLoop; #釋放遊標 CLOSE cur_test; END
四、建立 「事件」調用寫好的過程 p_t3()。調用 存儲過程 通常用 CALL + 過程名。
五、點擊保存時,可能提示 「event_scheduler = OFF」 未開啓,咱們開啓下便可,指令以下。注意,每次重啓MySQL後,該值會設爲 off 須要從新開啓一下。
#開啓 SET GLOBAL event_scheduler = ON; #關閉 SET GLOBAL event_scheduler = OFF;
最後:只要數據庫服務開啓,每分鐘都會調用一次p_t3(),實現裏面的業務規則。第一個簡單存儲過程加事件的調用,到此爲止,至於爲何SQL裏面這樣寫,咱們往下看個人「MySQL實現定時清理過時數據」篇。