Because none of the JDBC operations have a concept of timeout, is it advisable to try to close JDBC connection of the overdue operation from the other thread if timeout is exceeded?
I am aware of Statement.cancel method, however it does not seem to work in all cases. Also, the driver that I am using does not respond to interrupts.
I think Connection.close is, unfortunately, the lowest common denominator that can be used to prevent resource leakage in case the database operation had ran amok.
I am aware that when using connection pooling I have to close the real connection object.
For derby it should be ok:
http://db.apache.org/derby/docs/10.8/devguide/cdevconcepts23499.html
According to the JDBC spec you can share Connections and Statements with multiple threads
The best answer is, it depends on what driver you are using. But from the jdbc stack point of view, it should be ok.
I'd wrap that operation in a ThreadPoolExecutor with a timeout. It'll give you more control over what's happening.
Related
I've been researching all around the web the most efficient way to design a connection pool and tried to analyze into details the available libraries (HikariCP, BoneCP, etc.).
Our application is a heavy-load consumer webapp and most of the time the users are working on similar business objects (thus the underlying SQL queries executed are the often the same, but still there are numerous).
It is designed to work with different DBMS (Oracle and MS SQL Server especially).
So a simplified use case would be :
User goes on a particular JSP page (e.g. Enterprise).
A corresponding Bean is created.
Each time it realizes an action (e.g. getEmployees(), computeTurnover()), the Bean asks the pool for a connection and returns it back when done.
If we want to take advantage of the Prepared Statement caching of the underlying JDBC driver (as PStatements are attached to a connection - jTDS doc.), from what I understand an optimal way of doing it would be :
Analyze what kind of SQL query a particular Bean want to execute before providing it an available connection from the pool.
Find a connection where the same prepared statement has already been executed if possible.
Serve the connection accordingly (and use the benefits of the cache/precompiled statement).
Return the connection to the pool and start over.
Am I missing an important point here (like JDBC drivers capable of reusing cached statements regardless of the connection) or is my analysis correct ?
The different sources I found state it is not possible, but why ?
For your scheme to work, you'd need to be able to get the connection that already has that statement prepared.
This falls foul on two points:
In JDBC you obtain the connection first,
Cached prepared statements (if a driver or connection pool even supports that) aren't exposed in a standardized way (if at all) nor would you be able to introspect them.
The performance overhead of finding the right connection (and the subsequent contention on the few connections that already have it prepared) would probably undo any benefit of reusing the prepared statement.
Also note that some database systems also have a serverside cache for prepared statements (meaning that it already has the plan etc available), limiting the overhead from a new prepare from the client.
If you really think the performance benefit is big enough, you should consider using a data source specific for this functionality (so it is almost guaranteed that the connection will have the statement in its cache).
A solution could be for a connection pool implementation to delay retrieving the connection from the pool until the Connection.prepareStatement() is called. At that time a connection pool would look up available connections by the SQL statement text and then play forward all the calls made before Connection.prepareStatement(). This way it would be possible to get a connection with a ready PreparedStatement without the issues other guys suggested.
In other words, when you request a connection from the pool, it would return a wrapper that logs everything until the first operation requiring DB access (such as prepareStatement() is requested.
You'd need to ask a vendor of your connection pool functionality to add this feature.
I've logged this request with C3P0:
https://github.com/swaldman/c3p0/issues/55
Hope this helps.
How would you detect a lost connection using JDBC in a reliable and an efficient way? Currently I'm using a Vertica JDBC driver. I don't think I can use connection pools as I need to control to which node I'm connected at all times. Things I thought of so far:
Assume SQLException is a lost connection. Seems unreliable.
Check ex.getCause and look for a socket exception. Not sure if checking cause is a good practice.
Check error code which I know is a case for a lost connection. Also seems a bit unreliable.
Edit:
I've tried isValid and isClosed. isValid throws an exception and isClosed always returns false regardless.
From version 1.6, you can theoretically use the Connection.isValid method but I am not sure if every vendor supports it. An other alternative is using a connection pool which manages connections and you get the connection from them and release it when you don't need it. Connection pools take the responsiblity of maintaining connections and they always provide valid connections.
We have seen connection droughts in our system every once in a while, and the problem seems to be that Sessions are not being returned to the connection pool quick enough. I wrote a test that seems to confirm using Session.disconnect() on the sessions (after being done with one) will solve this problem. However, I also timed these calls, and it seems like using disconnect is increasing running time by 3 times.
According to the docs (http://docs.jboss.org/hibernate/core/3.5/api/org/hibernate/Session.html#disconnect() ), disconnect should be returning it to the connection pool. However, the doc also says it "closes" the connection. I'm not sure what it means because I know for a fact that Session.close() does more than disconnect, and what good would a connection pool be if you close the connection before returning it?
In any case, I'm wondering why a method that returns the session to the connection pool would be anything but instantaneous and essentially free. Surely thats the whole point of a connection pool, right?
Any ideas would be appreciated.
I not very good in java.
I have made a website for a client but am continuously getting an error like Server connection failure during transaction. Due to underlying exception: 'com.mysql.jdbc.exceptions.MySQLSyntaxErrorException: User root already has more than 'max_user_connections' active connections'.
The website hosting that I am using provides only 10 max_user_connections. But if I continuously use that site, I get this error because of continuously hits on the webserver.
What can be the reason behind this?
Am I not closing the connections right?
I have closed all the connections using con.close().
Please help
Regards Apurv
To open the connection I have used
Connection con=null;
Statement st=null;
Class.forName("com.mysql.jdbc.Driver").newInstance();
String useq="root";
String paq="manager";
String url="jdbc:mysql://localhost:3306/jayna?autoReconnect=true";
con=DriverManager.getConnection(url,useq,paq);
st=con.createStatement();
To close the connection I have used
if(rs!=null){
rs.close();
}
if(st!=null){
st.close();
}
if(con!=null){
con.close();
}
I haven't used a database pool but what can be the use of that when I am closing each of the connection properly??
This seems like a case of connection leak.
Are you sure, you have closed all the connections?
Conneciton.close() throws IOException. Check if it is successfully able to close connections.
Use netstat or other tools to find whether connections are really closed or are in WAITING state or something.
I think you should increase number of connections. Because if there are 10 slow query and you get 11 requests to your site 11 request couldn't be processed and you get this error.
So:
Try increase a number of connections.
Try to find slow queries(using slow query log) and optimize them
Connection pooling is a technique to provide a set of ready-to-use connections, one of the advantages being that you save the creation/opening time on each call. Another advantage is that the connection pooler can help detect abandoned connections, ie connections that the application forgot to close.
There's a standard connection pool in Tomcat, for 5.x version Tomcats look here for some info, for version 6 look here and for version 7 info can be found here. Its removeAbandoned and logabandoned features can help you determine whether your app really forgets to close connections, or 10 just isn't enough - see Andrej's suggestion, you should profile your queries.
As others have said, you either are not getting connections closed or your application simply needs more than 10 concurrent connections under some load conditions.
If the error always occurs on the 11th request, it's likely you're never getting the connections closed.
If it occurs sometime later, unpredictably, and goes away on its own, it's more likely 10 simply isn't sufficient for certain load scenarios.
If it occurs later, unpredictably, but never goes away on its own, it's possible you're failing to close connections only in specific cases that aren't hit every time.
If 10 is too small for some load scenarios (option 2), you should both check your queries and code logic to ensure you're not holding connections way longer than necessary and you should probably try to move to a Connection Pool, as others have suggested. Among other things, creating new Connections from scratch has more overhead than reusing them from a pool, so that could be causing individual accesses to take much longer than necessary.
This problem can be solved by using a Singleton class structure for initializing connection objects.
Using the Singleton pattern, whenever a connection object is initialized, rather than creating a new object, it will look for existing instance of connection object and use that one, if it exists.
I would like to ask, if I am going to use a single connection in the whole program, do I need to use a connection pool? Does using a connection pool give me better performance?
For example, I may open a static connection and use it for multiple sql query, then finally when the program finish, I close the connection. Most of the program I am dealing with, are not multi-threaded, so I don't see the benefit of using connection pool in such situation. Would anyone can answer my question, thank you.
Thanks in advance.
For example, I may open a static
connection and use it for multiple sql
query, then finally when the program
finish, I close the connection. Most
of the program I am dealing with, are
not multi-threaded
Sounds like you don't need a connection pool.
You don't ever need a connection pool.
It can be useful if you require enforcement on having a limit number of connections.