首頁 後端開發 php教程 在php中防止SQL注入的方法

在php中防止SQL注入的方法

Nov 28, 2016 am 10:04 AM
php

【一、在伺服器端設定】

       安全,PHP程式編寫是一方面,PHP的設定更是非常關鍵。

我們php手手工安裝的,php的預設設定檔在 /usr/local/apache2/conf/php.ini,我們最主要就是要設定php.ini中的內容,讓我們執行 php能夠更安全。整個PHP中的安全設定主要是為了防止phpshell和SQL Injection的攻擊,一下我們慢慢探討。我們先使用任何編輯工具開啟 /etc/local/apache2/conf/php.ini,如果你是採用其他方式安裝,設定檔可能不在該目錄中。

(1) 打開php的安全模式

php的安全模式是個非常重要的內嵌的安全機制,能夠控制一些php中的函數,比如system(),

同時把很多文件操作函數進行了權限控制,也不允許對某些關鍵文件的文件,例如/etc/passwd,

但是預設的php.ini是沒有開啟安全模式的,我們把它打開:

safe_mode = on

(2) 用戶群組安全

當safe_mode打開時,safe_mode_gid被關閉,那麼php腳本能夠對檔案進行訪問,而且相同

群組的使用者也能夠對檔案進行存取。

建議設定為:

safe_mode_gid = off

如果不進行設置,可能我們無法對我們伺服器網站目錄下的檔案進行操作了,例如我們需要

對檔案進行操作的時候。

(3) 安全模式下執行程式主目錄

如果安全模式開啟了,但是卻是要執行某些程式的時候,可以指定要執行程式的主目錄:

safe_mode_exec_dir = D:/usr/bin

一般情況下是不需要執行什麼程式的,所以建議不要執行系統程式目錄,可以指向一個目錄,

然後把需要執行的程式拷貝過去,例如:

safe_mode_exec_dir = D:/tmp/cmd

safe_mode_exec_dir = D:/tmp/cmd

safe_mode_exec_dir = D:/tmp/cmd

safe_mode_exec_dir = D:/tmp/cmd

但是,我更建議不要執行任何程序,那麼就可以指向我們網頁目錄:

safe_mode_exec_dir = D:/usr/www

(4) 安全模式下包含文件

如果要在安全模式下包含某些公用文件,那就修改一下選項:

safe_mode_include_dir = D:/usr/www/include/

其實一般php腳本包含文件都是在程式自己已經寫好了,這個可以根據具體需要設定。

(5) 控制php腳本能存取的目錄

使用open_basedir選項能夠控制PHP腳本只能存取指定的目錄,這樣能夠避免PHP腳本存取

不應該存取的文件,一定程度上限制了phpshell的危害,我們一般可以設定為只能訪問網站目錄:

open_basedir = D:/usr/www

(6) 關閉危險函數

如果打開了安全模式,那麼函數禁止是可以不需要的,但是我們為了安全還是考慮進去。例如,

我們覺得不希望執行包括system()等在那的能夠執行命令的php函數,或者能夠查看php資訊的

phpinfo()等函數,那麼我們就可以禁止它們:

disable_functions = system ,passthru,exec,shell_exec,popen,phpinfo

如果你要禁止任何檔案和目錄的操作,那麼可以關閉很多檔案操作

disable_functions = chdir,chroot,dir,getcwd,opendir,readdir,scscandir,fopenunlink ,delete,copy,mkdir, rmdir,rename,file,file_get_contents,fputs,fwrite,chgrp,chmod,chown

以上只是列了部分不叫常用的檔案處理函數,你也可以把上面執行指令函數和這個函數結合,

就能夠抵制大部分的phpshell了。

(7) 關閉PHP版本信息在http頭中的洩漏

我們為了防止黑客獲取服務器中php版本的信息,可以關閉該信息斜路在http頭中:

expose_php = Off

比如黑客在telnet www.12345.com 80 的時候,那麼將無法看到PHP的資訊。

(8) 關閉註冊全域變數

在PHP中提交的變量,包括使用POST或GET提交的變量,都將自動註冊為全域變量,能夠直接訪問,

這是對伺服器非常不安全的,所以我們不能讓它註冊為全域變量,就把註冊全域變數選項關閉:

register_globals = Off

當然,如果這樣設定了,那麼取得對應變數的時候就要採用合理方式,例如取得GET提交的變量var,

那麼就要用$_GET['var']來進行獲取,這個php程式設計師要注意。

(9) 開啟magic_quotes_gpc來防止SQL注入

SQL注入是非常危險的問題,小則網站後台被入侵,重則整個伺服器淪陷,

所以一定要小心。 php.ini中有一個設定:

