PHP中magic_quotes_gpc和magic_quotes_runtime的區(qū)別、作用和用法
這兩天遇到一個奇怪的問題,用CKEditor編輯的內(nèi)容在本地測試服務(wù)器能保存,在正式服務(wù)器不能保存,程序代碼是一模一樣的,數(shù)據(jù)庫也是一樣的,那應(yīng)該就是PHP設(shè)置問題。那是哪個設(shè)置不一樣呢?搜索發(fā)現(xiàn),原來是魔法引用函數(shù)magic_quotes_gpc和magic_quotes_runtime設(shè)置的問題。在php.ini設(shè)置magic_quotes_gpc為ON,則問題解決。
一、magic_quotes_gpc示例
魔術(shù)引用magic_quotes_gpc發(fā)生作用是在傳遞$_GET,$_POST,$_COOKIE時。下面舉4個示例說明,本人所遇到的問題正是示例1。
示例1:
條件: magic_quotes_gpc=off,寫入數(shù)據(jù)庫的字符串未經(jīng)過任何過濾處理,從數(shù)據(jù)庫讀出的字符串也未作任何處理。
數(shù)據(jù): $data=”snow‘’‘’sun” ; (snow和sun之間是四個連續(xù)的單引號)
操作: 將字符串”snow‘’‘’sun” 寫入數(shù)據(jù)庫。
結(jié)果: 出現(xiàn)sql語句錯誤,mysql不能順利完成sql語句,寫入數(shù)據(jù)庫失敗。
數(shù)據(jù)庫保存格式:無數(shù)據(jù)。
輸出數(shù)據(jù)格式:無數(shù)據(jù)。
說明: 對于未經(jīng)處理的單引號在寫入數(shù)據(jù)庫時會使sql語句發(fā)生錯誤。
示例2:
條件: magic_quotes_gpc=off,寫入數(shù)據(jù)庫的字符串經(jīng)過函數(shù)addlashes()處理,從數(shù)據(jù)庫讀出的字符串未作任何處理。
數(shù)據(jù): $data=”snow‘’‘’sun” ; (snow和sun之間是四個連續(xù)的單引號)
操作: 將字符串”snow‘’‘’sun”寫入數(shù)據(jù)庫。
結(jié)果: sql語句順利執(zhí)行,數(shù)據(jù)成功寫入數(shù)據(jù)庫。
數(shù)據(jù)庫保存格式:snow‘’‘’sun(和輸入一樣)
輸出數(shù)據(jù)格式:snow‘’‘’sun(和輸入一樣)
說明: addslashes()函數(shù)將單引號轉(zhuǎn)換為轉(zhuǎn)義字符使sql語句成功執(zhí)行,但輸出并不是我們想象的字符串“snow‘’‘’sun”。
示例3:
條件: magic_quotes_gpc=on,寫入數(shù)據(jù)庫的字符串未經(jīng)過任何處理,從數(shù)據(jù)庫讀出的字符串未作任何處理。
數(shù)據(jù): $data=”snow‘’‘’sun” ; (snow和sun之間是四個連續(xù)的單引號)
操作: 將字符串”snow‘’‘’sun”寫入數(shù)據(jù)庫。
結(jié)果: sql語句順利執(zhí)行,數(shù)據(jù)成功寫入數(shù)據(jù)庫。
數(shù)據(jù)庫保存格式:snow‘’‘’sun(和輸入一樣)
輸出數(shù)據(jù)格式:snow‘’‘’sun(和輸入一樣)
說明: magic_quotes_gpc=on將單引號轉(zhuǎn)換為轉(zhuǎn)義字符使sql語句成功執(zhí)行,但輸出并不是我們想象的字符串“snow‘’‘’sun”。
示例4:
條件: magic_quotes_gpc=on,寫入數(shù)據(jù)庫的字符串經(jīng)過函數(shù)addlashes()處理,從數(shù)據(jù)庫讀出的字符串未作任何處理。
數(shù)據(jù): $data=”snow‘’‘’sun” ; (snow和sun之間是四個連續(xù)的單引號)
操作: 將字符串”snow‘’‘’sun”寫入數(shù)據(jù)庫。
結(jié)果: sql語句順利執(zhí)行,數(shù)據(jù)成功寫入數(shù)據(jù)庫。
數(shù)據(jù)庫保存格式:snow‘’‘’sun(添加了轉(zhuǎn)義字符)
輸出數(shù)據(jù)格式:snow‘’‘’sun(添加了轉(zhuǎn)義字符)
說明: magic_quotes_gpc=on將單引號轉(zhuǎn)換為轉(zhuǎn)義字符使sql語句成功執(zhí)行,addslashes()函數(shù)又將即將轉(zhuǎn)義字符中的單引號轉(zhuǎn)換為轉(zhuǎn)義字符被作為數(shù)據(jù)寫入數(shù)據(jù)庫,數(shù)據(jù)庫保存的字符串是“snow‘’‘’sun”。
總結(jié):
1、對于magic_quotes_gpc=on的情況,我們可以不對輸入和輸出數(shù)據(jù)庫的字符串?dāng)?shù)據(jù)作addslashes()函數(shù)和stripslashes()函數(shù)的操作,數(shù)據(jù)也會正常顯示。如果此時你對輸入的數(shù)據(jù)作了addslashes()函數(shù)處理,那么在輸出的時候就必須使用stripslashes()函數(shù)去掉多余的反斜杠。
2、 對于magic_quotes_gpc=off 的情況,必須使用addslashes()函數(shù)對輸入數(shù)據(jù)進行處理,但并不需要使用stripslashes()函數(shù)格式化輸出。因為addslashes()函數(shù)只是幫助mysql完成了sql語句的執(zhí)行,數(shù)據(jù)庫存儲的是轉(zhuǎn)換前的數(shù)據(jù)。
二、magic_quotes_gpc和magic_quotes_runtime的區(qū)別和用法
PHP提供兩個方便我們引用數(shù)據(jù)的魔法引用函數(shù)magic_quotes_gpc和magic_quotes_runtime,這兩個函數(shù)如果在php.ini設(shè)置為ON的時候,就會為我們引用的數(shù)據(jù)碰到單引號“,”和雙引號“"”以及反斜線“”是自動加上反斜線,幫我們自動轉(zhuǎn)譯符號,確保數(shù)據(jù)操作的正確運行,可是我們在php不同的版本或者不同的服務(wù)器配置下,有的magic_quotes_gpc和magic_quotes_runtime設(shè)置為on,有的又是off,所以我們寫的程序必須符合on和off兩種情況。那么magic_quotes_gpc和magic_quotes_runtime兩個函數(shù)有什么區(qū)別呢?看下面的說明:
1、magic_quotes_gpc?
作用范圍:Web客戶服務(wù)端;
作用時間:請求開始是,例如當(dāng)腳本運行時。
2、magic_quotes_runtime
作用范圍:從文件中讀取的數(shù)據(jù)或執(zhí)行exec()的結(jié)果或是從SQL查詢中得到的;
作用時間:每次當(dāng)腳本訪問運行狀態(tài)中產(chǎn)生的數(shù)據(jù)。
所以最關(guān)鍵的區(qū)別就是它們針對的處理對象不同:magic_quotes_gpc的設(shè)定值將會影響通過$_GET,$_POST,$_COOKIE獲得的數(shù)據(jù)。magic_quotes_runtime的設(shè)定值將會影響從文件中讀取的數(shù)據(jù)或從數(shù)據(jù)庫查詢得到的數(shù)據(jù)。
<?php
//---我們在表單里填寫“'”,“"”,“”這些符號,如果magic_quotes_gpc沒有開啟,那么他們不會被反斜杠轉(zhuǎn)義
echo '現(xiàn)在通過POST傳遞過來的值是:'.$_POST[str].'
';
//---檢查magic_quotes_gpc是否打開,如果沒有打開,用addslashes進行轉(zhuǎn)義
if(get_magic_quotes_gpc()){
$str = $_POST[str];
}else{
$str = addslashes($_POST[str]);
}
echo '這里是轉(zhuǎn)義過后的:'.$str.'';
$sql = "INSERT INTO lastnames(lastname) VALUES ($str)";
// 我們在try.php文件里面依然寫“'”,“"”,“”這幾個字符,用來測試
$data = implode(file(try.php));
echo '這里是try.php的數(shù)據(jù)';
if(get_magic_quotes_runtime()){
echo '被系統(tǒng)自帶轉(zhuǎn)義的:'.$data;
}else{
echo '被addslashes轉(zhuǎn)義了的:'.addslashes($data);
}
$sql = "INSERT INTO lastnames(lastname) VALUES ($data)";
echo '
SQL語句為:
'.$sql;
//---入庫都轉(zhuǎn)義了,但是多余了反斜杠,我們要讀出來是原來的數(shù)據(jù)時候使用stripslashes()去掉反斜杠
//---stripslashes()和addslashes()作用相反
?>
在這里順便在提幾個想關(guān)聯(lián)的函數(shù):
1、set_magic_quotes_runtime()
設(shè)置magic_quotes_runtime值:0=關(guān)閉,1=打開,默認(rèn)狀態(tài)是關(guān)閉的。可以通過phpinfo()查看magic_quotes_runtime狀態(tài)。
2、get_magic_quotes_gpc()
查看magic_quotes_gpc值:0=關(guān)閉,1=打開。
3、get_magic_quotes_runtime()
查看magic_quotes_runtime值:0=關(guān)閉,1=打開。
注意:沒有set_magic_quotes_gpc()這個函數(shù),就是不能在程序里面設(shè)置magic_quotes_gpc的值。





