2012-07-05 89 views
2

我正在嘗試構建一個網頁以更好地學習Java和SQL。我的問題是,有沒有辦法在Java中做出一個通用的SQL select語句?例如:在sql語句中使用java變量

SELECT var1 FROM var2 WHERE var3=var4 

或類似的東西。

我的想法是用網頁中的用戶選擇的項目填充var。我知道這可以使用Post方法在PHP中完成,但我沒有使用PHP。另外,我已經閱讀了Java中的Prepared Statement,但似乎只在比較運算符之後使用時才起作用;例如:

SELECT * FROM table Where attr = ? & 

另外,我知道我能做到的"SELECT " + var1 + "FROM " + var2 + "WHERE attr = " + var3 + " "硬編碼的版本,但是這似乎並不很通用的,容易出現很多錯誤。

  • Incase:我正在嘗試使用HTML & JSP構建此測試頁。
+1

你是對的。我強烈建議爲此PreparedStatements。你的第一種方法是SQL注入和其他各種問題。我也會認爲這些列會非常靜態的,或者至少我會期望有一些你需要的有限數量的真實陳述。 – tjg184

+1

不能使用它來設置表名等 – Thihara

+0

你可以看看類似的問題:http://stackoverflow.com/questions/3135973/variable-column-names-using-prepared-statements – ria

回答

3

你在做什麼與?參數化查詢。該查詢只能針對不是表格或列名稱的值進行參數化。

每次運行查詢。數據庫必須創建查詢計劃。如果您一次又一次運行相同的查詢,則可以通過創建PreparedStatement來減少此開銷。 第一次執行PreparedStatement將生成查詢計劃。隨後的執行將重用相同的計劃。這裏

相同的查詢裝置,它是除數值在所有方面相同的where子句,表達式等

如果改變列或表名稱或修改查詢的結構,則它是一個不同的使用查詢並將需要不同的查詢計劃。 PreparedStement在這種情況下沒有用,你應該堅持你談論的硬編碼版本。由於這個原因,如果您嘗試參數化PreparedStement中的表或列名稱,則會出現錯誤。

話雖如此。採取這種通用方法進行查詢是不可取的。如果你的查詢很簡單,你可以從ORM工具中受益。你甚至不必維護一行SQL。對於複雜的查詢,您可以選擇使用ORM特定的查詢語言或JPQL或Native SQL。尋找JPA +休眠

0

您的具體用法不被JDBC允許。創建準備好的語句時,您需要對錶名進行硬編碼。如果你真的想這樣做,我建議你使用字符串連接來創建SQL語句,然後用參數創建一個PreparedStatement來處理where部分。如果您想知道爲什麼要在特定的解決方案中使用PreparedStatements,那就是爲了避免SQL注入。

-3

如果使用JDBC,可以試試這個

PreparedStatement statement = connection.prepareStatement("SELECT ? FROM ? WHERE ?=? "); 

然後

statement.setString(1, "column_name"); 
statement.setString(2, "table_name"); 
statement.setString(3, "column_name"); 
statement.setBigDecimal(4, 123); 

如果你正在使用其他的ORM如Hibernate或JPA,我相信也有方法可以做到。

+2

你不能這樣做。只要運行它,看看.... – Thihara

0

您可以使用PreparedStatement來實現您的目標。

例如 -

String query = "SELECT * FROM table Where attr = ?"; 
PreparedStatement pt = con.prepareStatement(query); 
pt.setString(1, attribete); 
pt.executeUpdate(); 
0

有任何SQL包裝類或其他沒有這樣的直接規定,更換表,列名與查詢參數值一起,在查詢字符串中使用一個單一的方法。

您需要依賴PreparedStatement和任何字符串方法replace(...)replaceFirst(...)才能達到您的要求。

String sql = "Select $1, $2 from $3 where $4=? and $5=?"; 
sql = sql.replaceFirst("$1", "col1_name"); 
sql = sql.replaceFirst("$2", "col2_name"); 
sql = sql.replaceFirst("$3", "table_name"); 
sql = sql.replaceFirst("$4", "col4_name"); 
sql = sql.replaceFirst("$5", "col5_name"); 
// .. and so on 

PreparedStatement pst = con.prepareStatement(sql); 
// use relevant set methods to set the query parametrs. 
pst.setXXX(1, value_for_first_query_parameter); // from a variable or literal 
pst.setXXX(2, value_for_second_query_parameter); // from a variable or literal 
// ... and so on