2011-09-27

What's New in Tomcat 7 & Servlet 3

The Apache Tomcat web server and Servlet container has been significantly upgraded in version 7 to now support Servlet 3 spec and many other changes.

For info, check out this video recording of a slideshow presentation, by Mark Thomas, the Tomcat release manager.

An article about the new async processing feature in Servlet 3.

An Introduction to Servlet 3.

The Servlet 3.0 spec (JSR 315).

Jason Hunter seems to no longer be writing his famous “New Features in Servlet X.X” articles. But to see the evolution of Servlet technology, you may want to read his past articles for Servlet 2.5, 2.4, 2.3, 2.2, 2.1. I believe Mr. Hunter was also the author of these Servlet Best Practices, parts 1, 2, and 3. And his article on Servlet Filters.

If you are new to Servlet technology, start with this Wikipedia page.

2011-09-21

When Vaadin Seems to Ignore Your Modifications

They first thing you’ll notice when trying the Vaadin 6 tutorial is how little code is needed for an interactive web app. The second thing you’ll notice is that when you modify the source code, nothing happens.

You might add a label to the form, for example, but at runtime the label fails to appear.

This is maddening when the joy of a new app turns into utter frustration. You might even quit Eclipse, restart, run your app, and still find your changes ignored. What’s going on? Well multiple bugs and features are biting.

Restart App

While developing and testing you may need to restart your Vaadin app. Do this by appending the app's URL in your web browser's address bar with:
?restartApplication
Another way is to append:
?debug
That approach displays a JavaScript window on top of your app’s window with buttons for restarting the app, as well as debugging your window's layout, and other features.

Session Persistance

First, if you are using Tomcat as your web server, you’ve discovered Tomcat's default feature where it persists a session object automatically when quitting. In a conventional app, the session has just a few simple values, probably just small pieces of text. So it makes sense to save those to disk, and restore those values to memory when the session is recreated at runtime. With Vaadin, the session object holds your entire Vaadin app including all the windows and their current state. Upon restarting the session, Tomcat restores your Vaadin app as it was running previously, like magic. Unfortunately, your Vaadin app's "init"  method is not run again. So your changes do not take effect. Makes sense, as the definition of the "init" method is to run when the app first begins, and in this case of Tomcat restoring your session, the app is already running so no need to call "init".

The solution is simple: Turn off the Tomcat feature of session persistence. Doing seems simple: Find and edit Tomcat’s "context.xml" file to uncomment the line:
<Manager pathname="" />
The trick is which "context.xml" to edit. No need to edit the one your Tomcat installation, which would affect all web apps. Instead, copy the "context.xml" from the tomcat/conf folder. Place that copy nested inside your project folder, and edit there:
/workspace/your_project/WebContent/WEB-INF/context.xml
Now you'll only be affecting this webapp, and not others.

I suggest doing turning off session persistence for every Vaadin app you create. Session persistence and restoration of a Vaadin app is a big deal. You should think through ramifications such as how to handle database connections. Admittedly it would be nice if users found their app in the same configuration as their last work session, but you need to develop and test appropriately.

Missing Pieces

When you run a Vaadin app in Eclipse, you are using the WTP (Web Tools Project) plugins set which handles getting your Eclipse session to find, configure, and run a web server with your web app. Unfortunately, WTP seems to have “issues”, as we say when speaking politely, when running your web app.

What actually happens is that WTP deploys a copy of your webapp to a hidden folder, and then invokes Tomcat. That works fine the first time. But upon successive times, WTP seems to get confused about what to copy over.

A workaround is to clear your web app from the hidden folder. Look for the hidden folder ".metadata" in your Eclipse workspace folder. Then ".plugins" > "org.eclipse.wst.server.core" > "tmp0" > "wtpwebapps". There you'll find your webapp's folder. You may delete it. But you must also delete this file to avoid confusing Eclipse: workspace/.metadata/.plugins/org.eclipse.wst.server.core/publish/publish0.dat

