Is there a way to deterministically determine the database that is being used from a user type ? My user type needs to pass different object to preparedStatement.setObject depending on the database (whether it is HSQL or Oracle). I was planning to use DataBaseMetaData from preparedStatement as
preparedStatement.getConnection().getMetaData().getDatabaseProductName()
but I’m not sure if there is a well defined set of strings that I can compare the above with to determine the database.
The larger problem that I’m trying to solve is , we use DATE column in Oracle, whereas hibernate maps JodaDateTime to TIMESTAMP(which is the only type that can hold date and time). So Oracle promotes DATE value in the DB to timestamp before performing date comparisons. This results in poor performance because database indexes are skipped. The option of changing column type from DATE to TIMESTAMP is ruled out because it requires more space and our application does not require precision beyond seconds. Thus I plan to write a userType that converts DateTime to oracle.sql.DATE and set the parameter in preparedStatement so that there is no index mismatch. (snippet shown below):
public void nullSafeSet(PreparedStatement preparedStatement, Object value, int index) throws HibernateException, SQLException {
if (value == null) {
Hibernate.TIMESTAMP.nullSafeSet(preparedStatement, null, index);
} else {
preparedStatement.setObject(index, new oracle.sql.DATE(new Timestamp(((DateTime) value).getMillis())), Types.DATE);
}
}
The problem with the above approach is that , If I use a different database for unit testing (HSQLDB), it won’t work because HSQLDialect does not understand “oracle.sql.DATE”. This is where I need to know the DB from userType and set different objects in preparedStatement.
So, I would like to know
- If there is a better way to solve the DATE-TIMESTAMP mismatch problem
- If not, how to identify DB from a usertype correctly.
Thanks.
Use Dialect.getDialect() to retrieve your current dialect. Check the instance type to know the database .e.g below:
I am not very sure about your objective, but above should help you.