For our application to work properly we need to execute a SQL Statement on every new connection, before that connection is handed out to the application.
How do I configure a data source in WAS 7 accordingly?
We found the (deprecated) option to validate the datasource using a sql statement, which hopefully does the trick (coworker is testing it right now). This sounds wrong, since we are not 'testing' the connection, but setting it up properly. Also its deprecated so this probably will stop working with future versions of websphere
Is there a clean and correct way to do this?
The statement we'd like to execute is
ALTER SESSION NLS_SORT='GERMAN_AI'
One alternative approache: The application is hibernate based, so if we could convince hibernate to execute the statement before using a connection, this would work as well.
If it were me, I would just use the "connection test" approach:
It works!
The YAGNI principle says "worry about deprecation when it happens... if it ever happens" - probably years away or never
You will not add any business value by finding the "correct" way
You can drop this and get on with some real work that actually adds value to your project
The only downside is that it will be executed every time a connection is tested, which may be many times during the life of the connection, but so what - it's a very fast executing statement and is idempotent, so no problem.
Not a WAS expert by any means, but if you can set up Tomcat JDBC to provide your database connection pooling, it has a parameter amongst others called "initSQL". You can set that to a SQL statement that you want the connection pool to run whenever a connection is created.
Tomcat JDBC Connection Pool
A.
One way to go would be to use a custom Hibernate dialect, since you are actually specifying a 'different' way to talk with the database. I have no idea where to add the initialization code though.
Related
I am migrating an application from WAS7 to Liberty.
The existing code usesWSCallHelper.clearStatementCache(connection) in some scenarios(example : package not found in case of procedure calls).
I found WSCallHelper doesn't exist in liberty server.
Could you please help me with an alternative solution for this in liberty.
It can be either specific liberty or a general approach which will support all servers.
It would be helpful to know more about the scenario where you need to call WSCallHelper.clearStatementCache(connection), but based on what you have described I'll assume that it is only called on an error path.
In Liberty, there is no API to programmatically clear the statement cache. However, cached statements will only be matched if a number of properties are the same such as: SQL string, RS holdability, schema, isolation level, and several others.
Why you don't need clearStatementCache:
The example scenario you described for calling clearStatementCache is when the package is not found in the DB, but the package should be reflected in either the SQL string or Schema. So, assuming that your application does not retry a failed SQL string, you should not need to invoke clearStatementCache at all.
If you really really want to clear the statement cache:
As defined by the JDBC spec, Statements are child objects of a Connection. So a creative way of clearing the statement cache would be to get rid of the connection with the bad statements. Invoking connection.close() may not accomplish this because connections can be pooled by the application server, but invoking connection.abort() will get rid of the underlying connection and therefore clear your statement cache.
We should also point out that if you want a more targeted approach and have a specific statement that you want removed from the cache (or to never go into the cache in the first place), you can use JDBC spec API java.sql.Statement.setPoolable(false)
. Invoke this prior to closing the statement handle. The application server will not cache statements that are marked as poolable=false.
We have an old and big Java EE project, where at some places due to bad coding database connections has not been closed properly/or not cleaned up in catch/finally block.
We have limited our database connection pool to 100 connections. Sometimes it happens that the connection remains open and all the 100 connections are used, so the application gets hanged up. I'm trying to restructure this project, obviously I'll take care of this bad code when I get there, I'm wondering is there any lightweight Java EE framework which closes this opened db connection automatically without writing conn.close() or session.close().
Maybe something like Django where every db connection are closed at the end of every request/reposnse cycle.
I do know that I can use tools like p6spy and IronTrack SQL to look for statements that fail to close, but I'm more interested in frameworks as this project doesn't use any and I'm trying to integrate this project with a framework.
There is try-with-resource in Java 7 that may help.
Take a look
http://docs.oracle.com/javase/tutorial/essential/exceptions/tryResourceClose.html
http://docs.oracle.com/javase/7/docs/technotes/guides/language/try-with-resources.html
Here Java 7 Automatic Resource Management JDBC (try-with-resources statement) you can similar question.
Check for detecting connection leak. I am sure, you will find some tools for this.
I think you should go through a couple different frameworks, demos should be available if you search for them and choose the one which most fits your current and near future needs. I personally like Primefaces/Hibernate (if you're in JSF).
The lightweight approach in Java EE is to use simple POJO based beans called EJBs that do the DB work.
With them, in many or all cases, the DB connection is a thing that's completely handled for you behind the covers by the server.
For instance (assuming your queries for now are native SQL):
#Stateless
public class MyBean {
#PersistenceContext
private EntityManager entityManager;
public void doDBWork() {
entityManager.createNativeQuery("update foo set a = 1").executeUpdate();
}
}
In this example when you call doDBWork a transaction automatically starts and it ends when you leave that method. Somewhere in between a connection is retrieved from the connection pool and returned to it. The code is automatically totally safe in the face of exceptions or concurrent access.
I have a Java-written server which uses a connection using JDBC with SQLite which is set in auto commit mode. However all the queries end up generating a journal file and when the server restarts, the database looks never changed. Is there some general reason why this may happen? I know it would be helpful to provide some code, but I've been working on it for hours and I cannot even reproduce it with smaller amount of code...
Can anyone give a general idea of why a journal file is still there even when autocommit is set to true? Thanks!
OK I found the reason. ResultSet has to be closed whenever we're done with it.
I have a view defined in SQL server 2008 that joins 4 tables together. Executing this view in SQL Server Management Studio takes roughly 3 seconds to run and returns about 45,000 records. My application is written in Java using hibernate to simply do a "from MyViewObject" query in HQL. When this is run, the execution time is consistently around 45 seconds. I have also tried simply using JDBC to run this query and received the same level of performance, so I've assumed it has nothing to do with hibernate.
My question: What can I do to diagnose this problem? There is obviously something different between how Management Studio is running the query vs how my application is running the query but I have not been able to come up with much.
The only thing I've come up with as a potentially viable explanation is an issue with the jtds library that contains the driver for SQL Server in Java.
Any guidance here would be greatly appreciated.
UPDATE
I went back to trying pure JDBC and tried adding the selectMethod and responseBuffering attributes to my connection string but didn't get any improvements. I also took my JDBC code from my application and ran it from a test program containing nothing but my JDBC code and it ran in the expected 3 seconds. So to me this seems environmental for the application.
My application is a Google Web Toolkit(GWT) based app, and the JDBC code is being run in my primary RPC Servlet. Essentially, the RPC method receives the call and immediately executes the JDBC code. Nothing in this setup gives me much indication of why the performance is terrible though. I am going to try the JDBC 3.0 driver and see if that works any better, but it doesn't feel like that will fix the issue to me quite yet.
My goal for the moment is to get my query working live with JDBC and then switch it back over to Hibernate so I can keep the testing simple enough. Thanks for the help so far!
UPDATE 2
I'm finally starting to zero in on the source of the problem, though still no idea what the actual issue is. I opened up the view in SQL Server and copied the SQL statement (rather large) exactly into my code and executed it using JDBC instead of pulling the data from the view and most of the performance issues are gone. It seems that some combination of GWT, SQL Server Views and JDBC is not working properly here. I don't see keeping a very large hand-written query in my code as a long term solution, but it does offer a bit more insight.
<property name="hibernate.show_sql">true</property>
setting this will show you the SQL query generated by hibernate. Analyze the query and make sure you are not missing a relationship.
reply for Update 1 and 2:
Like you mentioned, ran the query on your sql query and it seems like it is fast. So another thing to remember about hibernate is that it creates the object that is returned by your query (of course this depends if you initialize lazy obj. Dont remember what it is called). How many objects does your query return? also you can do a simple bench on where the issue is.
For example, before running the query, sysout the current time and then sysout the current time after. do these for all the places that you suspect is slowing your application down.
To analyze the problem you should look up you manual for tools that display the query or execution plan. Maybe you're missing an index on a join column.
I have never connected to a database in java before. May I know if I should go about accessing a derby database with servlet?
I have checked this: How do I access a database from my servlet or JSP?
But I saw comments on the article saying that this is a bad way to connect. Could any one explain or show me the best way to that I should code to access my derby database?
Thank you very much.
They are all right indeed, in suggesting that. We don't don't access database directly from Servlets or JSPs, these both are meant to be web tier, isn't it?
So, what to do? Grab a JDBC tutorial. The official one is an excellent choice here. That will give you a good idea about connecting to database from Java, and grasp over JDBC API. After that you should go and read about DAO pattern, and how we employ that in real apps.
Moreover, I think you also should read about MVC pattern, because it seems to me that you are not very clear on that as well.
Once you understand all these and come up with a toy like application using all these stuff. Next step would be to have a look into Connection Pooling mechanism.
Since you are using servelt you must be using a container line Apache Tomcat. You should look to define a connection pool like this http://tomcat.apache.org/tomcat-5.5-doc/jndi-datasource-examples-howto.html. If you are using any other container then that will also have similar setup.
Other option is to create a separate DBManager kind of class which looks after initializing and returning connection. This class you can use in the servlet.
Using JDBC and having your app server's application pool is a good start. You can also use some API to make your life easier like Hibernate.
It is a "bad way", because it doesn't make use of a (JNDI-managed) connection pool to obtain connections. Although acquiring a connection costs "only" a few hundred milliseconds, this has impact in a busy multiuser environment. A connection pool will worry about opening and closing connections and release them immediately on every getConnection() call so that it effectively costs almost zero milliseconds. If you sum that up in a busy multiuser environment, then the differences are noticeable.
A connection pool is usually to be configured in flavor of a JNDI datasource which is managed by the servletcontainer in question. As you didn't mention which one you're using, I can at highest point to one of my answers which contains a Tomcat 6.0 targeted example: here.
Hope this helps.