All posts by Nick Lothian

Struts Shale Proposal

It concerns me a little that the Struts 2.0 (Shale) proposal is tied to the Servlets 2.4 spec. I'd prefer to see it abstracted away from the servlet spec so it could provide better support for Portlets.

One day I mean to write about how annoying the Portlets spec is to integrate into an existing MVC framework because of the way it already has its own semi-MVC API (the do* and processAction methods). It is possible – the Spring Framework portlet support has had a few more advances since my patches – but generally it makes it difficult because of how tightly most frameworks are tied to their own dispatching mechanisms

The first two laws of Software Engineering

From a guy at work:

The readability of generated code is inversely proportional to the readability of the code which generated it.

The first law of software engineering (and until I heard the one above the only one I thought existed) is:

((U+C+I) x (10-S))/20 x A x 1/(1-sin(F/10))

(See also http://www.news.com.au/common/printpage/0,6093,11009375,00.html
for an expanded explaination of that formula..)

Seriously, though – is it better to have readable generated code or readable generation code?

Delta-Encoded Feed Support in Rome

The Rome Fetcher now supports RFC3229 Delta-Encoded feeds (in CVS). The Rome Fetcher already supports GZipped feeds and conditional get. Hopefully, this additional feature should ease the burden on syndication client authors.

There are test cases in CVS, but I have failed to find any real world servers to test the delta-encoding support against, so any stories of succesful use (because obviously there could not possibly be any bugs…) would be appreciated.

Retrieving GMail Atom feed with Rome

