我試圖使用自己的連接池來處理數據庫連接,但由於某種原因它似乎被阻塞,即使我使用了一個線程,有人可以幫我指出我的錯誤。帶線程的Java Servlet阻塞?
這是帶有線程類的servlet代碼。
protected void processRequest(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
// PrintWriter out = response.getWriter();
OutputStream ostream = response.getOutputStream();
PrintStream out = new PrintStream(ostream, true, "UTF8");
try {
response.setContentType("text/html");
String test = request.getParameter("test");
System.out.println("Received text: " + test);
if(test.equals("free"))
{
for (int i = 0; i < list.size(); i++) {
dbcm.freeConnection(list.get(i));
}
list.clear();
}else
{
GetConnThread gct = new GetConnThread(test, dbcm);
gct.start();
}
} catch (Exception e) {
e.printStackTrace();
out.println("fail");
} finally {
out.close();
}
}
private class GetConnThread extends Thread
{
private String test;
private DBConnectionManager dbcm;
public GetConnThread(String test, DBConnectionManager dbcm)
{
this.test = test;
this.dbcm = dbcm;
}
public void run()
{
try {
Connection conn = dbcm.getConnection(test);
list.add(conn);
System.out.println(conn);
System.out.println("list size: " + list.size());
} catch (Exception e) {
e.printStackTrace();
}
}
}
這是DBConnectionManager
public synchronized Connection getConnection(String test) throws CGFatalException {
Connection con = null;
boolean connectionIsValid = false;
if (freeConnections.size() > 0) {
con = (Connection) freeConnections.firstElement();
freeConnections.removeElementAt(0);
connectionIsValid = validateConnection(con);
if (connectionIsValid == false) {
con = getConnection(test);
}
} else if (maxConn == 0 || checkedOut < maxConn) {
con = newConnection();
connectionIsValid = validateConnection(con);
if (connectionIsValid == false) {
con = getConnection(test);
}
}else
{
System.out.println("No available connections for " + test + ", try again in 2 secs....");
try {
Thread.sleep(2000);
con = getConnection(test);
} catch (Exception e) {
e.printStackTrace();
}
}
if (con != null && connectionIsValid == true) {
checkedOut++;
}
System.out.println("checkedOut: " + checkedOut);
System.out.println("maxConn: " + maxConn);
return con;
}
我設置最大連接到2,從而後我調用servlet它進入這行代碼的第三時間getConnection方法:
System.out.println("No available connections for " + test + ", try again in 2 secs....");
當我第四次說它時,我期待
System.out.println("No available connections for " + test + ", try again in 2 secs....");
作爲一個單獨的線程開始,但第三個調用似乎阻止它,因爲我希望調用「free」來清除連接並且一切都恢復正常,所以預計會出現無限循環。
我想你需要提供更多的信息 - 可能是一個日誌文件。你說_無限循環是期待的,但是你沒有向我們展示一個無限循環。第三個電話似乎阻止了它,但沒有證據表明這一點,所以我們不得不依靠你的猜測工作。 – Tim 2012-02-13 03:25:00
「無限循環」是由遞歸調用在thread.sleep(2000)之後試圖獲得「空閒」連接引起的。 – Maurice 2012-02-13 03:27:58
除非是純粹的愛好目的,否則如果您已經不知道線程和併發性如何工作,請執行** not ** homegrow連接池。去選擇一個現有的連接池庫。每個自我推崇的servletcontainer都附帶內置的連接池設施,包括Tomcat。利用它。真。連接池是一個非常重要的健康Web應用程序的人工製品,你不想在0理解的情況下自行生成。 – BalusC 2012-02-13 04:40:12