magic_quotes_gpc = Off

這個預設是關閉的,如果它打開後將自動把用戶提交對sql的查詢進行轉換,

比如把' 轉為'等,這對防止sql注射有重大作用。所以我們推薦設定為:🎜🎜magic_quotes_gpc = On🎜🎜(10) 錯誤訊息控制🎜🎜一般php在沒有連接到資料庫或其他情況下會有提示錯誤,一般錯誤訊息中會包含php腳本當

前的路徑資訊或查詢的SQL語句等信息,這類資訊提供給駭客後,是不安全的,所以一般伺服器建議禁止錯誤提示:

display_errors = Off

如果你卻是要顯示錯誤信息,一定要設置顯示錯誤的級別,比如只顯示警告以上的信息:

error_reporting = E_WARNING & E_ERROR

當然,我還是建議關閉錯誤提示。

(11) 錯誤日誌

建議在關閉display_errors後能夠把錯誤訊息記錄下來,便於查找伺服器運行的原因:

log_errors = On

同時也設定錯誤日誌存放的目錄,建議根apache的日誌存在一起:

error_log = D:/usr/local/apache2/logs/php_error.log

注意:給檔案必須允許apache使用者的和群組具有寫入的權限。

MYSQL的降權運行

新建立一個使用者例如mysqlstart

net user mysqlstart fuckmicrosoft /add

net localgroup users mysqlstart /del


net localgroup users mysqlstart /del mysqlstart 完全控制的權限

然後在系統服務中設置,MYSQL的服務屬性,在登入屬性當中,選擇此使用者mysqlstart 然後輸入密碼,確定。

重新啟動 MYSQL服務,然後MYSQL就運行在低權限下了。

如果是在windos平台下搭建的apache我們還需要注意一點,apache默認運行是system權限,

這很恐怖,這讓人感覺很不爽.那我們就給apache降降權限吧。

net user apache fuckmicrosoft /add

net localgroup users apache /del

ok.我們建立了一個不屬於任何群組的使用者apche。

我們開啟電腦管理器,選服務,點apache服務的屬性,我們選擇log on,選擇this account,我們填入上面所建立的帳戶和密碼,

重啟apache服務,ok,apache運行在低權限下了。

其實我們也可以透過設定各個資料夾的權限,來讓apache使用者只能執行我們想讓它能幹的事情,給每個目錄建立一個單獨能讀寫的使用者。

這也是當前許多虛擬主機供應商的流行配置方法哦,不過這​​種方法用來防止這裡就顯的有點大材小用了。 

【二、在PHP程式碼編寫】

       雖然國內許多PHP程式設計師仍在依賴addslashes防止SQL注入,還是建議大家加強中文防止SQL注入的檢查。 addslashes的問題在於駭客可以用0xbf27來代替單引號,而addslashes只是將0xbf27修改為0xbf5c27,成為一個有效的多字節字符,其中的0xbf5c仍會被看作是單引號,所以addslashes無法成功攔截。

       當然addslashes也不是毫無用處,它是用於單字節字串的處理,多位元組字元還是用mysql_real_escape_string吧。
       另外為php手冊中get_magic_quotes_gpc的舉例:
if (!get_magic_quotes_gpc()) {
$lastname = addslashes($_POST['lastname')) {
$lastname = addslashes($_POST['lastname')) {
$lastname = addslashes($_POST['lastname'));
}

最好對magic_quotes_gpc已經開放的情況下,還是對$_POST[’lastname’]進行檢查一下。
再說下mysql_real_escape_string和mysql_escape_string這2個函數的差別:
mysql_real_escape_string 必須在(PHP 4 >= 4.3.0, PHP 5)的情況下才能使用。否則只能用 mysql_escape_string ,兩者的差異是:mysql_real_escape_string 考慮到連接的
當前字元集,而mysql_escape_string 不考慮。
總結一下:
* addslashes() 是強行加;
* mysql_real_escape_string()  會判斷字元集,但是對PHP版本有要求;
* mysql_escape_string不考慮連接的目前字元集。
------------------------------------------------- ------------------------------------------------
在PHP編碼的時候,如果考慮到一些比較基本的安全問題,首先一點:
1. 初始化你的變數
為什麼這麼說呢?我們看下面的程式碼:
PHP代碼   
       if ($admin)     ';     
    include('admin.php');     
    }          echo '你不是管理員,無法進行管理! ';     
    }     
    ?>
      例如我們的這個頁是http://daybook.diandian.com/login.php,那我們提交:http://daybook.diandian.com/login.php?admin=1,呵呵,你想一些,我們是不是直接就是管理員了,直接進行管理。
     當然,可能我們不會犯這麼簡單錯的錯誤,那麼一些很隱密的錯誤也可能導致這個問題,例如phpwind論壇有個漏洞,導致能夠直接拿到管理員權限,就是因為有個$skin變數沒有初始化,導致了後面一系列問題。那我們該如何避免上面的問題呢?首先,從php.ini入手,把php.ini裡面的register_global =off,就是不是所有的註冊變數為全局,那麼就能避免了。但是,我們不是伺服器管理員,只能從程式碼上改進了,那我們要如何改進上面的程式碼呢?我們改寫如下:
PHP程式碼      
        $admin = 0; // 初始化     
    {     
    // 判斷提交的管理者使用者名稱與密碼是不是對的對應的處理代碼     
    // ...     
    $admin = 1;     
    {     
    $admin = 0;     
    }     
    echo '登陸成功! ';     
    include('admin.php');     
    }          echo '你不是管理員,無法進行管理! ';     
    }     
    ?>
    那麼這時候你再提交http://daybook.diandian.com/login. 0 了,那麼你就無法透過這個漏洞取得管理員權限。
2. 防止SQL Injection (sql注射)
SQL 注射應該是目前程式危害最大的了,包括最早從asp到php,基本上都是國內這兩年流行的技術,基本原理就是透過對提交變數的不過濾形成注入點然後使惡意使用者能夠提交一些sql查詢語句,導致重要資料被竊取、資料遺失或損壞,或被入侵到後台管理。
    那麼我們既然了解了基本的注射入侵的方式,那麼我們該如何去防範呢?這個就應該我們從程式碼去入手了。
   我們知道Web上提交資料有兩種方式,一種是get、一種是post,那麼很多常見的sql注射就是從get方式入手的,而且注射的語句裡面一定是包含一些sql語句的,因為沒有sql語句,那麼如何進行,sql語句有四大句:select 、update、delete、insert,那麼我們如果在我們提交的資料中進行過濾是不是能夠避免這些問題呢?
所以我們使用正規則建構以下函數:
PHP程式碼
           return eregi('select|insert|update|delete|'|     
    function verify_id($id=null)
    {     
    if (!$id) { exit('沒有提交參數!'); } // 是否為空判斷     
); / 注射判斷     
    elseif (!is_numeric($id)) { exit('提交的參數非法!'); } //數字判斷        return $id;
    }     
    ?>
     呵呵,因此我們就能夠進行校驗了,於是我們上面的程式碼就變成了下面的:🠎PHP>?    if (inject_check($_GET['id']) )     
    {     
    exit('你提交的資料非法,請檢查後重新提交!');     
    {     
    $id = verify_id($_GET['id']); // 這裡引用了我們的過濾函數,對$id進行過濾     
    echo '提交的資料合法,請繼續! ';     
    }    ,大批量的資料呢?的magic_quotes_gpc = off的時候,那麼提交的不符合資料庫規則的資料都是不會自動在前面加上' '的,那麼我們要控制這些問題,於是建構如下函數:
PHP程式碼      
  ( $str )     
    {     
    if (!get_magic_quotes_gpc()) // 值 $str = addslashes($str); // 過濾     
    }     
    $str = str_replace("_", "_ ", $str); // 把'_'過濾掉     
    $str = str_replace("%", "%", $str); // 把' % '過濾掉     🠎
    }     
    ?>
    我們又一次的避免了伺服器被淪陷的危險。
    最後,再考慮提交一些大量資料的情況,例如發貼,或寫文章、新聞,我們需要一些函數來幫我們過濾和進行轉換,再上面函數的基礎上,我們建構如下函數:
PHP程式碼
        function post_check($post)     
    pc是否為開啟     
    {     
    $post = addslashes($post); // 進行magic_quotes_gpc沒有開啟的情況對提交資料的過濾     
    }     
    $post = str_replace("_", "_", $post); // $post/str post$ / 把' % '過濾掉     
    $post = nl2br($post); // 回車轉換     
    $post     
    }     
    ?>
    呵呵,基本上到這裡,我們把一些情況都說了一遍,其實我覺得自己講的東西還很少,至少我才只講了兩方面,再整個安全中是很少的內容了,考慮下一次講更多,包括php安全配置,apache安全等等,讓我們的安全正的是一個整體,做到最安全。
    最後在告訴你上面表達的:1. 初始化你的變數 2. 一定記得要過濾你的變數


本網站聲明
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn

熱AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover

AI Clothes Remover

用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool

Undress AI Tool

免費脫衣圖片

Clothoff.io

Clothoff.io

AI脫衣器

Video Face Swap

Video Face Swap