That workaround is tedious to do repeatedly. Another workaround is to avoid WTP altogether. Some folks on the Vaadin forums talk about running Jetty directly within your project, while avoiding WTP entirely. Jetty is built to be embeddable, so this is supposedly pretty easy. But I already know and use Tomcat, and want to be using it for development. And I did not want to learn yet another development arrangement. So I chose not to go that route, though it may a wise one.

Another workaround is JRebel. Some references to this product on the Vaadin forums led me to this remarkable product. JRebel pulls a few tricks to make development easier, especially web app development. It does seem to solve this problem of missing pieces while running within the IDE. I'm not clear on how JRebel accomplishes this, but it seems to be working well for me.

Hot Swapping Classes

Another frustration of web app development is making changes to classes and then having to shutdown and restart the web server all over again. The Java platform has built-in features for hot-swapping classes while still running the app. But for various reasons, those features do not work well with web-servers.

You can shutdown the web server by clicking in Eclipse's Servers panel, select your web server, and click the red square icon to perform a shutdown. But this gets tedious. And I often found myself with problems that seemed to require quitting and restarting Eclipse as well. Not fun.

Solution: JRebel, again. Swapping fresh classes while running is JRebel's raison d'être. I’ve only begun to work with JRebel for a few days, but it seems to be doing this hot-swap trick very well.

I Save File → Eclipse Re-compiles → JRebel Re-deploys

In fact, it works so well, I did not understand how to use it after installation. I made a change to a class, and then went back to the docs to see how to tell JRebel to compile and deploy it. I could not find any such doc. Frustrated, I switched back to Eclipse. There I noticed a fresh line in the console pane, something about SuchAndSuch class has been deployed. While not believing it, I did a restart of my app using the URL trick mentioned above, and voilà, my changed classes too effect. Apparently all I need is to save the .java file! Saving triggers Eclipse to automatically re-compile. The re-compile triggers JRebel to re-deploy of the changed class to Tomcat running via WTP within Eclipse. My fresh class was installed while Tomcat continued executing. Amazing. JRebel has a plugin for Eclipse that provides for this integration.

While not absolutely mandatory for Vaadin work, JRebel certainly makes life easier. They have a free-of-cost “Social” edition for non-commercial purposes while connected on the Internets, so give JRebel a try.

JRebel does not affect deploying your app to production. However, if you want to hot-swap parts of your app in production, LiveRebel is a sibling product designed for that purpose. JRebel is for development, while LiveRebel is for deployment.

Be sure to make the correct settings for JRebel, both when you install JRebel and each time you create a Vaadin project. For JRebel in Eclipse, read sections 2.2, 3.2, and 4.2 of the JRebel Reference Manual. Really quite easy.

2011-09-19

To Create a Jar

Creating a .jar file in Java is not as easy as it seems. The flag letters must be in a certain order. Unfortunately, I've not found the documentation for that ordering. This tutorial says the flags may be in any order, but not so in my experience.

After some frustrating trial-and-error, I found the following line works.
jar c0mfv META-INF/MANIFEST.MF whatever.jar source_folders_&_files
To break it down:
  • The 'jar' is the name of the command-line tool
  • 'c' means 'create a jar file'
  • '0' (zero) means no compression
  • 'm' means to use an existing manifest file rather than create one. Omit this to have a manifest auto-generated. 
  • 'f' means send the output of this command to a file rather than to standard output (on the command line).
  • 'v' means 'verbose', to describe each step of the process, displayed on the command line. You can read this to verify, for example, that your pre-existing manifest was copied rather than a new one generated.
  • Pass the relative location of your pre-existing manifest file. Omit if you are omitting the 'm' flag.
  • Pass the name of the jar file to be created. Type the '.jar' on the end yourself. 
  • Pass one or more files and folders to be included. Include the top folder of any packages such as "com" if you have a package such as "com.example.myapp.gui".

Change Directory 

