2011-07-11 16 views
1

我正在寫一個小小的python腳本來幫助我自動創建我的個人項目的mysql數據庫和相關帳戶。該腳本的一部分是一個將數據庫名稱作爲字符串的函數,然後創建數據庫。是否有任何安全的方式來參數化MySQL查詢中的數據庫名稱?

def createDB(dbConn, dbName): 
    import MySQLdb 
    c = dbConn.cursor() 
    query = """CREATE DATABASE %s;"""; 
    c.execute(query, (dbName,)) 

這不起作用,因爲MySQL's CREATE DATABASE詢問數據庫的未加引號的名稱,如

CREATE DATAbASE test_db 

,但我的代碼,試圖安全地插入提供的數據庫名稱爲查詢的用戶創建:

CREATE DATABASE 'test_db' 

然後你會得到「你的MySQL語法在測試附近有問題」。

即使這是個人使用,我真的不想直接插入用戶提供的字符串到任何類型的查詢。它反對我的宗教信仰。有沒有一種安全的方法可以將用戶提供的數據庫名稱插入python(或任何語言)的mySQL查詢中,以確保用戶輸入(例如test_db; DROP some_other_db;)將被正確拒絕或轉義?

+0

嘗試'conn.escape_string',根據第二個答案在這裏:http://stackoverflow.com/questions/3617052/escape-string-python-for-mysql –

回答

1

後一些挖掘事實證明,phpmyadmin使用反引號引用數據庫,表和列名。他們只是做:

$sql_query = 'CREATE DATABASE ' . PMA_backquote($new_db); 

這將使在錯誤的情況下上述類似

CREATE DATABASE `test_db; DROP some_other_db`; 

當然在輸入字符串中的任何反引號需要進行轉義,而根據phpMyAdmin的代碼是通過更換完成所有單背蜱雙蜱。我找不到證實這是正確的地方。

我也注意到在線雖然反引號不是標準的SQL。

4

數據庫名稱(不是列或表名稱)不是數據值,因此不適合使用佔位符。想要這樣做通常是一個不好的跡象;只有DBA應該能夠發出create database,因爲這樣做需要一些相當的權限。大多數應用程序需要DBA發出create database,然後將創建的數據庫作爲參數用於dbapi.Connection的參數中。

如果你確定你需要這個,你信任的輸入源,並且您已經檢查無效字符的輸入,你只是做在Python的替代,是這樣的:

def createDB(dbConn, dbName): 
    c = dbConn.cursor() 
    query = """CREATE DATABASE %s;""" % dbName 
    c.execute(query) 
+0

對不起,不是一個非常令人滿意的答案。如果只有數據庫管理員應該這樣做,而且只能通過不使用任何工具的直接查詢來完成,那麼phpmyadmin和其他類似工具如何工作?我怎樣才能在網絡表單中輸入數據庫名稱,並讓它在後端運行一些查詢來創建數據庫?似乎他們有同樣的問題,需要驗證用戶輸入並將其安全地放入查詢中。 –

+0

phpmyadmin認爲這是與之交談的DBA。 「admin」就是這個名字。他們同樣執行自己的邏輯來確保傳遞給他們的db名稱是理智的,並且管理員知道他們在做什麼。 – SingleNegationElimination

+0

我的腳本假定相同。我的腳本由運行在我的開發箱上的mysql的管理員運行,以使我更加方便開發一個新的有趣的個人項目。 –

相關問題