Discovering the platform profile from Java
    What's the simplest way to get CPU speed, amount of RAM, OS version, and other hardware details from the running JVM? I'm putting together a yet-to-be-announced tool that will include hardware specs in its reporting. 
So far, I've been able to get the hardware profile on Mac OS X using 
sysctl and on Linux using 
/proc/cpuinfo and 
/proc/meminfo:
java.version: 1.5.0_13
java.vm.name: Java HotSpot(TM) Client VM
os.arch: i386
os.name: Mac OS X
os.version: 10.5.1
user.name: jessewilson
host.name: jessewilson-macbookpro-2.local
os.kernel.version: 9.1.0
host.model: MacBookPro1,1
host.cpus: 2
host.cpu.speeds: 2000000000
host.cpu.arch: i386
host.cpu.bits.physical: 32
host.cpu.names: Genuine Intel(R) CPU            1500  @ 2.00GHz
host.cpu.caches.l2: 2097152
host.memory.physical: 2147483648
This comes from a quick-n-dirty Java app, 
HostInfo.java. Curious - anyone know of a simpler approach? Or a more reliable API? I'm not interested in JNI or nontrivial applications, since they complicate deployment.
Still to do - figure out what's necessary to discover this information on the Windows platform...
    # posted by Jesse Wilson 
     on Monday, March 24, 2008
     5 comments
               post a comment
    
    
   
 
  
    Coding in the small with Google Collections: ImmutableSet
    Part 15 in a 
Series.
The 
Google Collections project has released an 
impressive new collection of features. 
The new release has prompted me to continue this series. My favourite feature of the new release is 
ImmutableSet. It's a top-level implementation of 
Set that's full of features - this class alone justifies adding the entire 
.jar to your application's libraries folder...
For static constants
Before  public static final Set<Integer> LUCKY_NUMBERS;
  static {
    Set<Integer> luckyNumbersMutable = new HashSet<Integer>();
    luckyNumbersMutable.add(4);
    luckyNumbersMutable.add(8);
    luckyNumbersMutable.add(15);
    luckyNumbersMutable.add(16);
    luckyNumbersMutable.add(23);
    luckyNumbersMutable.add(42);
    LUCKY_NUMBERS = Collections.unmodifiableSet(luckyNumbersMutable);
  }
After:  public static final ImmutableSet<Integer> LUCKY_NUMBERS 
      = ImmutableSet.of(4, 8, 15, 16, 23, 42);
For defensive copies
Before:  private final Set<Integer> luckyNumbers;
  
  public Hatch(Set<Integer> luckyNumbers) {
    this.luckyNumbers = Collections.unmodifiableSet(new HashSet<Integer>(luckyNumbers));
  }
  
  public Set<Integer> getLuckyNumbers() {
    return luckyNumbers;
  }
After:  private final ImmutableSet<Integer> luckyNumbers;
  public Foo(Set<Integer> luckyNumbers) {
    this.luckyNumbers = ImmutableSet.copyOf(luckyNumbers);
  }
  public ImmutableSet<Integer> getLuckyNumbers() {
    return luckyNumbers;
  }
For more defensive copies
ImmutableSet.copyOf has been heavily optimized when the argument is itself an ImmutableSet. It turns out that this method can 
no-op if the argument is itself an 
ImmutableSet, since copying immutable objects is redundant. The more you use 
ImmutableSet, the cheaper it is to do defensive copies!
For predictable insertion order
ImmutableSet's elements iterate in the same order that they're added in. That means there's less 
unpredictable behaviour in your application's business logic. There's no need to worry about tests that pass on one JVM and fail with another because of 
HashSet's unspecified iteration order.
    ImmutableSet<Integer> numbers = ImmutableSet.of(8, 6, 7, 5, 3, 0, 9);
    assertEquals("[8, 6, 7, 5, 3, 0, 9]", numbers.toString());
For self-documenting APIs
Before:  /**
   * Returns numbers most likely to be selected in upcoming lottery drawings.
   * 
   * @return an immutable, non-empty set
   */
  public Set<Integer> getLuckyNumbers();
After:  /**
   * Returns numbers most likely to be selected in upcoming lottery drawings.
   * 
   * @return a non-empty set
   */
  public ImmutableSet<Integer> getLuckyNumbers();