Before typing that 'jar' line, change directory ('cd') to the folder containing the top folder of your package. In other words, you don't jar the folder above your source. From the tutorial linked above, if you have this folder hierarchy:


You would 'cd' into "TicTacToe", and then pass 3 items at the end of your jar comand, for the .class file and 2 folders.

2011-09-17

Time Keeps on Ticking, Ticking, Ticking, Into The Future

Here are a few handy links to Date and Time info.

The core pearl of wisdom:
Timezones are a presentation-layer problem!
Most of your code shouldn't be dealing with timezones or local time.

2011-09-09

New Adventure Begins: Vaadin

I’m exploring Vaadin, a framework for server-side webapps that require no knowledge of HTML, CSS, DOM, JavaScript, or HTTP. Similar in concept to Real Studio, Web Edition, but built in pure Java. Vaadin is quite promising, as seen in this great demo of their rich collection of GUI widgets, and excellent doc in The Book of Vaadin.

Unfortunately, getting started with Vaadin is almost impossible. After strange initial behavior, and wrestling the Eclipse IDE, I gave up trying weeks ago. I was quite disappointed given how you can have a working interactive web app running in your first 5 or 10 minutes with Real Studio. However, my greatest strength as a developer kicked in: stubbornness. I tried again. And I’ve nearly won this time.

So here’s some pointers for other brave souls venturing into the world of web apps.

Tip 1: Use Eclipse

While Eclipse is my least favorite Java IDE, the Vaadin plugin is designed only for Eclipse. Be sure to get this edition, Eclipse IDE for Java EE Developers. In theory, you could use another edition of Eclipse  and add enough modules to get the equivalent of the EE edition. I tried, I failed. I already had another edition for other purposes (Swing apps). I added and added modules, but never got it to work. Reading the Vaadin forums led me to many answers asking “Did you start with the Java EE edition of Eclipse”. So I gave up, replaced my Eclipse, and found some success.

Bonus: I found I could add the WindowBuilder modules to the Java EE edition, thereby giving me the best of both, Swing and web apps.

I am using:

Eclipse Java EE IDE for Web Developers.
Version: Indigo Release
Build id: 20110615-0604
with Mac OS X 10.6.7 on an Intel MacBook Core 2 Duo, 6 gigs of memory, executing in Tomcat 7.0.21 under Apple's implementation of 64-bit Java 1.6.0_26.

Tip 2: Use the Vaadin plugin for Eclipse

While not technically necessary, the plugin is virtually a necessity. The plugin creates a properly configured Vaadin web app project with a Hello World application. The plugin provides other features as well.

Tip 3: Let Eclipse download and install the Vaadin plugin

I naïvely downloaded and installed the plugin myself. That led to problems. Among other things, Eclipse offered to upgrade the plugin later, but could not actually do so. To install the plugin the proper way, let Eclipse do it.

  1. Choose Help > Install New Software. 
  2. In the Work with field, paste the URL as instructed by the Vaadin site.
Tip 4: Install Tomcat before using Vaadin

Download, prepare, and configure Apache Tomcat before you start using Vaadin.

Download: Unzip the Tomcat download. You may put the Tomcat folder anywhere. I put it at the top of my home folder.

Prepare: See another post of mine explaining how to perform the crucial step of running your unzipped Tomcat through the BatChmod app if you are running on a Mac.

Configure: You must tell Eclipse how to work with your Tomcat installation. As I’ve forgotten how at this moment, I'll try to write another post on this topic.

Tip 5: Create your first project as a Vaadin project using the Wizard

In Eclipse, choose File > New > Other. In the Wizards filter field, type: Vaadin. From the list, pick "Vaadin Project". For the most part, go with the default values in the wizard. If you are doing real work, as opposed to the tutorial, change the base package to your own.

Tip 6: Build before running

