接口防sql注入的調研


注入的來源

http請求的路徑、參數和header,比如cookie等都可能作為sql注入的來源。
在實際的開發工作中,因為現有框架中header、路徑作為參數直接查詢數據庫的使用比較少。因此,主要處理參數sql注入。

 

防止sql注入PHP已知方案

未經轉義的參數直接作為sql語句發給db就會發生sql注入,防止sql注入主要有以下幾種方式:

  1. 強類型參數校驗和轉義,禁止特殊字符的參數傳遞。
  2. 框架和數據庫統一提供的PREPARE, EXECUTE語法。
  3. 讀寫分離。

 

需要注意的是addslashes和mysql_real_escape_string都不能作為防SQL注入的方式。原因請參考:

https://blog.csdn.net/qq_36705093/article/details/79865601

 

詳細說明

 

強類型參數校驗和轉義

1. thinkphp框架input()幫助函數提供了以下幾種參數轉義:`d`:轉義int類型,`a`:轉義數組類型,`f`: 轉義浮點類型, `b`:轉義bool類型,`s`: 轉義字符串類型.
2. 也可以用intval, doubleval, floatval相關的函數進行參數過濾。識別無效的參數返回。

prepare, EXECUTE語法

thinkphp框架提供了prepare, execute語法來處理參數。詳細的mysql prepare語法可以查看:

sql-prepared-statements

 

執行步驟:

  1. 發送sql語句。
  2. 設置變量。
  3. 使用變量執行語句。

 

舉個例子:

prepare example from 'select * from sdb_user where id=?';
set @a=1;
EXECUTE example USING @a;

 

步驟1中的sql語句會被mysql認為是需要執行的部分。步驟2, 3的語句傳入的變量不會被mysql執行。因此這種方式是最安全的mysql防注入的方式。對於thinkphp框架來說,是語句部分還是需要綁定的參數,是根據是否是變量來標識的。對於直接字符串拼接的部分,框架會認為是是sql語句而直接在步驟1發送給mysql,如果這部分有參數拼接就可能發生sql注入。

讀寫分離

thinkphp提供了方便的讀寫分離的配置。對於大部分業務來說,讀的接口都是在其中占據較大的部分,因此可以使用讀寫分離的方式來降低sql注入時對db造成嚴重破壞的概率,比如改寫數據,刪庫等。

主要包含以下database.php配置

<?php

return [
    "hostname":[
          "127.0.0.1",   //master
          "127.0.0.1"    //readonly
     ],
     "username": [
           "foo_write",   //master 
           "foo_read",    //readonly
     ],
     "password": [
            "bar_write",   //master
            "bar_read",    //readonly
     ],
     'hostport'    => '3306',
    
    'deploy'      => 1,
    'rw_separate' => true,
];

 

因此使用tp框架防止sql注入可以做以下改進:

  1. 強類型參數校驗。
  2. 使用參數的方式傳遞查詢條件,禁止直接拼接參數。
  3. 讀寫分離。

 

by: zhangfeng


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM