本文分享我自己如何實作使用者資料的驗證與消毒,驗證與消毒可以使你的應用程式更安全。但請注意,以下介紹的只是我的作法(或者我知道的作法),並不代表只能這樣做,或者我的作法是好的。
$_GET、$_POST、$_COOKIE、file_get_contents()、遠端資料庫......
不要信任你的使用者,因為隨時有人會刻意或不小心輸入有問題的資料,例如使用者在留言板當中插入不正當的<script>標籤,嵌入JAVASCRIPT程式碼而導致XSS攻擊;直接將使用者輸入的資料直接執行資料庫查詢也是十分危險的,驗證與消毒使用者資料可以使你的網站避免資料庫注入與跨網站腳本攻擊。
htmlentities()函式可以將HTML的特殊字元(如<、&)消毒成對應的HTML代表字元,給定一個字串,函式會跳脫所有的字元,並將字串轉換成安全的形式。
但是這個函式預設不會跳脫單引號,在第二個參數使用ENT_QUOTES常數,告知函示要將單引號轉換,最後一個參數則指定使用的編碼。
$s="<script>";
htmlentities($s,ENT_QUTES,"UTF-8");
ENT_QUTES部分也可以使用數字3代替。
絕對不要以正則表達式來消毒HTML,如preg_replace()等函式,正則表達式相當複雜,且HTML輸入可能也不符合規則,產生錯誤的可能性很大。
如果你只要跳脫單雙引號,可以使用addslashes()函式。
$userinput=$_GET["id"];
addslashes($userinput);
如果你的資料格式非常簡單,使用這個函式以正則表達式驗證資料是否符合要求,但是如果相對複雜就不建議使用。
如果你的網站文章以GET方式取得其文章ID,並進入SQL查詢,除了要進行消毒以外,也可以利用preg_match檢查文章ID,例如我的文章ID單純為數字,就檢查該ID是否為純數字,否則就不執行SQL查詢。
if (preg_match("/^([0-9]+)$/", $_GET["id"])) {
/*SQL......*/
}
如果你要驗證一字串是否為EMAIL,可以使用filter_var()函式,搭配FILTER_VALIDATE_*常數來驗證輸入,PHP提供了不同常數來驗證電子郵件、浮點數、URL、正則表達式等。
$mail=$_POST["email"];
if (filter($mail,FILTER_VALIDATE_EMAIL)) {
/*IS MAIL*/
}else{
/*NOT MAIL*/
}
驗證資料可以使你獲得預期的資料,例如要求EMAIL地址,確認這個輸入真的是一個EMAIL地址,如果遇到無效的資料,則放棄後續資料庫的處理。
驗證與消毒不同的是,驗證並沒有去除任何的資料,只有確保輸入的資料達到你的預期。
關於作者
粉絲專頁
文章分類