For less memory allocation
ImmutableSet allocates fewer objects and smaller objects than either 
HashSet or 
LinkedHashSet. This makes your program's heap smaller. There's also less work for your garbage collector.
For non-null data
ImmutableSet does not permit null elements. This is almost always what you want, and helps to detect bugs early:
Before:  public Hatch(Set<Integer> numbers) {
    for (Integer number : numbers) {
      if (number == null) {
        throw new NullPointerException();
      }
    }
    this.numbers = Collections.unmodifiableSet(new LinkedHashSet<Integer>(numbers));
  }
After:  public Hatch(Set<Integer> numbers) {
    this.numbers = ImmutableSet.copyOf(numbers);
  }
ImmutableSet is my new default collection, replacing 
ArrayList. It's that good. And as a special treat, when I do need a List, Google Collections also includes 
ImmutableList.
    # posted by Jesse Wilson 
     on Friday, March 21, 2008
     3 comments
               post a comment
    
    
   
 
  
    The 'anything goes' SecurityManager
    As previously mentioned, my current 20% project involves some 
RMI hackery. Today I ran into an unfortunate error message:
java.lang.ClassNotFoundException: com.publicobject.m2x.Measurer (no security manager: RMI class loader disabled)
 at sun.rmi.server.LoaderHandler.loadClass(LoaderHandler.java:371)
 at sun.rmi.server.LoaderHandler.loadClass(LoaderHandler.java:165)
 at java.rmi.server.RMIClassLoader$2.loadClass(RMIClassLoader.java:620)
 at java.rmi.server.RMIClassLoader.loadClass(RMIClassLoader.java:247)
 at sun.rmi.server.MarshalInputStream.resolveClass(MarshalInputStream.java:197)
Apparently Java RMI won't let me download remote code without a security manager installed. The standard workaround for this problem is to create a 
.policy like so:
grant {
  permission java.security.AllPermission;
};
. . . and then I need to reference the file when I launch the app:
java -cp . -Djava.security.Policy=m2x.policy com.publicobject.m2x.Main
I don't like this solution because it forces me to change how my app is launched, complicating deployment. It adds another file to manage. And the deployment work needs to be solved in Unixland, far from my comfort zone of Javaland.
It turns out I can do the same thing in Java code by installing a no-op security manager:
    System.setSecurityManager(new SecurityManager() {
      public void checkPermission(Permission permission) { }
      public void checkPermission(Permission permission, Object context) { }
    });
I like this better.
Java should be first on the Java Platform
When designing APIs for the Java platform, programmatic access must be a first-class citizen. APIs that require XML, configuration files, or System properties shouldn't be the only way to access functionality.
    # posted by Jesse Wilson 
     on Thursday, March 20, 2008
     1 comments
               post a comment
    
    
   
 
  
    Java RMI without a webserver
    One of the four steps to setup 
Java RMI is "Making classes network accessible." Since I'm new to Java RMI, I found this requirement surprising. We have a client and a server. Of the two of them, surely one of the two has a full set of classes. Why require a third server to host the classes?
I suppose they were thinking that somewhere near the RMI server would be a big expensive heavyweight J2EE container, and that thing can serve the classes. But even if I have the J2EE server setup, this is still annoying - I still need to configure the webserver, and then keep it's jars synchronized with the ones my RMI server is using.
Instead, I decided to do the Simplest Thing That Could Possibly Work. I wrote a tiny 
HTTP Server (168 lines of code) and used it to publish all the classes in my local JVM. Now in my RMI code, I simply need this:
    String currentHostname = "jessesmac.publicobject.com";
    new RmiClassServer(currentHostname).run();
The RMI server serves classes to anyone who's interested. I don't need to tell it which classpath to use - it uses the exact same classes that the local classloader uses, via 
Class.getResource. 
Sound useful for your RMI application? You'll need 
 RmiClassServer.java and 
MiniHttpServer.java, both of which are available under your choice of 
Mozilla 1.1 or 
LGPL license.
A final word of caution - this server exposes everything on your application's classpath. Unless your classes themselves are public, please don't put this server (or your RMI server!) on your public website.
    # posted by Jesse Wilson 
     on Tuesday, March 18, 2008
     2 comments
               post a comment
    
    
   
 
  
    MiniHttpServer.java - an HTTP Server in 168 lines
    For part of an project which I'll be announcing shortly, I needed an extremely lightweight HTTP server. Fortunately, HTTP is quite easy-to-implement. Tonight I hacked together 
