Category Archives: J2EE

Commons Net FTP and Active vs. Pasv connections

In my current project at work I needed to programmatically FTP some XML documents to a remote system and so in my continuing quest to try and use every open source Java library that exists in the wild (not really, but it seems like it sometimes), this week I present to you Jakarta Commons Net. This project “.. implements the client side of many basic Internet protocols. The purpose of the library is to provide fundamental protocol access, not higher-level abstractions.” which of course includes FTP.

It’s fairly easy to get started since the JavaDocs for the FTPClient class include a couple examples, so I won’t illustrate that. The reason I’m writing is because I ran into an issue where the tests I wrote and executed on my desktop didn’t work once I deployed them to the server. Active and Passive mode are well documented elsewhere, but they don’t manifest themselves very clearly when you’re looking at a stack trace. For instance, the code to connect to an FTP server and send a file using Commons Net looks like this:

String server = "ftp.yoursite.com";
FTPClient client = new FTPClient();
client.connect(server);
client.login("username", "password");
File file = new File("testfile.txt");
InputStream is = new FileInputStream(file);
client.storeFile("testfile.txt", is);
client.disconnect();

Straightforward and it worked fine from my desktop. The same code moved to a server in the DMZ at work didn’t work and threw a java.net.SocketException, saying java.net.SocketException: Connection reset“. The FTPClient class, as a subclass of the SocketClient, contains a method isConnected(), which, when invoked, returned true. So I could login, change the working directory and disconnect with no errors thrown, but as soon as I tried to send a file I got an SocketException. The simple solution was to change the mode from Active to Passive using the enterLocalPassiveMode() method, which would have been obvious if I had known a bit more about the FTP protocol. In short, active mode FTP means that your client connects to the FTP server on the command port and then the FTP attempts to make a connection to your client for the data port, which isn’t going to work in a completely locked down environment. Changing to passive mode means that the client connects to the server for both command and data port transmission.

Hibernate: Returning N records in a random order

Hibernate: Returning N records in a random order

I was pleasantly surprised by Hibernate yesterday when I tried need to have a web page show a listing of 3 randomly chosen articles. Using SQL Server, you’d write a query like this:
SELECT top 3 * FROM mytable ORDER BY newid()
The ‘top n’ syntax is specific to SQL Server, which makes it non portable. I saw that the Query class has a method that allows you to restrict the number of rows that are returned from a query:

String query = "SELECT * FROM mytable ORDER BY newid()";
Query q = session.createQuery(query);
q.setMaxResults(3);

but I thought that would be inefficient because Hibernate would have to retrieve a large resultset and then only return the first n rows. Turns out that Hibernate actually figures out that SQL Server is the underlying platform and uses the ‘TOP’ keyword [look at the getLimitString() method]. Hibernate has made what used to be proprietary SQL Server sql, portable across any database platform that Hibernate supports. Case in point — if you use the same method q.setMaxResults(3) when using MySQL, Hibernate will automatically use the MySQLDialect and substitute the limit keyword that MySQL uses.

Of course, Hibernate can’t do everything… yet. The second part of my query ordered the results in a random fashion. You can do that in SQL Server using the newid() function; MySQL accomplishes the same thing with the rand() function.

UBL 1.0

Last week Tim Bray mentioned the May 1st release of UBL 1.0, which he defines as “… a set of general-purpose XML-encoded business documents: orders, acknowledgments, packing slips, invoices, receipts.” He goes on to compare UBL to HTML, saying that because it (UBL) is a generic format rather than a format made for a particular industry (just like HTML was a generic, simpler subset of SGML), it has a chance to become the HTML of the business document world (read: explosive growth, eventual ubitquity). Tim quotes an email from Jon Bosak on some of the other reasons for the creation of UBL:

· Developing and maintaining multiple versions of common business documents like purchase orders and invoices is a major duplication of effort.
· Creating and maintaining multiple adapters to enable trading relationships across domain boundaries is an even greater effort.
· The existence of multiple XML formats makes it much harder to integrate XML business messages with back-office systems.
· The need to support an arbitrary number of XML formats makes tools more expensive and trained workers harder to find.