Those of you with a GMail account might like this. It retrieves the GMail
Atom feed of you inbox status using the Rome Syndication libraries (Grab Rome 0.4 and Rome Fetcher 0.4 from http://rome.dev.java.net). You'll need to edit the BasicAuthenticator
class to set your username and password.

Gmail currently doesn't support conditional-gets or ETags, so unfortunately
it has to retrieve the entire feed each time.

public class Main {       
	public static void main(String args[] ) throws IllegalArgumentException, 
	MalformedURLException, IOException, FeedException, FetcherException {
		FeedFetcherCache feedInfoCache = HashMapFeedInfoCache.getInstance();
		FeedFetcher fetcher = new HttpURLFeedFetcher(feedInfoCache);
		java.net.Authenticator.setDefault(new BasicAuthenticator()); // turn on authentication
		SyndFeed feed = fetcher.retrieveFeed(new URL("https://gmail.google.com/gmail/feed/atom"));
		System.out.println(feed.getTitle());
		int feedSize = feed.getEntries().size();
		System.out.println("Contains " + feedSize + " items");
		for (Iterator iter = feed.getEntries().iterator(); iter.hasNext(); )
		{
			SyndEntry entry = (SyndEntry) iter.next();
			System.out.println(entry.getTitle());
			System.out.println("\t excerpt: " +
					entry.getDescription().getValue());
		}
		while (true) {
			try {
				Thread.sleep(1000 * 60 * 10); // check every 10 minutes
			} catch (InterruptedException e) {
				// ignore } System.err.print("Retrieving..");
				feed = fetcher.retrieveFeed(new
						URL("https://gmail.google.com/gmail/feed/atom"));
				System.err.println("Done.");
				int newFeedSize = feed.getEntries().size();
				// note that this won't detect new items if the feed size is at maximum
				if (feedSize != newFeedSize) {
					System.out.println("New messages detected. There are now " +
							newFeedSize + " items");
					int itemsToShow = newFeedSize - feedSize;                   
					int count = 0;
					for (Iterator iter = feed.getEntries().iterator();
					iter.hasNext();) {
						SyndEntry entry = (SyndEntry) iter.next();
						System.out.println(entry.getTitle());
						System.out.println("\t excerpt: " +
								entry.getDescription().getValue());
						count++;
						if (count >= itemsToShow) {
							break;
						}
					}                  
					feedSize = newFeedSize;
				}
			}
		}           
		static class BasicAuthenticator extends Authenticator {
			/**
			 * @see java.net.Authenticator#getPasswordAuthentication()
			 */
			protected PasswordAuthentication getPasswordAuthentication() {
				if ("gmail.google.com".equals(getRequestingHost())) {
					return new PasswordAuthentication("user.name", "password".toCharArray());
				} else {
					return null;
				}
			}
		}
	}

Got bandwidth problems?

A few people have been complaining about the bandwidth things like PodCasting take up ( Duh!).

I'd recommend they look at using the Coral cache. If you haven't tried it, it is a free content distribution network (think Akamai). It does run on port 8090, so people behind some firewals can't use it, but for for a lot of people it will both give them quicker downloads and save you bandwidth.

For instance, the Coralled version of this page is http://www.mackmo.com.nyud.net:8090/nick/blog/.

Re: What is the state of the enterprise Java world, anyway?

Ted & Don are arguing the point of JavaContainersNG (Spring, Pico, HiveMind etc).

I'm a little surprised – the main point of them all is a very Microsoftish concept – reduce the amount code you have to write.

At TechEd this year (in the few product sessions I went to) it was all about “.NET 2.0 will reduce the number of lines of code you write by 1000%” (or whatever). That's what Spring etc do – no more worrying about wiring code, and just concentrate on your business logic.

Yes, they have other features, too, and yes, they can let you run your code outside EJBs, and yes it is cool that you can test you logic easier, and yes the AOP stuff can be very useful, but the main point is you don't need to write all that stupid wiring code that pollutes most programs.

Don's right to be puzzled why Spring is easier than EJB – you still need stupid XML configuration files, and it doesn't magically make EJBs as easy as .NET development. BUT – and I suspect this is what you miss unless you've actually suffered through EJBs – Spring is easier than using POEJBs (Plain-Old EJBs) because is hides 90% of the things you don't need to worry about.

Don's right about ORM mappers, too, and I don't think any Java person would disagree. There are 3 current JCPs for ORM, not counting the SDO (Service Data Object) one, and that also exclude Hibernate, Apache OBJ and iBatis, which all have pretty reasonable mind/marketshare. That's just so stupid – but the competition makes it interesting.

Evil JDK 1.5 Open-GL configuration

J2SE 5.0 includes a new OpenGL-based pipeline for Java 2D. This pipeline provides hardware acceleration for simple rendering operations (text, images, lines, and filled primitives) as well as those that involve complex transforms, paints, composites, and clips. This pipeline is available on all platforms (Solaris, Linux, and Microsoft Windows) and is currently disabled by default.

Cool!

To silently enable the OpenGL-based pipeline, specify the 
following system property on the command line:

    -Dsun.java2d.opengl=true

To receive verbose console output about whether the OpenGL-based pipeline is   
initialized successfully for a particular screen, specify "True" (note the 
uppercase T) :

    -Dsun.java2d.opengl=True

Hu!?! On what planet is that a good idea? Is there precedent for this? As someone said at work today – perhaps in JDK 1.5 “tRue” will be another option, and to turn them both on: “TRue” (!?!)

Automated summaries using Classifier4J

The DevX article on Classifier4J includes a good example of using Classifier4J for doing automatic text summary. I have to admit the example given makes it seem pretty impressive. I'm not sure everyone will get as good results as that (the summarising code is the ugliest in Classifier4J by far – I just wanted to see if it would work), but none the less summarising http://www.devx.com/xml/Article/16704/1954?pf=true
to:

The invention of database driver methodologies such as JDBC
and ODBC led to applications being loosely coupled with their back end databases,
allowing best-of-breed databases to be chosen—and swapped
out when necessary—without any ill-effect on the user interface.
Similarly, the decoupling of data and presentation in HTML—by using XML for the data and
XSLT for the presentation of data—has led to much innovation and flexibility,
not least of which is the ability to deliver a document as data in XML and deliver
custom styling for that document with different XSLTs.
A runtime engine would be present on the desktop, and servers would
be able to deliver the GUI to the browser with an XML document.

is pretty useful. It does demonstrate that the software might currently have a preference for using sentances too early in the article, though.