Glassfish v2 Create Domain – Keytool Error:java.io.EOFException

Yesterday night, I had to work on some interesting stuff with my application’s deployment tool. We have a Ruby RakeFile to automatically create glassfish domain and deploy apps. As I was running the tool creating domains atleast 10 times or so, suddenly at one stage I got an error while creating glassfish domain…the error was “keytool error: java.io.EOFException”. I thought some evil spirits has got into my laptop at the wee hours…hence gave up and went off to sleep.

Today morning, I thought let me give this a fresh look…
And I learnt that you can turn on debug logging by adding -DDebug in the asadmin script. This helped me to say that there is something wrong with a keystore that Glassfish was looking for while creating the domain.

After couple of rounds of googling, I realized that the keystore is stored in my home folder with the name .asadmintruststore. Apparently the file size was just 1 byte. I just deleted the file and now the creation of domain went thru fine 🙂

On thinking what could have corrupted the keystore, I realized once when the creation of domain was going thru, I had abruptly killed the operation by Ctrl+C, which could possibly have corrupted the keystore!

Hope this helps someone who bumps on this issue 🙂

Moral of the story : Dont try to stay late and work…sleep early 🙂

Ubuntu : On Hibernate , machine restarts

Uff! I have been trying to get Hibernate (Suspend-to-disk) option work properly with Ubuntu in my home PC, versions after versions, starting from Dapper Drake (v6.04) to the recent Karmic Koala(v9.10).

Even though the actual hibernation(meaning, dumping the memory content into the Swap partition of my disk) happens fine, my machine suddenly restarts within 3 seconds after a complete halt. I have been going crazy to even figure out the sentence to help google find what I am looking for from the net.

Finally, at 9:45pm with half sleepy eyes, I managed to find some help after going thru lines and lines of posts from various forums…that I had to add a file to my /etc/pm/conf.d and add the following line to the file

HIBERNATE_MODE=shutdown

the hibernation happens properly and my machine goes to sleep happily thereafter 🙂
Thanks to this post
PS: Folks, also please ensure that you specify where your hibernate file is present to Grub to ensure it wakes up instead of booting afresh. You have to add resume=/dev/sda5(swap partition). But I also noticed recently in my dad’s netbook, without this resume option, GRUB properly wakes up from Hibernation. God knows how!…Something to research on sometime later….Will post my findings if any 🙂

Unexpected behavior in Mysql JDBC Driver 3.x

Till very recently, we have been using v3.x of Mysql JDBC Driver in our application. Our application stores serialized objects as bytes in a blob field in Mysql. When we tried to read the data from the field using resultset.getObject(), Mysql Driver threw a ClassNotFoundException as at that particular instance, the class of the serialized object was not present in the classpath.

On investigating further, we learnt that Mysql reads the first 2 bytes of the data in the field and if it finds that it is a byte array representation of a serialized object, it AUTOMATICALLY attempts to deserialize the object, which is quite unexpected of Mysql to do because there is no guarantee that the serialized object’s class would be present in the classpath.

Thankfully, what we found is that the latest version of Mysql JDBC Driver v5.1.6 does not have this problem. And the behaviour is controlled by a property that is available in the mysql connection object called “autoDeserialize”. Thankfully, the default value of the property is “false”.

A sample Presenter Implementation for Rails

Recently, my friend Venkat introduced me to the Presenter Pattern and we were discussing on its advantages and the situations where using a Presenter would be useful.

Thanks to Jay Fields for elaborating on the Presenter and also providing a sample Presenter implementation in one of his blogs.

I have modified the sample Presenter class provided by Jay, fixed a few minor issues and have made it available here.

Adding JNDI DataSource support for Rails-Integration

In the past few weeks, we have been working on getting our rails application to run on JRuby. Ofcourse, we were successful in packaging our application as a J2EE .WAR archive, thanks to Rails-Integration and ARJDBC, without which this would not have been possible.

While we were at it, we also wanted to check out the jndi data source support of ARJDBC as well as Rails-Integration projects.

After spending some time, we discovered that the ARJDBC v0.2.3 had a bug in jndi_adapter.rb. The method “Jndi_Connection” was not present and instead there was a method called “Jdbc_Connection“. I had to correct the same before getting the ARJDBC to support JNDI Data source. Apparently, I also found that this issue does not exist in the trunk version of ARJDBC.

Rails-Integration comes with rake tasks to create a war file for the rails app and configure jetty
web server. To configure JNDI support, the following changes are required to be done…

1. Add the data source configuration to the jetty.xml file. However, Please note that everytime you run the rake task – war:standalone:run, the jetty.xml is recreated. Therefore, I suggest that you modify the rails-integration war plugin library, called run.rb and add the below entries in the appropriate place.

For instance, for oracle data source,

jdbc/MyApp

jdbc:oracle:thin:@192.168.2.23:1521:swami
myapp
myapp

 

For the full list of configuration details for various databases, please go here.

Please note that, as per jetty documentation, the above entries can be updated in jetty-env.xml or jetty-web.xml as well. The scope of this configuration depends on where you put this configuration information.

2. Now, search for the section

in your jetty.xml(or the run.rb file) and add the following entries after the two entries…

org.mortbay.jetty.webapp.WebInfConfiguration
org.mortbay.jetty.plus.webapp.EnvConfiguration
org.mortbay.jetty.plus.webapp.Configuration
org.mortbay.jetty.webapp.JettyWebXmlConfiguration
org.mortbay.jetty.webapp.TagLibConfiguration

3. Now, we need to specify the JNDI Logical Name for our web application, add the following entries in your web.xml under WEB-INF folder of your war file. However, Please note that every time you run the rake task – war:standalone:run, web.xml is recreated. Therefore, I suggest that you modify the rails-integration war plugin library, called create_war.rb and add the below entries in the appropriate place.

My DataSource Reference
jdbc/MyApp
javax.sql.DataSource
Container

4. Lastly, to add JNDI support, jetty requires two more libraries Jetty-Naming and Jetty-Plus.
The best way to do this is to modify the rails-integration war plugin library, called war_config.rb. Search for the word add_jetty_library and append the following lines telling the war_config to download the two libraries as well.

add_jetty_library(maven_library(‘org.mortbay.jetty’, ‘jetty-plus’, ‘6.1.1’))
add_jetty_library(maven_library(‘org.mortbay.jetty’, ‘jetty-naming’, ‘6.1.1’))

5. Now for the final step, modify your database.yml to use jndi…

production:
adapter: jndi
jndi: java:comp/env/jdbc/MyApp
driver: oracle

Thats it! Your rails web application is ready to run with JNDI Data source.

Rails Integration – Session Restore restores symbols as Strings

In the last one week, our focus was to deploy our rails app as a war file and run on jetty, with the help of Rails Integration plugin.

We noticed that we had problems with respect to accessing our session variables across pages. We narrowed down the problem to “JavaServletStore” class bundled as part of the Rails Integration plugin.

Since Java is not aware of Ruby Symbol objects, these symbols are converted to string and updated into the Session Object. And now, when the session is restored, the data stored as symbols originally in rails would be available as Strings. Hence if we look for the symbols we would not find them in the session.

As a temporary work around, we modified the restore method to convert the keys as symbols. This would just work for us as we use symbols all thru when writing and reading from Session.

Our temporary fix is given below :

# Restore session state from the Java session
def restore
@session_data = {}
java_session = @java_request.getSession(false)
if java_session
names = java_session.getAttributeNames
while names.hasMoreElements
name = names.nextElement
@session_data[name.to_sym] = java_session.getAttribute(name)
end
end
@session_data
end

The proper fix should ensure that “update-session” method stores some info about the type of the object and appropriately convert them during the “restore-session”. May be there is a better solution.

JRuby and Rails-Integration

I must acknowledge that am one of the fortunate folks to have got bitten by the Ruby bug lately…and we have been developing applications with Ruby on Rails in our organization. Though we are excited about Ruby and Ruby On Rails, we always had that concern as to how do we convince the IT Team in the Banks(this is where our applications are deployed) to deploy Ruby application in Production.

We were quite excited about the JRuby momentum and were following the progress in the Rails-Integration Project recently. Now, we certainly have an opportunity to develop in Rails and deploy in the well established J2EE platform. Kudos to JRuby team and the Rails-Integration team to make this a reality 🙂

Last week, we took our Rails application and played around with Rails-Integration to create a .war archive of our app and deployed successfully in Jetty with some minor hiccups, which I would further describe in my future posts.

Keytool and foreign locale problems

Recently, we hit upon an very interesting(!?!) problem using Keytool inside our application.

We have a customer in Thailand who complained that the self-signed certificates generated in our application(which in turns uses Keytool) have got the Certificate “Valid From” Date and “Valid To” dates completely wrong.

The catch here is that Thai Calendar Year is 543 years ahead of the Julian Calendar. In other words, year 2006 in English Calendar is equivalent to year 2549 in Thailand Calendar.

Lets say I generate a self-signed certificate using Keytool with my machine running on Thai Locale, the Year portion of “Valid From” should be stamped as 2549(2006 is the current year + 543).

And if the validity of the certificate is 3 years, then the Year of Expiry is 2552.

But, Keytool just ignores this whole difference in the Calendars and lives with the all famous Y2K Bug!!!

The Certificate would show as Valid from 2049 to 1952!!! Howzzat???

Any amount of googling thru the java sun forums and other newsgroups, I could not find anything that talks about this problem/behavior.

Am I missing something big here??? Hope some one some day will help me resolve this mystery!

I am giving the exact keytool syntax I used for easy reference for anyone who would like to try this out 🙂