My current project, which should be released soon, utilizes software from many different companies: tax software, credit card software, shipping rate software, custom software written by the company that manages the distribution of product, etc.. Obviously having a single format to work with would decrease the time I spend a) digging through each companies documentation trying to understand their format and b) wiring up the custom documents for each format, so I’m definitely looking forward to the day when I can use UBL.

For anyone interested, it looks like there is a smattering of support for UBL out there in the Java world: http://softml.net/jedi/ubl/sw/java/, https://jwsdp.dev.java.net/ubl/, http://www.sys-con.com/story/?storyid=37553&DE=1. For further information regarding UBL, see the OASIS UBL TC web page at:
http://www.oasis-open.org/committees/tc_home.php?wg_abbrev=ubl

ColdFusion MX and java.sql

Last week a reader sent me an interesting problem. When deleting a record from a database using a standard <cfquery> tag you don’t get any indication back that let’s you know whether or not the row or rows in question actually existed, nor do you get back any indication as to how many rows might have been affected. He wanted to be able run a single query that deleted a record AND let him know whether or not the record existed. He thought (correctly) that there was a way to do this in Java and wondered if I could write a CFX tag to do it for him. I could, but it would be much easier to do it in <cfscript>. In Java, you would write this:

// replace the package/class name of your db driver
Class.forName("org.gjt.mm.mysql.Driver");
// replace w/ your server, database name, username & password
String conurl = "jdbc:mysql://server/db?user=u&password=p";
Connection con = DriverManager.getConnection(conurl);
PreparedStatement ps;
ps = con.prepareStatement("DELETE from table_name where id = 3045");
int result = ps.executeUpdate();
con.close();

In short, you load the appropriate database driver (I’m using MySQL in the above example), obtain a connection to the database using the DriverManager class, create a PreparedStatement, and then call the executeUpdate() method. This method returns an int: “… either (1) the row count for INSERT, UPDATE, or DELETE statements or (2) 0 for SQL statements that return nothing.”

Using the above sample it’s pretty easy to do the same thing in ColdFusion using <cfscript>:

<cfscript>
clazz = CreateObject("java", "java.lang.Class");
// replace the package/class name of your db driver
clazz.forName("org.gjt.mm.mysql.Driver");
driverManager = CreateObject("java", "java.sql.DriverManager");
// replace w/ your server, database name, username & password
conurl = "jdbc:mysql://server/db?user=u&password=p";
connection = driverManager.getConnection(conurl);
query = "DELETE from category where id = 3045";
preparedStatement = connection.prepareStatement(query);
result = preparedStatement.executeUpdate();
WriteOutput("result = " & result);
connection.close();
</cfscript>

Further, you can test the value of the result variable so that you can show a custom message to a end user or perform some other type of business logic:

if (result == "0") {
  WriteOutput("No records were deleted.");
} else if (result == "1") {
  WriteOutput("One record was deleted.");
} else {
  WriteOutput(result & " records were deleted.");
}

Hibernate: Non object retrieval

Hibernate has significantly reduced the amount of time I’ve spent on the writing and maintaining SQL in the applications I’m working on. Because it exists to map data from Java classes to database tables and back, there aren’t alot of examples on the site if you need to get non object data out of the database (for instance if you’re doing reporting on the existing data). That’s not to say that it’s not possible! Given a Query object, call the list() method and then iterate over the resulting List. Calling the get() method on the list results in an array of Objects (which is analogous to a row returned from a resultset). Then you’ll just need to retrieve the appropriate element of the array given your SQL query (where the order of the items in your ‘SELECT ..’ SQL query determines the order in which the objects are returned in the Object[]).

// .. code to create a Query object
List list = q.list();
for (int i=0; i
If you're having trouble finding out the Java type of the element in a row, I've found Hibern8IDE to be an excellent help in running, testing and debugging Hibernate queries.

Struts & Java Tips: Issue #2

A couple weeks ago I wrote a short essay on some of the things that I ran into while working with Java and Jakarta Struts. Because I didn’t know what else to call it, I jokingly referred to it as Issue #1. Well, a month and a half later I think I have enough to write issue #2. I should probably call it something more general like ‘Java Web Development Tips’ or something, but why change now?

First, I thought I’d touch on some of the interesting things that I’ve run into while working in the presentation layer which in my case is JSP. This week I needed to create a search form that enabled end users to sort and filter results based on a number of parameters. Without showing 1000 lines of code, one of the challenges when doing a form like this is maintaining the form state when doing filtering and sorting (because not all the fields are sortable and not all can be filtered) and the most common solution is to use hidden form fields. Struts includes a <html:hidden> tag that will automatically maintain state for you form, but it requires that you know all the names of all the fields up front when you’re writing your form. If you decide to add a sortable or filterable property later, you’d need to hardcode another hidden form field. Instead, I chose to use the JSTL forEach tag and the special ‘param’ scope to programatically create my hidden form fields:

<c:forEach var="p" items="${param}">
  <input type="hidden" name="${p.key}" value="${p.value}">
</c:forEach>

The non-intuitive part of this code in my mind is the param ‘scope’, which (if you mess around with it a bit) is a HashMap derived from the getParameterMap() method of the ServletRequest interface. The forEach tag iterates over each parameter, which results in a Map.Entry; the Map.Entry provides JavaBean style accessors for key and value, which I can then use to create the hidden form fields.

The Action class that backs the search form uses an ActionForm to collect the data and then copies the data from the ActionForm bean to a bean made specifically for use with the search DAO. That code looks something like this:

public ActionForward execute(ActionMapping m, ActionForm f, HttpServletRequest req, HttpServletResponse res)
throws Exception {
...
// get the data posted from the form
SearchOrdersForm input = (SearchOrdersForm)f;
// bean coupled w/ the search DAO
ManagerSearchParams sp = new ManagerSearchParams();
// copy the properties from the form to the searchparams bean
// using the BeanUtils class
BeanUtils.copyProperties(sp, input);
// perform the search (in this case we're looking for orders
Collection orders = OrderDAO.findOrders(sp);
// push the collection to the jsp
request.setAttribute("orders", orders);

I’m not sure if there is a pattern in this or not, but the coupling of the ManagerSearchParams bean with the OrderDAO in the above example turned out (at least so far) to be very useful. Another part of the application required that I retrieve orders from persistent storage (in this case Hibernate & SQL Server) by date (ie: I needed to find all orders between date1 and date2). Instead of writing a new method on the DAO (ie: OrderDAO.searchbyDate()), the ManagerSearchParams bean already had start & end date properties. I simply created a new instance of the ManagerSearchParams bean, populated the startdate and enddate properties, and then fired the findOrders() method on the OrderDAO class.

Hibernate: Communication link failure: java.io.IOException

I recently launched a new site based on Struts, Hibernate and MySQL and immediately ran into a weird issue where Hibernate lost the ability to make database connections after a long period of inactivity. For the record, the stack trace is below:

java.sql.SQLException: Communication link failure: java.io.IOException
  at org.gjt.mm.mysql.MysqlIO.sendCommand(Unknown Source)
  at org.gjt.mm.mysql.MysqlIO.sqlQueryDirect(Unknown Source)
  at org.gjt.mm.mysql.Connection.execSQL(Unknown Source)
  at org.gjt.mm.mysql.PreparedStatement.executeQuery(Unknown Source)
  at net.sf.hibernate.impl.BatcherImpl.getResultSet(BatcherImpl.java:83)
  at net.sf.hibernate.loader.Loader.getResultSet(Loader.java:794)
  at net.sf.hibernate.hql.QueryTranslator.iterate(QueryTranslator.java:846)
  at net.sf.hibernate.impl.SessionImpl.iterate(SessionImpl.java:1540)
  at net.sf.hibernate.impl.SessionImpl.iterate(SessionImpl.java:1513)
  at net.sf.hibernate.impl.SessionImpl.iterate(SessionImpl.java:1505)

Looks like there are other people having the same problem, the first suggestion was to use the Thread Local Session pattern, which I already had in place. The solution was to add the following properties to my hibernate.cfg.xml:

<property name="connection.autoReconnect">true</property>
<property name="connection.autoReconnectForPools">true</property>
<property name="connection.is-connection-validation-required">true</property>

which I believe are specific to MySQL, but as far as I can tell, aren’t documented anywhere on the Hibernate site (or should they be documented on the MySQL JDBC driver site?)

For what it’s worth, Hibernate is a dream come true. I don’t like writing create, update, and delete SQL statements and I’ve found that the software I’ve written is much easier to manage and troubleshoot. If you haven’t played with it yet, check it out now.