The resulting project should be ready to run. Except that for some mysterious reason, the wizard's Run configuration fails to first build the project. So to run:
  1. Select the name of the project in the Project Explorer. (Crucial!)
  2. Choose Project > Clean Project (Crucial! Successive runs do not freshen properly unless you clean -- don't ask me why)
  3. Click the Run button in toolbar.
If you are lucky, Tomcat launches, and after several moments your app appears in Eclipse's built-in web browser. Eclipse lets you specify using a real web browser instead. But when I tried Firefox, I got annoyed my Eclipse telling me to close all windows in Firefox or quit Firefox. Hopefully I can solve that problem another day.

Tip 7: Stop Session Persistence

After my first successful run with the Hello World app, I did what any eager student does. I tweaked the app, and ran again. I added a "new java.util.Date" to the app's Hello label. I ran my app again, but no date. I stopped the Tomcat server, and tried to run again. No date. I quit Eclipse and restarted and ran. No date. Arghh!

Turns out to be a feature, not a bug. Unbeknownst to me, by version 7, Tomcat had acquired the default behavior of persisting sessions automatically. So when Tomcat shuts down, any existing Session objects have their values written to disk. When that web runs again after restarting Tomcat, the sessions are reconstituted in the JVM

Meanwhile, the Hello World app created by the Vaadin project wizard has its gui constructed during a call to the Vaadin 'init' method. Turns out, the init method is only called when starting a new session. Since Tomcat was reconstituting the old session on every run, the init method was never being called again. So my edits to the init method never took effect. This tricky Catch-22 cost me hours and hours of frustration and confusion. 

To avoid this behavior:
  1. As mentioned in Tip 6 above, always Clean rather than build your project.
  2. Turn off the Tomcat feature of persisting sessions.
To disable that Tomcat feature, install a configuration file.
  1. Locate the "context.xml" file found in the "conf" folder of Tomcat. In my case: /Users/basilbourque/apache-tomcat-7.0.21/conf/context.xml
  2. Paste a copy of that file to the "WEB-INF" folder of your Eclipse project's "WebContent" folder. In my case: /Users/basilbourque/Documents/workspace/myproj/WebContent/WEB-INF/context.xml
  3. Edit that new "context.xml" by uncommenting the line reading: <Manager pathname="" />. Note that the comment itself explains this will disable the session persistence feature.

2011-09-05

Starting and Stopping Jetty Web Server

I’ve looked at Jetty a few times in the past but could not even find documentation on how to start or stop the dang thing. Trying to use Vaadin has brought me once again to Jetty, version 8.

I don't know if this is necessary, but after unzipping the downloaded Jetty file, I drag and drop the resulting folder to the BatChmod app. I check all the checkboxes except 'Clear xattrs'.

I finally discovered how to start and stop Jetty on Mac OS X. It's easy. While Apache Tomcat has an explicit start and stop shell script (.sh files), Jetty uses a single shell script for both purposes. You pass the word 'start' or 'stop' without any quotes.

To start Jetty web server:
  1. Locate the shell script: …/YourJettyFolder/bin/jetty.sh
  2. Drag and drop that script file to a terminal window in either Terminal.app or Path Finder.
  3. Type a space and the word 'start'. Press Return key.
Example:
/Users/basilbourque/jetty-distribution-8.0.0.v20110901/bin/jetty.sh start

You’ll see something like this:
Starting Jetty: STARTED Jetty Mon Sep  5 16:39:26 PDT 2011

To stop Jetty web server:
  1. Press the Up Arrow key to repeat the previous line at the command line.
  2. Press Backspace to replace the word 'start' with the word 'stop'.
  3. Press Return to execute that line.
You’ll see something like this:
Stopping Jetty: OK

To verify Jetty is running and verify its configuration, pass the word check rather than start or stop.

Jetty defaults to port 8080. So to try it, point your web browser to:
http://localhost:8080/
To use port 80, see my other posts on port-forwarding.

I’m working on an Intel MacBook with Core 2 Duo running Mac OS X 10.6.7 with Java version "1.6.0_26" 64-bit.