使用我們完全免費的人工智慧換臉工具,輕鬆在任何影片中換臉!

熱工具

記事本++7.3.1

記事本++7.3.1

好用且免費的程式碼編輯器

SublimeText3漢化版

SublimeText3漢化版

中文版,非常好用

禪工作室 13.0.1

禪工作室 13.0.1

強大的PHP整合開發環境

Dreamweaver CS6

Dreamweaver CS6

視覺化網頁開發工具

SublimeText3 Mac版

SublimeText3 Mac版

神級程式碼編輯軟體(SublimeText3)

適用於 Ubuntu 和 Debian 的 PHP 8.4 安裝和升級指南 適用於 Ubuntu 和 Debian 的 PHP 8.4 安裝和升級指南 Dec 24, 2024 pm 04:42 PM

PHP 8.4 帶來了多項新功能、安全性改進和效能改進,同時棄用和刪除了大量功能。 本指南介紹如何在 Ubuntu、Debian 或其衍生版本上安裝 PHP 8.4 或升級到 PHP 8.4

我後悔之前不知道的 7 個 PHP 函數 我後悔之前不知道的 7 個 PHP 函數 Nov 13, 2024 am 09:42 AM

如果您是經驗豐富的PHP 開發人員,您可能會感覺您已經在那裡並且已經完成了。操作

如何設定 Visual Studio Code (VS Code) 進行 PHP 開發 如何設定 Visual Studio Code (VS Code) 進行 PHP 開發 Dec 20, 2024 am 11:31 AM

Visual Studio Code,也稱為 VS Code,是一個免費的原始碼編輯器 - 或整合開發環境 (IDE) - 可用於所有主要作業系統。 VS Code 擁有大量針對多種程式語言的擴展,可以輕鬆編寫

在PHP API中說明JSON Web令牌(JWT)及其用例。 在PHP API中說明JSON Web令牌(JWT)及其用例。 Apr 05, 2025 am 12:04 AM

JWT是一種基於JSON的開放標準,用於在各方之間安全地傳輸信息,主要用於身份驗證和信息交換。 1.JWT由Header、Payload和Signature三部分組成。 2.JWT的工作原理包括生成JWT、驗證JWT和解析Payload三個步驟。 3.在PHP中使用JWT進行身份驗證時,可以生成和驗證JWT,並在高級用法中包含用戶角色和權限信息。 4.常見錯誤包括簽名驗證失敗、令牌過期和Payload過大,調試技巧包括使用調試工具和日誌記錄。 5.性能優化和最佳實踐包括使用合適的簽名算法、合理設置有效期、

php程序在字符串中計數元音 php程序在字符串中計數元音 Feb 07, 2025 pm 12:12 PM

字符串是由字符組成的序列,包括字母、數字和符號。本教程將學習如何使用不同的方法在PHP中計算給定字符串中元音的數量。英語中的元音是a、e、i、o、u,它們可以是大寫或小寫。 什麼是元音? 元音是代表特定語音的字母字符。英語中共有五個元音,包括大寫和小寫: a, e, i, o, u 示例 1 輸入:字符串 = "Tutorialspoint" 輸出:6 解釋 字符串 "Tutorialspoint" 中的元音是 u、o、i、a、o、i。總共有 6 個元

您如何在PHP中解析和處理HTML/XML? 您如何在PHP中解析和處理HTML/XML? Feb 07, 2025 am 11:57 AM

本教程演示瞭如何使用PHP有效地處理XML文檔。 XML(可擴展的標記語言)是一種用於人類可讀性和機器解析的多功能文本標記語言。它通常用於數據存儲

解釋PHP中的晚期靜態綁定(靜態::)。 解釋PHP中的晚期靜態綁定(靜態::)。 Apr 03, 2025 am 12:04 AM

靜態綁定(static::)在PHP中實現晚期靜態綁定(LSB),允許在靜態上下文中引用調用類而非定義類。 1)解析過程在運行時進行,2)在繼承關係中向上查找調用類,3)可能帶來性能開銷。

什麼是PHP魔術方法(__ -construct,__destruct,__call,__get,__ set等)並提供用例? 什麼是PHP魔術方法(__ -construct,__destruct,__call,__get,__ set等)並提供用例? Apr 03, 2025 am 12:03 AM

PHP的魔法方法有哪些? PHP的魔法方法包括:1.\_\_construct,用於初始化對象;2.\_\_destruct,用於清理資源;3.\_\_call,處理不存在的方法調用;4.\_\_get,實現動態屬性訪問;5.\_\_set,實現動態屬性設置。這些方法在特定情況下自動調用,提升代碼的靈活性和效率。

See all articles