我的JDBC PreparedStatement
不起作用。我正在使用Oracle 11g Express Edition,Tomcat 7,Java 7,ojdbc7.jar位於$ CATALINA_HOME/lib中。我正在開發的應用程序使用spring框架。但是這並不重要,因爲我構建了一個簡單的Java類來測試相同的PreparedStatement
,但仍然沒有結果。準備好的語句不會返回Oracle XE數據庫的結果
如果我在sqlplus中運行查詢,我會得到預期的結果。如果我在正常的Statement
中使用相同的查詢,我會得到預期的結果。如果我在Spring中使用我的硬編碼值JdbcTemplate
,我會得到結果。只是沒有在那個darned PreparedStatement
。
正如您從下面的日誌中看到的,我的參數正在插入到JDBC中的PreparedStatement
中。跟蹤文件顯示該值在數據庫中綁定,查詢正在運行,但是取回不會返回任何內容。
的log4jdbc日誌顯示我:
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator methodReturned
INFO: 3. Connection.prepareStatement(select distinct staff_id from OE_ROLES where staff_id = ?) returned [email protected]
Jun 09, 2015 1:05:35 PM org.springframework.jdbc.core.StatementCreatorUtils setParameterValueInternal
FINEST: Setting SQL statement parameter value: column index 1, parameter value [jibbyj], value class [java.lang.String], SQL type unknown
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator methodReturned
INFO: 3. PreparedStatement.setString(1, "jibbyj") returned
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator sqlOccured
INFO: select distinct staff_id from OE_ROLES where staff_id = 'jibbyj'
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator sqlTimingOccured
INFO: select distinct staff_id from OE_ROLES where staff_id = 'jibbyj'
{executed in 2 msec}
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator methodReturned
INFO: 3. ResultSet.new ResultSet returned
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator methodReturned
INFO: 3. PreparedStatement.executeQuery() returned [email protected]
Jun 09, 2015 1:05:35 PM net.sf.log4jdbc.Slf4jSpyLogDelegator methodReturned
INFO: 3. ResultSet.next() returned false
這是從跟蹤文件:
PARSING IN CURSOR #140603768927480 len=59 dep=0 uid=52 oct=3 lid=52 tim=1433880335336621 hv=1464048059 ad='87cfc090' sqlid='6hbrj2tbn76dv'
select distinct staff_id from OE_ROLES where staff_id = :1
END OF STMT
PARSE #140603768927480:c=0,e=124,p=0,cr=0,cu=0,mis=0,r=0,dep=0,og=1,plh=4279656581,tim=1433880335336604
BINDS #140603768927480:
Bind#0
oacdty=01 mxl=32(24) mxlc=00 mal=00 scl=00 pre=00
oacflg=03 fl2=1000010 frm=01 csi=873 siz=32 off=0
kxsbbbfp=7fe0ddb35b88 bln=32 avl=06 flg=05
value="jibbyj"
EXEC#140603768927480:c=0,e=87,p=0,cr=0,cu=0,mis=0,r=0,dep=0,og=1,plh=4279656581,tim=1433880335336761
WAIT #140603768927480: nam='SQL*Net message to client' ela= 6 driver id=1413697536 #bytes=1 p3=0 obj#=-1 tim=1433880335336794
FETCH #140603768927480:c=0,e=37,p=0,cr=1,cu=0,mis=0,r=0,dep=0,og=1,plh=4279656581,tim=1433880335336853
STAT #140603768927480 id=1 cnt=0 pid=0 pos=1 obj=0 op='SORT UNIQUE NOSORT (cr=1 pr=0 pw=0 time=46 us cost=2 size=9 card=1)'
STAT #140603768927480 id=2 cnt=0 pid=1 pos=1 obj=24702 op='INDEX RANGE SCAN AI_OE_ROLES_3 (cr=1 pr=0 pw=0 time=34 us cost=1 size=36 card=4)'
WAIT #140603768927480: nam='SQL*Net message from client' ela= 16956 driver id=1413697536 #bytes=1 p3=0 obj#=-1 tim=1433880335353990
CLOSE #140603768927480:c=0,e=22,dep=0,type=0,tim=1433880335354080
XCTEND rlbk=0, rd_only=1, tim=1433880335354131
這是從輸出通過TKPROF運行跟蹤文件後:
SQL ID: 6hbrj2tbn76dv Plan Hash: 4279656581
select distinct staff_id
from
OE_ROLES where staff_id = :1
call count cpu elapsed disk query current rows
------- ------ -------- ---------- ---------- ---------- ---------- ----------
Parse 1 0.00 0.00 0 0 0 0
Execute 1 0.00 0.00 0 0 0 0
Fetch 1 0.00 0.00 0 1 0 0
------- ------ -------- ---------- ---------- ---------- ---------- ----------
total 3 0.00 0.00 0 1 0 0
Misses in library cache during parse: 0
Optimizer mode: ALL_ROWS
Parsing user id: 52
Number of plan statistics captured: 1
我用POJO試過,還沒有結果
public static void main(String[] args) {
String url = "jdbc:oracle:thin:@oracle-test.company.com:1521:XE";
String user = "schema-owner";
String passwd = "password";
System.out.println("Go!");
try(Connection conn = DriverManager.getConnection(url, user, passwd)){
String pQuery = "select distinct staff_id from OE_ROLES where staff_id = ?";
PreparedStatement pstmt = conn.prepareStatement(pQuery);
pstmt.setString(1, "jibbyj");
ResultSet rs = pstmt.executeQuery();
System.out.println("Execute!");
while (rs.next()){
System.out.println("Work!");
System.out.println(rs.getString(1));
}
} catch (Exception E) {System.out.println(E.getMessage());}
System.out.println("No!");
}
輸出結果爲:Go! Execute! No!
,並且跟蹤文件再次顯示查詢已運行,但未返回任何結果。常規聲明返回
Go! Execute! Work! jibbyj No!
這是正確的。
如果有人知道爲什麼JDBC PreparedStatement不能在我們的oracle數據庫上工作,我和我的dba很想知道。謝謝。
'staff_id'的數據類型是什麼?什麼是有效的查詢?你有被'char'和'varchar2'語義咬住的機會嗎?什麼是'AI_OE_ROLES_3'索引?工作查詢是否使用不同的查詢計劃? –
'ojdbc7.jar'用於Oracle 12c;你可以試試11g的官方驅動程序,['ojdbc6.jar'](http://www.oracle.com/technetwork/apps-tech/jdbc-112010-090769.html)?我會假設新的驅動程序是向後兼容的,但仍然可能至少值得一試。 –
@Justin Cave:staff_id是CHAR(8),這個查詢的作用是「從OE_ROLES中選擇不同的staff_id,其中staff_id ='jibbyj'」,我不知道其他三個問題的答案,但會問我的dba 。 – Jibbyj