1. Generate Self Signed Certificate
keytool -genkey -keyalg rsa -sigalg sha1withrsa -keysize 1024 -storetype jceks -validity 1095 -storepass storepass -keypass keypass -dname CN=MyName,O=MyOrganization,OU=MyDepartment ST=Karnataka,L=Bangalore,C=IN -keystore test.jceks

2. Export the Certificate in .der format
keytool -export -file cert.der -keystore test.jceks -storetype jceks -storepass storepass

Issue with Gzipped Content over SSL

After we upgraded our web application in our customer’s place, lots of users started complaining that the webpage is not getting downloaded to their browser…

Observation

  • This issue happens only in Windows 98 and some machines with WindowsXP without any service packs. And that too only when accessing the server with HTTP 1.1 compression ENABLED. We confirmed this by requesting the customer to turn off HTTP 1.1 compression and he confirmed that the application worked fine.
  • Fortunately, we were able to reproduce this issue locally in one of our Test Machines running Win98. We found that this issue happens only when we go thru Web Server. When we accessed the application via Application Server, the issue was NOT reproduced.
  • The above observation led us to another important clue, that this issue could be something to do with SSL, as that is one major difference between Web Server and App Server.

Based on all the above observation, we concluded that this issue happens only with HTTP 1.1 enabled Browser accessing the Bali Server via SSL. And the machine is running Win98 or plain Winxp(without any service packs) operating Systems.

With the above information at hand, we started monitoring the HTTP Traffic between Browser and Server using some Network Sniffing tools and found that a particular javascript file called “FMProduct.js” seems to be the culprit. Even though the file was downloaded to the Browser, the file never got written to the Temporary Internet Files cache.

Concluding that this file is the one that could be causing all the problems we tried to take the file separately and tried to access it via Weblogic Web Server and we were successfully able to reproduce the problamatic behavior.

To eliminate the possibility of Weblogic Server in playing a role in the above erratic behavior, we hosted the FMProduct.js on Apache Web Server. And now, we were able to download the file without any problems from any browser.

Now, we concluded that apart from the combinations of SSL, HTTP1.1, Win98/xp, there is yet another variant, Weblogic Server playing a role in the erratic behavior.

We monitored the network traffic when accessing Apache Web Server as against Weblogic Web Server. We found something very interesting. That is, Weblogic serves the files in a CHUNKED manner with chunk size of 4072 bytes(we are not sure what is the significance of this number). Apache serves the whole content of the file in one chunk.

The problem occurs ONLY when the last chunk is of size between 1 to 9 bytes. In other words, if the size of the file is 4074 or 4081 or 8119 etc…
The size of compressed version of FMProduct.js is 20362 – which means 5 chunks of 4072 and the last chunk contains 2 bytes.

Resolution

It certainly seems that Microsoft has fixed this erratic behavior with SSL + HTTP 1.1 combination, and hence the latest version of Windows XP (SP2) does not have this erratic behavior.

Additionally, we shall also review our build process to see if we can add a check to see if the file size falls into this magic number and if so, try and add some more insignificant characters to increase the file size.

Please note that the above erratic behavior is NOT reproduced in Mozilla FireFox? browser.

The attached Ruby Script helps print out all the files that fall into this wierd pattern.

require “find”
if ARGV[0].nil?
puts “Usage: ruby FileChunkSizeFinder.rb [path_of_baliweb]”
exit
end

Find.find(ARGV[0]) do |file|
if File.file?(file) && File.basename(file) =~ /\.gz$/ && (1..9) === File.size(file)%4072
puts file + ” ==> ” + File.size(file).to_s
end
end

Exporting Private Key from iPlanet Web Server

In quite a few occassions, we would have to sniff SSL Traffic between the browser and a iPlanet Web Server. To sniff SSL using ClearWatch Tool, we require the Private Key file in PEM format.

IPlanet stores keys internally. Hence we need to go thru a few steps to achieve the above…

Step 1 :
Firstly, the Key will have to be exported to a PKCS#12 file.

To export to a PKCS#12 file, Use the pk12util command that ships with iplanet. This file is generally available under Servers\bin\https\admin\bin folder

Syntax :
pk12util -o exportfile -n certname [-d certdir] [-P dbprefix]

Example :
pk12util -o c:\temp\pkey.txt -n Server-Cert -d c:\iplanet\servers\alias -P dbprefix

In the above dbprefix is nothing but the prefix for the Key file available under Servers\alias folder. If the key file is xyz-key3.db, then dbprefix is ‘xyz’

Step 2 :
Once you have a pkcs12 file containing a private key, you can convert it to a PEM file by using the freely available OpenSSL tool,

Syntax :
openssl pkcs12 -in server.p12 -out server.pem -nocerts -passin pass:yourpassword -passout pass:dummy

where “server.p12” is the original PKCS#12 file you are converting and “yourpassword” is the password that is associated with the PKCS#12 file.

Step 3 :
Now, we can remove the Password Protection on the Key by running the following command.

openssl rsa -in server.pem -out server.key -passin pass:dummy