Sunday, June 29, 2008

Hibernate Criteria sqlRestriction alias variable limitation

The API Documenataion of Hibernate's Criteria API's sqlRestriction method, defines as follows:


/**
* Apply a constraint expressed in SQL, with the given JDBC
* parameter. Any occurrences of {alias} will be replaced
* by the table alias. */


Make note of the {alias} placeholder in the above comments.


The catch is the only {alias} this method understands is the alias name of the root table on which the Criteria call is constructed. If more than one table is joined in the Criteria query either using the createCriteria or the createAlias method, the alias of these 'joined' tables are not understood by the Criteria API.


In order to get over this problem in our project, we had to look at the SQL generated by the Criteria object, figure out the alias name generated by hibernate and then code that in the SQL that is passed in as an argument to the sqlRestriction method.


For example in the below snippet,

Criteria c = session.createCriteria(BaseTable.class, "base");
c.createAlias(SecondTable.class, "second", CriteriaSpecification.LEFT_JOIN);


sqlRestriction method can interpret only "base" as the alias.

Friday, June 27, 2008

Hibernate's Formula

In a reporting application we were building, we had a need to display different text descriptions based on the value in a column.

The resultset we were expecting to get back was so large that it was not an option to loop through the result set and set the description programmatically.

We were using Hibernate's Criteria API for generating the report queries. What we ended up doing is writing a FORMULA with a CASE statement in the hibernate mapping files that would return the description we wanted based on the code.

<property name="errorReason" type="string"
formula="CASE WHEN err_status = -1 THEN 'INACTIVE'
WHEN err_status = 1 THEN 'NOT FOUND'
WHEN err_status = 2 THEN 'DUPLICATE'
WHEN err_status = 3 THEN 'DUPLICATE (ACTIVE)'
WHEN err_status = 4 THEN 'DUPLICATE (INACTIVE)'
ELSE ' 'END" />

When we are creating the Criteria Query, if we just add the name of the property 'errorReason', this CASE statement will be tagged along behind the scenes with the query and we will get the description we need.In the above example based on the err_status different descriptions are returned.

Saturday, March 1, 2008

Struts Multi-Select Form Wipes out Data

I had a multiple select box in a form into which users could add/remove some attributes. On submitting the system was supposed to update the database with additions/removals done by the user.

But every time i submitted the form, all the records in the specific table was getting deleted. After spending a considerable amount of time scratching my head, i tried to set the focus on that field prior to submitting the form and then it worked.

var options = document.getElementById("selectedKeys").options;
for (var i = 0; i < options.length; i++) {
options[i].selected = true;
}
form.submit();

I am not sure if it is anything to do with Struts forms, or HTML in general.

Setting css property in JavaScript calls

I wanted to dynamically set color for some of the options in a drop down list. I tried the following call:
document.getElementById("selectedKeys").options[i].style = 'color:red';

This did not work, at least in IE.

For this to work, i had to do something like this:
document.getElementById("selectedKeys").options[i].style.color = 'red';

SimpleDateFormat is lenient

Today i discovered something about SimpleDateFormat, a Java Date Formatter API.

I used a statement like,
DateFormat df = new SimpleDateFormat("MM/dd/yyyy");

In my unit test i wanted a failing test when i pass in a String "13/01/2008". The method
df.parse()
has a ParseException in its throws clause. I was hoping that, that exception will be thrown when this invalid date was passed in..

Instead it parsed it as January 1 2009.

When i did some digging around, i realised that there was a method called setLenient.

Once i made a call df.setLenient(false), prior to the parse call, it threw the ParseException when invalid date was passed in..

I found it a little weird and would have expected setLenient to be set to false by default.

Friday, February 22, 2008

ResourceBundles in Windows

I was tasked with supporting a new system ( a real pile of junk). I was given URLs to all the environments in which the system runs and was given a demo. So far so good.

I tried downloading on to my local machine, set up my IntelliJ editor, and when i ran my first report (It is a Java based reporting app), i got an error which i have seen a number of times but still could not figure out what it could be..

Error - java.util.MissingResourceException: Can't find bundle for base name com\xxxxx\xx\xxxxxxxxxxxxxxxxx\reportProcessing\ReportProcessing, locale en_US

It is the same code which worked in all the Linux machines and it broke in the following line:
return ResourceBundle.getBundle("com\xxxxxxxxx\xxxx\xxxxxxxxxxxxxxxxx\reportProcessing\ReportProcessing");

The properties file was in the same folder as the class file but it could not pick up.. I tried replacing \ with /, then \ with //. Then removed the package name and just gave the properties file name.. Nothing worked...

Then tried the following line, after reading a lot of forums and it worked...
return ResourceBundle.getBundle("com.xxxx.xx.yyyyyyyyyyy.reportProcessing.ReportProcessing");

Wanted to blog this hack for resourcebundles.