當binlog記錄存儲程式(存儲過程,存儲函數,觸發器,事件)的時候,可能存在一下問題:
statement複制模式下:
1、一條語句在master和slave上會影響不同的記錄。
2、Slave端的SQL線程在執行statement的時候,具有所有的權限(不做權限檢查)
可能某個存儲過程在master和slave端執行效果不一緻:
比如:
類似這種情況的,如果不改變複制模式,可以考慮使用SQL SECURITY DEFINNER關鍵字來加強下防線。
3、存儲程式所修改的資料是不确定的,這種情況是不利于複制的,可能引擎master和slave的不一緻。
如果我們采用row模式進行複制,就不會出現上述問題,它隻會記錄受變化的表的行記錄資訊。
像存儲過程 call 語句是不會被記錄的,存儲函數所産生的結果會被記錄而不是調用函數的語句。對于觸發器也是記錄它所做的行記錄的改變。
下面的這些 規則隻适用于存儲函數,不适用于其他存儲程式
1、為了能建立和修改一個存儲函數,必須擁有super 、create routine、alter routine權限。
2、建立的存儲函數必須明确指出它所做的修改是 deterministic 或者它不會修改資料。
聲明的時候需要有一下幾個關鍵字:DETERMINISTIC ,NO SQL,READS SQL DATA。否則會有下面的提示:
下面這個是可以的:
下面這個使用UUID函數,是以是 not deterministic
一個函數的本質評估是基于“誠信”的創造者,MySQL 對于 書寫了 deterministic的語句但是産生不确定的情況是不做檢查的。
如果我們不使用 deterministric的話,我們必須使用row複制模式或者是mixed模式來保證主從複制的一緻性。
預設情況下,隻有super權限來定義存儲函數,設定變量:log-bin-trust-function-creators 選項來 允許其他使用者定義自己的function。
以上的這些讨論,同樣适用于trigger,但trigger并沒有deterministic關鍵字。
本文轉自 位鵬飛 51CTO部落格,原文連結:http://blog.51cto.com/weipengfei/1071546,如需轉載請自行聯系原作者