Tuesday, October 31, 2006

Embedded Tomcat 5.5.17 Eclipse Project

I like to use Tomcat because of its simplicity. I'm sure that there are many reasons to use the embedded version of Tomcat, I'm using it because I can start a vanilla Tomcat engine in under one second. Additionally, it's easy to place all of the configuration files under version control when all of the files are part of a Eclipse project. You can download a Zip file containing a working example of embedded Tomcat by clicking the title above. Make sure that you edit the .classpath file and change the location of the Jar files to whereever you have installed Tomcat. If you want to follow the steps that I took instead of downloading the zip file, here they are: 1. Create a Java class to start Tomcat:
package com.affy;
import org.apache.catalina.startup.Bootstrap;
public class EmbeddedTomcat {
 public static void main(String[] args) throws Exception {
  Bootstrap bootStrap = new Bootstrap();
  bootStrap.init();
  bootStrap.start();
 }
}
2. Update your classpath so it contains the following jar files.
TOMCAT_HOME/bin/bootstrap.jar
TOMCAT_HOME/bin/commons-logging-api.jar
TOMCAT_HOME/common/lib/commons-el.jar
TOMCAT_HOME/common/lib/jasper-compiler.jar
TOMCAT_HOME/common/lib/jasper-compiler-jdt.jar
TOMCAT_HOME/common/lib/jasper-runtime.jar
TOMCAT_HOME/common/lib/jsp-api.jar
TOMCAT_HOME/common/lib/naming-factory.jar
TOMCAT_HOME/common/lib/naming-resources.jar
TOMCAT_HOME/common/lib/servlet-api.jar
TOMCAT_HOME/server/lib/catalina.jar
TOMCAT_HOME/server/lib/catalina-cluster.jar
TOMCAT_HOME/server/lib/catalina-storeconfig.jar
TOMCAT_HOME/server/lib/commons-modeler.jar
TOMCAT_HOME/server/lib/servlets-default.jar
TOMCAT_HOME/server/lib/tomcat-ajp.jar
TOMCAT_HOME/server/lib/tomcat-coyote.jar
TOMCAT_HOME/server/lib/tomcat-util.jar
TOMCAT_HOME/server/lib/tomcat-http.jar
3. Create a conf directory with the following files (copied directly from the conf in TOMCAT_HOME.
catalina.policy
catalina.properties
context.xml
logging.properties
server.xml
tomcat-users.xml
web.xml
4. Create the webapps and webapps/ROOT directories. 5. Create a webapps/ROOT/index.html file with any content you'd like. 6. Run the EmbeddedTomcat Java program. This step will automatically create a work directory. 7. Connect to http://localhost:8080/ with your browser and you should see the index.html page that you created in step 5. Good luck and Have Fun playing with your embedded Tomcat!

Embedded Tomcat; Fixing the 'No Java Compiler available' error.

I am investigating the use of embedded Tomcat in one of my projects. During my testing, I ran into an error message:
No Java compiler available
I was unable to find significant information about this message via Google so I downloaded the Tomcat source and poked around. To make a short story shorter, include the following jar files to fix this issue:
TOMCAT_HOME\common\lib\jasper-compiler.jar
TOMCAT_HOME\common\lib\jasper-compiler-jdt.jar

Fixing the "No Java compiler available" Error When Running Embedded Tomcat

I created an Eclipse project which runs an embedded version of Tomcat. More about that in a future post. I ran into the following message when I tried to serve a JSP page: java.lang.IllegalStateException: No Java compiler available I downloaded the Tomcat source (gotta love open source!) and found the following lines of code:
  jspCompiler = null;
  if (options.getCompiler() == null) {
    jspCompiler = createCompiler("org.apache.jasper.compiler.JDTCompiler");
    if (jspCompiler == null) {
      jspCompiler = createCompiler("org.apache.jasper.compiler.AntCompiler");
    }
  }
I did a little digging and found that several jar files where not in my classpath: jasper-compiler.jar jasper-compiler-jdt.jar

Thursday, October 26, 2006

Running HttpServerTestApp as an Eclipse Project

I've been trying to get the apache-httpd example of Apache's MUSE project to run. Since I like using Eclipse, I created an Eclipse project to run the HttpServerTestApp application. It took quite awhile to find all of the needed Jar files. To save you time, here is the list:
  • apache-httpd.jar
  • muse-core-2.0.0.jar
  • muse-util-2.0.0.jar
  • muse-util-xml-2.0.0.jar
  • muse-util-xstream-2.0.0.jar
  • muse-wsa-soap-2.0.0.jar
  • muse-wsrf-api-2.0.0.jar
  • muse-wsrf-impl-2.0.0.jar
  • xercesImpl-2.8.1.jar
  • xstream-1.1.2.jar

Wednesday, October 25, 2006

Use CSS to Ensure Common Navigation HTML on Every Page

This tip was developed (or at least described by) Trenton Moss on the ITWALES.com site. I reproduce the essential elements of only one of the ten tips that he writes about. Please visit itwales.com to see all ten. Add a class to each navigation item: <ul> <li><a href="#" class="home">Home</a></li> <li><a href="#" class="about">About us</a></li> <li><a href="#" class="contact">Contact us</a></li> </ul> Then insert an id into the <body> tag that indicates which are it represents. For example, When in 'Home' it should read <body id="home">. Now create a CSS rule: #home .home, #about .about, #contact .contact { commands for highlighted navigation go here }

Monday, October 09, 2006

MoonEdit - Tom Dobrowolski's multi-platform collaborative text editor.

I recently found this neat editor. However, when I checked Google under 'collaborative text editor'. So this blog entry is my little attempt to give it more widespread notice.

Sunday, October 08, 2006

Using Composite Object For Hash Key Better Than Concatenated String

Kirk Pepperdine has written a guest article for the Java Specialists' newsletter about the DRY or Don't Repeat Yourself principle. While I agree with DRY, the important part of the article was his performance timing study. He compared using personsByName.put(firstName + lastName, person); versus personsByName.put(new CompositeKey(firstName, lastName), person); Cutting to the result of the test, the composite key cut the example's execution by 66% and reduced memory consumption by about 65Mb. Visit the link above for more details or simply use Composite keys from now on!

Using XML to Reduce Accidental Corruption

Elliote Harold wrote an article about Fuzz testing which was published on IBM's developerWorks web site. In it he gives some great reasons for choosing to use an XML format for your data files instead of using a text-based format (like CVS) or a binary format (like serialized objects). The important point was that XML parser are designed to separate good input from bad. Why redo all that error-checking just to create your own format? In Elliote's own words:
The key characteristic that makes XML formats resistant to fuzz is that an XML parser assumes nothing about the input. This is precisely what you want in a robust file format. XML parsers are designed so that any input (well-formed or not, valid or not) is handled in a defined way. An XML parser can process any byte stream. If your data first passes through an XML parser, all you need to be ready for is whatever the parser can give you. For instance, you don't need to check whether the data contains null characters because an XML parser will never pass you a null. If the XML parser sees a null character in its input, it throws an exception and stops processing. You still need to handle this exception of course, but writing a catch block to handle a detected error is much simpler than writing code to detect all possible errors. For further security you can validate your document with a DTD and/or a schema. This checks not only that the XML is well-formed, but that it's at least close to what you expect. Validation will rarely tell you everything you need to know about a document, but it makes it easy to write a lot of simple checks. With XML, it is very straightforward to strictly limit the documents you accept to the formats you know how to handle.