MiniHttpServer.java, a simple server with zero third-party dependencies.
I was able to support the core of HTTP in with just 168 lines by doing only the bare-minimum. Here's the server's core:
        nextLine();
        readUntil("GET\\s+");
        String url = readUntil("\\s+HTTP/1.1");
        do {
          nextLine();
        } while (readUntil("$").length() > 0);
        InputStream responseData = handler.getResponse(url);
        if (responseData != null) {
          write("HTTP/1.1 200 OK\r\n\r\n");
          int b;
          while ((b = responseData.read()) != -1) {
            connection.getOutputStream().write(b);
          }
        } else {
          write("HTTP/1.1 404 Not Found\r\n\r\n");
          write("404 Not Found: " + url);
        }
        connection.close();
If you need an embedded HTTP server, please help yourself to this code. It's fully open source, and available under your choice of 
Mozilla 1.1 or 
LGPL license.
    # posted by Jesse Wilson 
     on Tuesday, March 18, 2008
     2 comments
               post a comment
    
    
   
 
  
    Java Minutiae - Instantiating inner classes
    Pop quiz - without reflection, access to private members, or changing the source, create an instance of 
Inner.
public final class Outer {
  public static final Outer INSTANCE = new Outer();
  private Outer() { }
  public class Inner { }
}
Note that Inner is non-static, so each 
Inner has a reference to its containing 
Outer.
Show AnswerWell it turns out that you can 'dereference' a containing instance to instantiate an inner class. The syntax is awkward, but it works:
  Inner inner = Outer.INSTANCE.new Inner();
I've found this syntax most useful for testing package-scoped inner classes.
    # posted by Jesse Wilson 
     on Sunday, March 16, 2008
     1 comments
               post a comment
    
    
   
 
  
    Java Minutiae - Map.remove()
    Suppose you'd like to remove an entry from a Map, and perform some action only if the remove actually removed. Since 
Map.remove() returns the value associated with the removed key, we can do this:
  if (map.remove(key) != null) {
   deleteAssociatedFiles(key);
  }
Unfortunately, if the map tolerates 
null values, this approach doesn't differentiate between removing 'key→null' and not removing. The standard workaround is to do two map lookups (which fails for 
ConcurrentMaps):
  if (map.containsKey(key)) {
    map.remove(key);
    deleteAssociatedFiles(key);
  }
But there is an elegant solution. Although 
Map.remove() doesn't know 'null' from 'nothing', it turns out that 
Set.remove() makes the distinction. That method returns 
true only if the set changed. We simply operate on the map's keys, which will write-through:
  if (map.keySet().remove(key)) {
    deleteAssociatedFiles(key);
  }
I learned this trick from Jared of the 
Google Collections team.
    # posted by Jesse Wilson 
     on Monday, March 10, 2008
     2 comments
               post a comment
    
    
   
 
  
    Java Minutiae - I love ternary
    I love the 
? : ternary operator. It makes my code feel tighter. Plus, I get to save code - fewer assignments, fewer return statements, and variable declarations are inline. In the code I was writing yesterday, a duplicated call to 'add()' made me itch for the ternary:
    for (String key : keys) {
      if (getCardinality(key) == 1) {
        singleValuedKeys.add(key);
      } else {
        multiValuedKeys.add(key);
      }
    }
Unfortunately, with standard use of a ternary, the code gets bigger instead of smaller:
    for (String key : keys) {
      Set<String> setToAddTo = (getCardinality(key) == 1)
          ? singleValuedKeys
          : multiValuedKeys;
      setToAddTo.add(key);
    }
Taking it one-step further, I inline the 
setToAddTo variable. This is where the code loses its familiar feel:
    for (String key : keys) {
      ((getCardinality(key) == 1)
          ? singleValuedKeys
          : multiValuedKeys).add(key);
    }
It's tight, but somehow I've written Java code that doesn't have the Java feel. So I ended up dropping the ternary, and went with the familiar if/else structure. What's your preference?
    # posted by Jesse Wilson 
     on Monday, March 10, 2008
     8 comments
               post a comment
    
    
   
 
  
    Guice wins Jolt Award!
    From the 
Guice User's group,
Congratulations Bob, Kevin and the rest of the Guice team! Guice beat out rival Spring and several other worthy projects to win the 2008 Jolt Award for libraries and tools.
It was great to see the guys win - they deserve to be recognized for their hard work.
The award is also good news for Google's open source effort. It confirms Guice as a top-tier open source project, and encourages them to invest more in open source. Plus, the award should help to put some momentum into the development of Guice 2.0.
I'm looking forward to seeing Kevin & Bob's picture in an upcoming issue of Dr. Dobb's Journal. In the picture, they're holding the award: a giant can of Jolt encased in lucite. The award may also be recognized on one of the Google blogs. 
    # posted by Jesse Wilson 
     on Wednesday, March 05, 2008
     1 comments
               post a comment