【python代碼審計】postgresSQL中sql注入

python使用pg數據sql注入分析

內容
審計python使用psycopg2庫操作pg數據庫中的sql注入
sql注入出現原因
總結有3個原因
1 對外接口中有不可信的數據輸入
2 未對輸入的數據進行安全性校驗(白名單,轉義等其他限制)
3 操作數據庫時使用函數的方法不對
審計python代碼
直接對查數據庫拼接字符串和查詢方法進行審計
tip1:對輸入數據直接拼接後查詢

def database():
    injectdata = "1"
    xcmd= "select * from user where id = " + injectdata #psycopg2庫未對數據校驗,傳入什麼參數,execute方法就會執行什麼
    conn = psycopg2.connect(database="test", user="post", password=passwd, host=ip, port="5432")
    cur = conn.cursor()
    cur.execute(xcmd)
    res = cur.fetchall()
    conn.commit()
    conn.close()

拼接注入語法:
1 injectdata = “1 and 1=1” 或者 injectdata = “1 or id =2” #查詢成功
2 injectdata = " 1’ or id =‘2’ " #查詢報錯(有安全校驗)#log(psycopg2.ProgrammingError: unterminated quoted string at or near “’”
3 injectdata = ‘1;select user’ #查詢成功,顯示當前用戶
4 injectdata = ‘1;select pg_sleep(5)’ #查詢成功
說明:"select * from user where id = " + injectdata 這中直接拼接的代碼寫法對sql注入基本沒有安全校驗

tip2:對輸入數據進行格式化後查詢數據庫

def database():
    injectdata = "1"
    xcmd= "select * from user where id = %s"%injectdata  #格式化處理
    conn = psycopg2.connect(database="test", user="post", password=passwd, host=ip, port="5432")
    cur = conn.cursor()
    cur.execute(xcmd)
    res = cur.fetchall()
    conn.commit()
    conn.close()

注入語法驗證:
1 injectdata = “1 and 1=1” 或者 injectdata = “1 or id =2” #查詢成功
2 injectdata = " 1’ " #查詢報錯(有安全校驗)#log(psycopg2.ProgrammingError: unterminated quoted string at or near “’”
3 injectdata = ‘1;select version()’ #查詢成功,有版本號返回
4 injectdata = ‘1;select pg_sleep(5)’ #基於時間盲注查詢成功
說明:"select * from user where id = %s "%injectdata 這種格式化處理傳入數據的寫法與tip1中一樣,未對數據進行安全性校驗

tip3:對輸入數據進行格式化後參數化的調用execute函數

def database():
    injectdata = "1"
    xcmd= "select * from user where id = %s"  #格式化處理
    conn = psycopg2.connect(database="test", user="post", password=passwd, host=ip, port="5432")
    cur = conn.cursor()
    cur.execute(xcmd,injectdata)   **#or [injectdata] or (injectdata) ,官網給出安全操作sql的調用方法,用傳參數的方法調用。**
    res = cur.fetchall()
    conn.commit()
    conn.close()

注入語法:
1 injectdata = “1 and 1=1” 或者 injectdata = “1 or id =2” #報錯TypeError: not all arguments converted during string formatting
2 injectdata = " 1’ " # 報錯
3 injectdata = ‘1;select version()’ #報錯
4 injectdata = ‘1;select pg_sleep(5)’ #報錯

python 調用psycopg的sql注入防禦方法:
psycopg2最直接最根本的解決方案是用官網提供的傳參方式操作數據庫。
#the correct conversion (no more SQL injections!) #正確使用(有sql注入防禦)
官網地址:http://initd.org/psycopg/docs/usage.html#passing-parameters-to-sql-queries
官網psycopg2用戶使用文檔
說明:做python白盒代碼審計時,重點看psycopg庫的使用方法是否是傳參調用的。

ps:本段代碼只是爲了驗證python調用psycopg時sql的相關內容,在實際項目中一般看不到這麼調用的,如果有這麼寫的安全問題還有很多(如:沒有try,沒有數據校驗…)

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章