Wednesday, February 23, 2011

Prevalence of Non-Java JVM Languages on JVM

The current Java.net poll is showing some interesting early results. With the number of responses approaching 100 so far, the poll question How much of your JVM-based programming is in languages other than Java? reveals that just over half of the respondents replied "All my JVM programming is in Java." In my experience, an even higher percentage of Java developers do not do any "JVM programming" outside the Java language itself. However, I'll admit that I had expected more than half of the respondents to a Java.net survey to be regular users of JVM languages other than Java. There has always been a disconnect between the everyday Java developer and the Java developer who regularly reads and responds to online Java community resources such as Java.net.

Only ten percent of current responses indicate "Most of my JVM programming isn't in Java." That relatively small percentage was about the percentage I would have predicted for a Java.net audience, but I don't know of any JVM developer that I know well who would have selected this response. Every developer I know that uses the JVM uses Java quite a bit still, but I'm confident that some of this depends on "the shop" one works in and what they are working on.

I believe that I fall into one of the two in-between categories: 20 percent "occasionally I use / have used other JVM languages" while 12 percent "use other JVM languages quite a lot." A few years ago, I was solidly in the "All my JVM programming is in Java" camp, but that changed once I got a solid taste of Groovy, played with JRuby, flirted with Scala, and thought Clojure had some interesting ideas. I've never been interested in jPerl or Fortran on the JVM. In a matter of about three years now, I've gone from Java only, to the "occasional" use of alternative JVM languages, and in the last couple years to using "other JVM languages quite a lot."

One of the reasons I like using Groovy and Java is that I use them largely independently of one another but in complimentary fashion. In other words, I mostly "mix" the two languages when my scripting meets my application development. I tend to prefer application development in Java and scripting and other developmental environment tasks in Groovy. The fact that my Groovy scripts can easily access my Java applications via a wide variety of Java-based interfaces makes this a particularly powerful combination. I know that there is a large group of people who use Groovy for application development, but I doubt there are many people who use Java for scripting.

My gut feel (and I have no evidence of this, squarely placing it within the "Speculation" category of this blog) is that Groovy is most likely to be the alternative JVM language that is heavily and frequently used without entirely or largely replacing Java for a particular developer. I postulate this because I imagine that a JRuby developer is choosing JRuby for reasons to do more with Ruby+JVM than for reasons having to do with the Java programming language. The same is likely true for Jython: it is likely to appeal to the developer who cares more about Python+JVM than about the Java language.

I believe that developers who use Clojure and Scala are more likely to be using these languages for full application development and largely as a replacement in a situation they would have previously used Java for. Although Groovy can be and is used for application development, my belief is that a large number of JVM developers use Groovy+Java in a way similar to how I use it: Java for the lion's share of application development and Groovy for scripting and environmental tasks. A big and growing subset of these users are likely to be systems administrators and database administrators who use Groovy to support Java-based development environments in which these administrators may not work much with Java itself. The most obvious exception to this might be Grails developers who might have largely or entirely replaced their web development in Java with Groovy/Grails.

Conclusion

There are numerous advantages to learning and using alternative languages that run on the JVM. I'm certainly happy to have so many options with their own set of strengths and advantages. The availability of alternative JVM languages has brought significant excitement to the Java community, but these Java.net results indicate that there is still significant potential for further growth and popularity of these alternative JVM languages among the Java development community.

Monday, February 21, 2011

Misplaced Urgency

Most experienced software developers have experienced a sense of urgency multiple times throughout their careers. There are positive aspects associated with a sense of urgency. such as motivating people to work harder and/or better. However, there are also negative effects of misplaced or false urgency such as distraction from what really deserves attention and allowing short-term decisions to override better long-term decisions while putting out fires. In this post, I look at techniques that can be used to create and properly maintain a sense of urgency and actions that can detract from a sense of urgency.

Authentic Source of Urgency

Phony urgency doesn't fool people for long. Any sense of urgency needs to be associated with real deadlines that really matter and for which there are real consequences if the deadlines are not met.

Significant Source of Urgency

Most developers are only going to feel a real sense of urgency if something significant and substantial is involved. If the end result for which the sense of urgency exists is small or deemed insignificant, then it is difficult to create or maintain that sense of urgency.

Actions Speak Louder than Words

Behaviors that belie urgency will completely drown out any spoken words regarding urgency. A manager who tells his or her employees that extra effort is required to accomplish a certain task in a limited amount of time needs to be sure not to behave in ways that detract from this message. If that same manager holds overly long meetings, involves extraneous individuals in the meeting who don't need to be there and don't have anything to add, or otherwise unnecessarily distracts people will have a difficult time convincing anyone that there is a real sense of urgency. A manager who tells his or her entire team that there are some tough deadlines approaching and finds a way to stuff 15 minutes of substance into an hour-long meeting is really sending a message that is entirely different than what he or she is saying. Similarly, unnecessary process or other nonproductive behaviors are quickly recognized by developers and reduce any credibility about an advertised sense of urgency.

Significant Actions Are What Matters

Some actions and behaviors matter more in establishing and maintaining a sense of urgency than others. For example, running between meetings to save a few seconds is probably not going to make a project due in five days be finished any sooner. However, highly organized communication techniques (short meetings, instant messaging, coordinator, etc.) can be used to improve the speed at which decisions are made and instituted.

The House Cannot Always Be On Fire

If a team is always running around frantically, the effect can begin to wear off. Too much urgency, especially if handled improperly, can backfire in the long run after some short term gains. If there is never an end in sight, developers may begin to not believe there is really a sense of urgency, may look for less chaotic situations, or may just give up. This isn't to say that a sense of urgency cannot be maintained; it's just that the urgency needs to be reasonable and real.

Share the Rewards

When developers respond to a sense of urgency, they should be allowed to enjoy the satisfaction associated with meeting a deadline or other milestone that caused the urgency in the first place. Individual and team recognition is often appreciated and motivating. Monetary compensation is never turned down either.

Externally Generated Urgency is Better Received than Internally Caused Urgency

Most developers will respond better to urgency caused by external forces such as market pressures, competitive forces, and customer demands. Many developers respond less enthusiastically if it is perceived that urgency is required due to mismanagement, neglect, incompetence, or other dysfunctional behavior within their own organization.

Don't Tie Urgency to Moving or False Deadlines

If a manager establishes a sense of urgency by advertising a deadline that somehow keeps moving or turns out not to be a real deadline, it is likely that same manager will have a difficult time doing that again. Developers are likely to be suspicious of any real or hard deadlines and to suspect the manager of trying to manipulate them.

The Best Sense of Urgency is My Sense of Urgency

In the movie The Other Boleyn Girl, Lady Elizabeth tells her daughter to live with and learn from the Queen of France and instructs her: "Observe the ladies of the court. See how they achieve what they want from their men, not by stamping their little feet but by allowing the men to believe that they, indeed, are in charge. That is the art of being a woman."

This can be the most effective way to establish a sense of urgency: allow developers to know what deadlines (external or internal) are coming and the consequences of making or missing those deadlines. Developers will soon be able to conclude for themselves that there is a sense of urgency. Developers will think it was their idea because it was their idea (even if you had it first). Most people, including developers, respond better to their own ideas and own perceptions than they do to the ideas they feel are foisted upon them by others. Providing the data to allow developers to recognize for themselves the sense of urgency may be a little trickier than just advertising it directly, but it can be much more beneficial. Of course, this approach relies on there being a real and substantial reason for a sense of urgency.

Respond Appropriately to Sense of Urgency

This should go without saying, but I'll write it here anyway. A sense of urgency is useless, or, even worse, detrimental if the responses to the sense of urgency are dysfunctional. Short-term thinking cannot be allowed to ruin long-term prospects. A sense of urgency can motivate extra effort and greater efficiency, but can also lead to negative consequences if responses to it are not managed properly.

Conclusion

A sense of urgency can be a useful thing. In fact, I have found that it can even be a little more fun and exciting to have an appropriate degree of urgency when it is appropriately handled and exists for a truly urgent need. However, there are few things more disappointing than being the victim of a false or over-exaggerated sense of urgency.

Dilbert.com (30 July 2007)

Dilbert.com (11 December 2003)

Java's File.deleteOnExit() in Groovy

I've blogged before (File.deleteDir(), File.getText(), and More File Fun) on the useful features that Groovy's GDK extension of the File class adds to Java's File class. However, Java's File class is no slouch itself and brings some highly useful functionality to Groovy scripts (and obviously Java applications) without any Groovy extensions required. In this post, I look at one such method: Java's File.deleteOnExit().

Java's File.deleteOnExit() has been available since JDK 1.2. The documentation for this method states:
Requests that the file or directory denoted by this abstract pathname be deleted when the virtual machine terminates. Files (or directories) are deleted in the reverse order that they are registered. Invoking this method to delete a file or directory that is already registered for deletion has no effect. Deletion will be attempted only for normal termination of the virtual machine, as defined by the Java Language Specification.

This simple method is simply demonstrated in the next Groovy code listing.

demoFileDeleteOnExit.groovy
#!/usr/bin/env groovy
/*
 * Demonstrate using Java's File.deleteOnExit() method in a Groovy script.
 */
def tmpFile = new File("temp.txt")
tmpFile.deleteOnExit()
tmpFile << "Dustin was here!"
println "${tmpFile.text}"

The above example is silly, but demonstrates the functionality. In a more realistic situation, a temporary file might be created to be acted upon by other file-handling capabilities in Groovy or other products. If the file truly is temporary and is merely a means to an end, then it is nice to have it automatically removed upon JVM exit.

When the line above that invokes the deleteOnExit() method is not present or is commented out, the "temporarily" created file is left around when the script finishes. The next screen snapshot demonstrates this.


When the invocation of deleteOnExit() is executed, the "temporarily" completed file is removed automatically upon successful completion of the script. This is demonstrated in the next screen snapshot.


Because deleteOnExit() is a method on the Java version of the File class, it is obviously available to Java applications as well as Groovy scripts. However, it is my experience that I use this type of functionality more often within scripting than in regular application development. It is obviously possible to clean up after oneself with explicit file deletion calls, but I like the automatic handling of removing upon exit provided by Java's File.deleteOnExit() method for clearer and more concise scripts. Because many of my scripts are self-contained and relatively small, and because Groovy kicks off a new JVM for each individual execution of my Groovy script, I know that the file deletion takes place in a timely manner.

Groovy Javadoc-based API Documentation: Three's Company

I have found three sets of Javadoc-based API documentation to be worth bookmarking. In this post, I briefly look at each of these.


Groovy JDK API Specification (GDK)

The Groovy JDK API Specification (http://groovy.codehaus.org/groovy-jdk/) provides documentation for Groovy's GDK, a set of classes and interfaces that extend the same-named Java classes and interfaces. The overall description provided by this documentation is the simple sentence: "This document describes the methods added to the JDK to make it more groovy." Much of the Groovy goodness I use everyday comes from these handy extensions to Java SDK classes such as String, File, List, Object[], and Object.


Groovy Javadoc for Java Classes

Groovy's JavaDoc for Java classes (http://groovy.codehaus.org/api/) provides API documentation for Java classes used as part of the Groovy implementation. Examples of classes that are documented as Java classes in Groovy include AntBuilder, MarkupBuilder, Closure, Expando,
Sql, Tuple, XmlParser, XmlSlurper, and GString. I don't use this API documentation very often because it is limited to Groovy's Java classes and the next discussed API documentation covers both the Java and Groovy classes that are a standard part of Groovy in a single set of documentation.


GroovyDoc for Groovy and Java Classes

Groovydoc for Groovy and Java Classes (http://groovy.codehaus.org/gapi/) is one-stop shopping for both the Groovy and the Java classes delivered with Groovy that are not accounted for in the GDK documentation previously discussed. In other words, "Groovydoc for Java and Groovy Classes" covers the same Java classes covered by the last API documentation and throws the Groovy classes in as well. The GDK classes are not included and still must be accessed in the Groovy JDK documentation discussed first in this post. Because "Groovydoc for Groovy and Java Classes" contains the Java classes, it provides documentation for classes such as AntBuilder, Closure, XmlParser, XmlSlurper, and GString just as the last discussed documentation did. However, it also has Groovy classes and so includes the documentation for classes such as CliBuilder. The GroovyDoc documentation also states whether each document class is Groovy or Java. Because it does not include the GDK classes, it does not document Groovy's extensions to String, List, Object, and so forth.


Conclusion

There is no shortage of Groovy API documentation. The two sets most Groovy developers will need are for the Groovy GDK and for the GroovyDoc with Groovy and Java Classes.

Saturday, February 19, 2011

Customizing Groovy's CliBuilder Usage Statements

There are numerous online examples that use Groovy's baked-in Apache Commons CLI based command-line parsing support. These examples include Groovy Command Line Options, Chris Mahns's Groovy Script: Get SSL Cipher and CLIBuilder Example, Groovy Goodness: Parsing Commandline Arguments with CliBuilder, and some of my own posts such as Explicitly Specifying 'args' Property with Groovy CliBuilder and Using Groovy to Check Seventh Grade Homework. Most of these examples do a nice job of showing how to use Groovy's CliBuilder to accept and properly process command-line arguments, but most of them do not fully demonstrate the granular control one can have over the usage statement provided by CliBuilder. This post addresses that by looking at some of the options one can use to granularly control the usage statement. I also look at nuances involved in specifying multiple values for a single command-line flag/argument.

The following Groovy code listing demonstrates using Groovy's built-in command-line parsing support to obtain city, state, and zip code details. It demonstrates how to handle multiple values for a single argument and how to use the "header" and "footer" options in CliBuilder to add more details to the printed usage statement.

#!/usr/bin/env groovy
/*
 * This is a simple script that demonstrates Groovy's built-in support for
 * Apache Commons CLI command-line argument parsing.
 */

// Many examples of using CliBuilder do so by instantiating it with a single
// 'usage' parameter. This example goes past that.
//    * 'header': Displayed after usage but before options.
//    * 'footer': Displayed after usage options.
//    * Multiple values for same command-line argument/flag.
//
def cli = new CliBuilder(
   usage: 'demoGroovyCliBuilder -c cityName -s stateName -z zipCodes',
   header: '\nAvailable options (use -h for help):\n',
   footer: '\nInformation provided via above options is used to generate printed string.\n')
import org.apache.commons.cli.Option
cli.with
{
   h(longOpt: 'help', 'Usage Information', required: false)
   c(longOpt: 'city', 'City Name', args: 1, required: true)
   s(longOpt: 'state', 'State Name', args: 1, required: true)
   z(longOpt: 'zip', 'Zip Codes (separated by comma)', required: true, args: Option.UNLIMITED_VALUES, valueSeparator: ',')
   o(longOpt: 'options', 'Print Options', required: false)
}
def opt = cli.parse(args)

if (!opt) return
if (opt.h) cli.usage()

def cityName = opt.c
def stateName = opt.s
def zipCodes = opt.zs   // append 's' to end of opt.z to get more than first
def printOptions = opt.o
print "The city ${cityName}, ${stateName} has the following zip codes: "
zipCodes.each
{
   print "${it} "
}
if (printOptions) println cli.options


In the above listing, I provided the CliBuilder constructor with three arguments: the oft-used usage argument along with header and footer arguments. The usage string is shown first, followed by the header string, followed by presentation of the options, followed by the footer. This is demonstrated in the next screen snapshot which shows the output of the script when the usage is displayed because no required options are specified and includes a successful running of the script to demonstrate the correct parsing of the multiple comma-separated zip codes provided to the -z/--zip option.


The "header" and "footer" are convenient because they allow for further customization of the usage statement beyond simple specifying a single Usage string and the individual options' descriptions. Various details about the options or about using the script can be provided via the header and footer mechanisms.

The use of multiple values for a single argument can also be highly useful. The direct use of Apache Commons CLI's Option class (and specifically its UNLIMITED_VALUES constant field) allows the developer to communicate to CliBuilder that there is a variable number of values that need to be parsed for this option. The character that separates these multiple values (a common in this example) must also be specified by specifying the character via "valueSeparator." It is also important to note that multiple values for the same argument are accessed by adding an "s" to the end of the option name when retrieving it from the instance of Groovy's OptionAccessor (variable named 'opt' in code listing above.)

Conclusion

Groovy's built-in command-line parsing is nice to use and can be customized via the usage, header, and footer settings. It also supports specification of multiple values for a single argument.

Contracts for Java: Another Entrant in Java Programming by Contract

Earlier this month, the Open Source at Google blog featured a post on Contracts for Java, a project described in that post as a "new open source tool" that is "based on Modern Jass by Johannes Rieken." Design by ContractTM (DoC) is often associated with the Eiffel programming language and, in fact, this term is trademarked by Eiffel Software. Because the term "Design by Contract"TM is trademarked, other terms often used to describe the same approach include "Programming by Contract" and "Contract-First Development." (This might be an opportune moment to explicitly mention what my blog always states: trademarks used here remain the property of their respective owners.)

Contracts for Java is not the first framework or tool aimed at providing Java developers the ability to use contracts to spell our preconditions, postconditions, and invariants in their code. Indeed, the Wikipedia entry on Design by Contract includes a section on languages with third-party support for this concept and numerous Java tools and frameworks are listed. These include Modern Jass, Contract4J, jContractor, and C4J. The Java Modeling Language can also be used to reach the same objectives and there are various tools that support JML. Another option is object validation with OVal.

Java's directly available assertions mechanism can be used for similar purposes. The Preconditions, Postconditions, and Class Invariants section of Programming with Assertions states "While the assert construct is not a full-blown design-by-contract facility, it can help support an informal design-by-contract style of programming." This section then goes on to explain that assertions should not be used to "check the parameters of a public method," but that it is acceptable to check the parameters of nonpublic methods and that assertions can be used to check the postconditions of both public and nonpublic methods.

The reasoning for not using assertions for public method argument checking is that assertions can be turned off at runtime and thus cannot prevent improper invocation of the public methods. This continues to be an issue for Contracts for Java as well because it allows its runtime checking to be disabled. The Contracts for Java FAQ addresses the comparison of assertions to Contracts for Java in the answer to the question How is this better than using assert?

Another Java-oriented approach to contract-first programming is Groovy-based gcontracts, a project directly inspired by Bertrand Meyer's "design by contract" terminology used in Object Oriented Software Construction.

The comments (16 of them at time of this writing) on the Contracts for Java announcement are interesting. They indicate some general reservations among Java developers about the need for the project. The availability of existing frameworks (some of which I mentioned above), the availability of the standard assertion mechanism, and a desire to see support given to JSR-305 instead.

Contracts for Java is a very new project that is likely to have some growing pains. It enters an already crowded field and a possibly skeptical audience. It does have some things going for it including a general agreement about the wisdom in Design by ContractTM and Google support (via the 20% time piece of The Google Way). I will be interested to see if it can rise above the existing frameworks, libraries, and tools designed for contract-oriented Java development.

Recent Posts of Significant Interest (Java Security, XML, Cloud Computing)

I maintain a list of topics that I would like to blog on sometime in the future. This list continues to grow as I cannot blog quickly enough to keep up with the ideas. In some cases, I simply cannot write the full blog post I'd like in response to a really good blog post and, when enough of them are gathered up, I publish a post like this one that covers multiple blog posts at the same time. In this post, I reference recent online posts that I have really enjoyed on topics such as Java security issues, Javadoc, XML, and cloud computing.


JavaDoc: The unloved child. A pragmatic approach.

One of the things I think it done better in Java than in just about any other language I have used is documentation via Javadoc. I frequently use Javadoc-generated documentation for the Java SE, for the Java EE, and for other products in the Java ecosystem such as JFreeChart and Groovy (which has three!: GDK, Javadoc for Java Classes, and Groovydoc for Groovy and Java Classes). I find using others' Javadoc to generally make it easier to use their APIs (assuming correct documentation!) and I like the ability to have ready access to API documentation online and in my favorite IDE. I also enjoy being able to document how to use my APIs, packages, and classes, in package descriptions. This allows the clients of my APIs to see examples of how to use my API and nicely includes the documentation in the same area/file as the source code itself. In the post JavaDoc: The unloved child. A pragmatic approach., Markus Eisele concisely describes why Javadoc is useful and suggests some tips for making writing and maintaining of Javadoc comments more effective.


XML: Contrary to popular belief, it doesn't always kill babies

We software developers (as a whole) seem to be prone to violent swings between positions on things. Derek Thurn's post XML: Contrary to popular belief, it doesn't always kill babies does a nice job of pointing out how this happened with XML (loved and revered for a while and now not discussed in polite company). As with most of these extreme shifts, neither extreme was appropriate. XML was overhyped for a while and was used in many unnatural ways, but now developers in general (if the blogosphere is at all indicative) seem to wish to avoid XML without regard to the problem. I believe the appropriate position is somewhere in between. Thurn's post briefly discusses situations where alternatives like JSON and YAML are preferable to XML and the outlines two situations where he believes XML is appropriate (and I agree). I also like that Thurn states "XPath turned out to be a godsend" (something I have found as well in my work with XQuery and other things areas where XPath support is useful). It's also very difficult to argue with Thurn's use of SOAP as an example of "terrible things" people have done with XML.


10 Reasons to Say “No” to Cloud Computing?

I like posts that challenge the Lemming Effect. The previously discussed XML post challenges the potential lemming behavior of avoiding XML regardless of whether the situation warrants it or not and is an example of bucking the lemmings' general direction avoiding something (negative reaction). On the other side, it can be just as useful to avoid thoughtless following of lemmings to adopt something (positive reaction). I like 10 Reasons to Say “No” to Cloud Computing? because the author starts out with this:
I have been writing about the benefits of migrating to the Cloud in previous articles but it is also important to highlight in which circumstances the Cloud Computing route may not be the appropriate one.

When I first read this paragraph, I was afraid this post was going to be another one of those that would have ten reasons such as "you want to do things the hard way" and "you like a good challenge." Fortunately, this post turned out to be what was really advertised. The ten reasons are good ones to think about and I also appreciate the author's pointing out that "Cloud Computing is NOT an all-or-nothing decision." No tool or methodology can be all things to all people all the time and I suspect anyone who claims their favorite to do just that. It is much more useful to read from an evangelist of an approach about where that approach fits or does not fit and this post fits into that more useful category. Some people think cloud computing is not a good idea, but it (or portions of it) can be useful when applied correctly in the appropriate situations.


Java Security

Two recent articles of interest related to Java security are RSA: Java is the Most Vulnerable Browser Plug-in and Google extensions could aid Java security.

In "RSA: Java is the Most Vulnerable Browser Plug-in," Sean Michael Kerner reports that Qualys CTO Wolfgang Kandek stated that 42% of monitored web users had "vulnerable out-of-date" Java plug-ins and that this plug-in was the most frequently out-of-date and vulnerable of those measured. Other plug-ins that were vulnerable due to being frequently out of date include Adobe Reader, Apple QuickTime, and Adobe Flash. As I read this, the ranking is not of how vulnerable one plug-in is as compared to another, but how vulnerable they are because they are out-of-date. Kerner also points out that Cisco had reported that Java vulnerabilities are now more exploited than those in Adobe Acrobat and Reader.

Joab Jackson writes that Google Contracts (Contracts for Java or cofoja), which is often advertised as and thought of as an approach for making it easier to appropriately use methods (above and beyond what the previously mentioned Javadoc provides), can also help make Java code more secure. He states that this project based off of Modern Jass can provide some of the same security benefits to Java that Eiffel developers claim are inherent in Eiffel's support for Design by Contract (DbC).


Conclusion

There are far too many interesting and insightful posts about software development to keep up with all of them. In this post, I've tried to summarize and publicize some recent posts that I believe are worth a look if you have not read them already.

Wednesday, February 16, 2011

RMOUG Training Days 2011: First Day

Today was the first day of the Rocky Mountain Oracle Users Group (RMOUG) Training Days 2011 regular sessions (there were half-day University Sessions yesterday with a much smaller overall participation level for these focused presentations). It was announced at lunch that this is the twentieth edition of RMOUG Training Days. They asked who was attending for the first time (a small number of hands responded to this), who had attended at least three times (greater number of hands raised), and who had attended five times, ten times, fifteen times, and all twenty times. Of the eight or so people at my table, at least four of us had attended more than ten editions of this conference. For me, this is my twelfth time attending and tenth year of presenting.

It is always satisfying to see a decent number of people show enough interest in a topic and provided abstract to attend one's presentation. Both my 90-minute Groovy presentation ("Groovier Java Scripting") and my 30-minute HTML5 presentation ("A First Look at HTML5") were relatively well attended with somewhere between 40 and 60 people in attendance in each.

There are three ways that I typically observe how interesting one of my presentations is to the general audience. The first is the obvious observation of what percentage of the audience is sleeping, obviously day dreaming, or otherwise obviously retreated to their happy place. I didn't seem to see any more people sleeping or fighting sleep than normal in either presentation and I didn't fall asleep, so things seemed to go well from that perspective.

The second measurement is the percentage of people who leave early. You can always expect a small number of people to leave as they realize a presentation or its topic is not what they were looking for or at the level they were looking for. This is especially true of longer presentations where people are more likely to abandon ship if they think they are in it for the long haul and just cannot stand the idea of that. There weren't many who left either presentation and I chose to stay the entire time, so I believe things also went well from this perspective.

The third measurement is the number and types of questions asked. I have been especially impressed with the insightful questions asked at RMOUG Training Days in recent years. These questions improve the overall value of the presentation because the answers either allow me to emphasize small points I made or thought I made or to cover points I had wanted to make but had forgotten to make. The content of the questions tells me if the audience is understanding the points I am trying to make. Today's questions in both sessions were all excellent and relative and implied to me that at least those asking the questions were hearing and understanding the implications of what I was talking about.

Both audiences at today's presentations of mine were outstanding and highly participative. Preparing for these presentations requires significant time and effort and it is more motivating for me to invest that time and energy when I have such great audiences who seem to appreciate the effort and who are actively involved. I learn much for preparing these presentations and that is a big motivator for doing so, but it is nice to feel that I may be contributing to the general good as well.

There were some changes in Training Days this year. One noticeable change was the different portion of the Colorado Convention Center in which the conference was held this year. Another change was no CD provided with presentations and papers (these are downloaded from RMOUG's Schedule Builder instead). I remember the years when we had voluminous bound books containing the white papers and it is interesting to see how far we've come.

Several other posts about RMOUG Training Days 2011 have started appearing. Kenneth Lee talks about a university session in RMOUG – First University Session. Shay Shmeltzer summarizes the presentations at Training Days 2011 related to Oracle ADF in the post ADF Sessions at RMOUG This Week. I expect to see at least a few more posts regarding this conference over the next few days.

Tuesday, February 15, 2011

AntBuilder: Groovy Meets Ant

One of convenient classes that Groovy provides is the AntBuilder class, whose purpose is best described in the Javadoc-based documentation: "Allows Ant tasks to be used with GroovyMarkup." The AntBuilder class provides a strong association between the Groovy programming language and the well-known and ubiquitous Ant build tool.

The Ant Integration with Groovy section of the Groovy User Guide describes three common situations in which Ant ("the predominant build environment for Java projects") and Groovy ("a leading Scripting language for the JVM") are used in conjunction with one another. The first listed approach is when developers supplement their Java-building Ant build.xml scripts with Groovy using the specific to Groovy <groovy> tag or the general to Ant <script> tag and embed Groovy code inside these tag's bodies.

The second listed approach for integrating Groovy and Ant is to use Ant to compile Groovy code. The groovyc Ant task (<groovyc>) can be used to build Groovy code with the groovyc joint compiler. Although it can be desirable to run Groovy scripts and other code without explicit compilation, there are several advantages to compiling Groovy with groovyc and this groovyc Ant task makes this even easier to do.

The third listed approach for integrating Groovy and Ant is use of AntBuilder and is the focus of this blog post. Groovy's DSL capabilities are leveraged by AntBuilder to provide a "fluent" Groovy markup representation of the Ant tasks most of us are familiar with from Ant XML files.

There are advantages to being able to apply one's Ant knowledge from within Groovy code. First, many of us have used Ant for years and have anywhere from a passing familiarity to deep knowledge of the available Ant tasks. This is an advantage both in terms of developing the Groovy script code and in terms of others reading and maintaining the code. Even a relatively inexperienced Groovy developer who has some Ant knowledge will benefit when using AntBuilder in Groovy scripts.

The second advantage of being able to invoke Ant functionality easily from Groovy code is that Ant has gained significant functionality over its (relatively) long existence. Ant is no longer used explicitly for simple compilation and JAR/WAR/EAR assembly. It has functionality for file copying and naming, using Java mail, and a wide breadth of other functionality. All of Ant's richness is available to the Groovy developer via AntBuilder. In some cases, it may be easier (more concise) for the Groovy developer to use Ant's predefined task functionality than to write the equivalent functionality in Groovy.

Even when the task is to build Java projects, a developer may choose to perform the build via Groovy scripts rather than via Ant and its XML directly. That is another example of an advantage offered by Groovy+Ant integration encapsulated in AntBuilder. The developer can write Groovy scripts with conditionals, loops, and other full language constructs while still taking advantage of Ant's deep and broad building functionality. In other words, with AntBuilder, the developer can benefit from all of Ant's features without using XML.

AntBuilder makes use of and is illustrative of Groovy's metaobject facilities and the ability to build Domain Specific Languages (DSLs) in Groovy. Martin Fowler describes what a domain specific language is: "a computer language that's targeted to a particular kind of problem, rather than a general purpose language that's aimed at any kind of software problem." I have illustrated another Groovy DSL (MarkupBuilder) in the post GroovySql and MarkupBuilder: SQL-to-XML. Like MarkupBuilder, AntBuilder extends the abstract base class BuilderSupport (as do SwingBuilder and NodeBuilder).

The Groovy builders are particularly well suited for generating hierarchical data output. Therefore, it's no surprise that builders are useful for building markup (XML and HTML for example) and even for helping with Swing. See How Builders Work for a basic introduction into using Groovy builders and Practical Groovy: Mark it up with Groovy Builders for greater details.

AntBuilder makes it easy to harness the functionality of Ant from within Groovy code. I'll use of an example of using AntBuilder to begin my explanation of how it works and is used. Ant's support for file operations has been proven perhaps millions of times by now. The next code listing demonstrates Groovy code that uses AntBuilder to take advantage of Ant's file copying functionality. AntBuilder is not the only way to copy files in Groovy and two other ways (copying delegated to Windows/DOS operating system and copying using Groovy GDK) are also included in the example.

demoGroovyFileCopying.groovy
#!/usr/bin/env groovy

/*
 * demoGroovyFileCopying.groovy
 *
 * Demonstrates copying files in Groovy with three different mechanisms:
 *   1. AntBuilder
 *   2. Operating System copying with String.execute()
 *   3. Groovy File.write(File.text)
 */
 
 // AntBuilder instance used throughout this script
 AntBuilder antBuilder = new AntBuilder()
 
 demonstrateFileCopying(args[0], "target", antBuilder)
 
 /**
  * Demonstrate file copying in Groovy. Generated target files will be copies of
  * the file represented by the provided sourceFilePathAndName and the generated
  * files have names that start with the targetFileNameBase and have the type of
  * Groovy copying appended to the base in the file name.
  *
  * @param sourceFilePathAndName Path and file name of source file to be copied.
  * @param targetFileNameBase Base portion of name of all target files created
  *    as copies of the source file.
  */
 def void demonstrateFileCopying(
    final String sourceFilePathAndName,
    final String targetFileNameBase,
    final AntBuilder ant)
 {
    // File copying with AntBuilder
    def targetFileFromAntCopyName = targetFileNameBase + "_ant"
    def targetFileFromAntCopy = ant.copy(file: sourceFilePathAndName,
                                         tofile: targetFileFromAntCopyName)

    // File copying with Windows/DOS operating system and GDK String.execute()
    //   (use 'copy' in DOS and need 'cmd /c')
    "cmd /c copy ${sourceFilePathAndName} ${targetFileNameBase+'_dos'}".execute()

    // File copying with Groovy GDK File functionality
    def sourceFile = new File(sourceFilePathAndName)
    new File(targetFileNameBase + '_groovy').write(sourceFile.text)
 }

The next screen snapshot demonstrates the directory before and after this script is executed and includes the output showing the Ant functionality for file copy being invoked.


It could be argued that for file copying, using the Groovy approach with the GDK File class is the easiest approach. However, a Groovy developer not familiar with the Groovy approach might be more comfortable with the AntBuilder approach. Either approach is obviously preferable in most cases to the operating system dependent approach.

The AntBuilder approach might be easier if specialized functionality related to the copying needed to be performed that is supported by the Ant copy task but might not be so readily applied directly in Groovy. Suppose that I had a file that I not only wanted to copy, but wanted to replace tokens inside the source file with something else in the copied target file. Ant shines here and therefore so does AntBuilder. To illustrate this, I use a simple source file as shown in the next listing.

tokenSource.txt
Hello, my name is @NAME@ and I like Ant and Groovy.

With the above source file in place with a token delimited with the @ character, AntBuilder is again demonstrated in the following example.

copyFileAndReplaceNameToken.groovy
#!/usr/bin/env groovy

/*
 * demoGroovyFileCopyingAndTokenReplacing.groovy
 *
 * Demonstrates copying file with Groovy and AntBuilder and replacing @NAME@
 * token in source file in the copied file.
 */
 
// AntBuilder instance used throughout this script
def ant = new AntBuilder()
def sourceFilePathAndName = args[0]
def targetFileFromAntCopyName =  "target_antToken"
def targetFileFromAntCopy =
   ant.copy(file: sourceFilePathAndName,
            tofile: targetFileFromAntCopyName)
            {
               filterset()
               {
                  filter(token: "NAME", value: "Dustin")
               }
            }

The above Groovy code uses AntBuilder to not only copy the file, but to also replace the token @NAME@ with "Dustin". This output is shown in the next screen snapshot.


As the last example shows, AntBuilder makes it easy to leverage Ant's wide set of functionality from Groovy without a hint of XML. A developer familiar with Ant's XML structure is likely to be able to map Ant XML to the Groovy markup. Builders work so well because they rely on conventions and AntBuilder is no different. The convention is that XML element names are nested within other XML element names by placing them within curly braces of the outer elements. Attributes in the XML map to name/value pairs separated by colons within the parentheses containing arguments to the names associated with XML elements. In other words, the above Groovy script for copying the file with the filter is equivalent to the XML below in an Ant build script (where "args[0]" corresponds to the String passed in as the first argument to the Groovy script).

  <copy file="args[0]" tofile="target_antToken">
    <filterset>
      <filter token="NAME" value="Dustin"/>
    </filterset>
  </copy>

It is relatively easy to see the mapping of the above XML to the Groovy markup the way I indented it. Of course, I could have chosen to use less whitespace to make the code appear even more concise, but at the arguable cost of being less readable.

To apply core Ant tasks (such as copy used above) within Groovy using AntBuilder, nothing has to be placed on the script's classpath because Ant is included in the Groovy distribution. However, any optional Ant tasks that have external library dependencies require those external libraries to be placed on the classpath.

Conclusion

AntBuilder provides powerful functionality for the Groovy developer. While it can certainly be used in building code, its providing of Ant's breadth and depth of features can be useful in all sorts of contexts in which Groovy might be used besides simply builds. Appropriate use of AntBuilder can reduce the necessary Groovy code required for certain operations when Ant already does the heavy lifting. AntBuilder can also serve as a crutch to the developer who knows Ant better than Groovy but wants to write Groovy scripts.

HTML5 Recommended in 2014

There are several recent developments worth noting related to HTML5.

HTML5 Specification Slated for Recommendation Status in 2014

I will be presenting A First Look at HTML5 at RMOUG Training Days 2011 tomorrow and I believe that many of those in attendance will naturally want to know the state of HTML5 today. With that in mind, the W3C announcement of HTML5's planned completion date is timely (the announcement, not the completion date). As reported in SD Times on the Web, JavaWorld/Network World/ComputerWorld/InfoWorld, The Register, and CNet, the World Wide Web Consortium (W3C) has announced plans to extend the HTML Working Group's charter, plans to meet the expectation of the HTML5 specification reaching Last Call status in May of this year, and new plans to progress the HTML5 specification to Recommendation status by 2014. Although 2014 may sound like a long way off, it's better than 2022.


Internet Explorer 9 RC Supports Geolocation API

Other big news in the world of HTML is related to something I will be discussing in tomorrow's presentation: the Geolocation API. Andy Pemberton and Matt Mehalso write that the latest beta release of Internet Explorer (IE9 RC) supports the Geolocation API in IE9 Geolocation in February Release Candidate. As I wrote in my post HTML5 Geolocation API: Your Browser Knows Where You Are, Internet Explorer 8 does NOT support the Geolocation API (though Google Toolbar for Internet Explorer can be used to provide this in IE8). See http://www.beautyoftheweb.com/ for more examples of HTML5 in IE9 RC or http://windows.microsoft.com/ie9 to download it.


W3C's Select Priorities and Milestones of 2011

The W3C has also posted W3C 2011: Select Priorities and Milestones, which does exactly what the title suggests: lists and describes specific priorities and milestones for the W3C in 2011, including focus on powerful web applications (with mention of Last Call for HTML5 in May 2011 and more work on HTML5 logo), web on television and mobile devices, and a web universally available to all.


Adobe Contributes to JQuery Mobile/HTML5

Cade Metz writes in The Register's Adobe open source code backs – gasp! – HTML5 that "Adobe is contributing to the open source jQuery Mobile" to "help create mobile components and to help create the capacity to develop more interactive and more engaging animation experiences." The article goes on to outlines other areas in which Adobe has contributed to various web browsers and HTML5 authoring tools.


Conclusion

Much is happening currently related to HTML5. The recent announcement of a planned delivery of a Recommendation for HTML5 coincides with announcements of browsers' continued enhanced support for HTML5. While all of this progress in HTML5 makes the timing of my presentation on HTML5 more current and cutting edge, it adds to the already difficult challenge I am facing of covering features of HTML5 along with the many political and process developments associated with HTML5 all in 30 minutes.

Saturday, February 12, 2011

JavaOne 2011 and Oracle OpenWorld: October 2-6, 2011

JavaOne 2011 is scheduled for October 2-6, 2011, in San Francisco. It appears that JavaOne will again be held in conjunction with Oracle OpenWorld. There is also evidence that JavaOne will again not be in the Moscone due to co-located Oracle OpenWorld: the JavaOne and Oracle Develop Exhibition Floor Map shows the exhibition area being in the Continental Ballroom of the Hilton San Francisco Union Square (the exhibition contract also verifies this). Although many had hoped that JavaOne 2011 would NOT be co-located with Oracle OpenWorld or that they would be held consecutively rather than simultaneously, it definitely seems that the conferences will be co-located again.

Java State of the Union: One Year Under Oracle

In this post, I look at three recent and interesting posts related to the state of Java today.


Java State of Union

In his first Java Observer/Observable post (Change of State), Athen O'Shea makes some observations regarding "Oracle's influence on Java so far" and refers to the upcoming (February 15) OTN Techcast (Java and Oracle, One Year Later) as Oracle's "first State of the Union" for Java.

In his post, Athen states that he'd like JavaWorld readers and contributors to comment on their thoughts regarding "Oracle's influence on Java so far." Athen adds that he is not looking so much for obvious comments about obvious Oracle impacts on Java or wild attempts at fear, uncertainty, and doubt (FUD). Rather, Athen is "more interested in subtleties and contradictions" and provides three examples:
  1. Oracle alliances with powerful competitor organizations (Oracle, Apple) in OpenJDK and Oracle's JCP Executive Committee nomination of the Brazilian Java Users Group SouJava (represented by Bruno Souza)
  2. "Oracle's well documented unilateral stubbornness in the JCP" contrasted with Doug Lea "being a co-signer on the initial draft OpenJDK governance bylaws"
  3. Multiple facets of the potential of a Java fork.

Athen has identified some interesting subtleties and contradictions. Other things I look forward to finding out is if Oracle is able to retrofit JavaFX to support standard Java APIs and to make it a popular, well-used rich interface technology. I have long believed that one of JavaFX's biggest hurdles was not really being Java in terms of language. However, even with a standard Java API, there will be concerns about JavaFX not being a standard and being proprietary.

The future of NetBeans under Oracle continues to interest me. The recent announcement of NetBeans dropping support for Ruby is obviously disappointing to Ruby developers, but may be an advantage for Java developers if more resources are applied to the Java portions and functionality of the IDE. I'd like to see continued improvements for Groovy and other alternative JVM languages. For example, I'd like to have a Groovy project without it being considered a Grails project. I also look forward to experimenting with Java 7 features in NetBeans 7. I believe that dropping of Ruby support from NetBeans is an overall positive development for most Java developers in the sense that it implies Oracle's true commitment to the Java side of the IDE. For those developers writing Java and Ruby code, it is not as positive.


A Year Later: Has Oracle Ruined or Saved Sun?

In the article A year later: Has Oracle ruined or saved Sun?, Paul Krill looks at the effect of Oracle's purchase of Sun on a wide set of Sun technologies including Java. He talks about NetBeans dropping support for Ruby (a rough week for Ruby), the confrontational relationship between Oracle and Apache (which is really a continuation of the Sun/Apache relationship), the Hudson/Jenkins developments, and the Google lawsuit over Android.


Java Ain't Dead - It's Still #1

Yakov Fain's recent post Forrester, Java ain’t dead – it’s still #1! takes issue with yet another report of Java's demise. Although just as even a broken clock is correct twice a day, the "Java is dead" posters will eventually be correct, just numerous years off on the timing of that event. I have commented on the ridiculousness of such posts previously, but I especially liked the approach Fain took in this post. Fain states (and I have often observed this to be the case): "Unfortunately, people who state that Java’s dead are not the people who use the latest Java technologies day in and day out." Fain also observes that "in this presentation the author made a number of statements that show that his perception of Java platform is based on the status of the platform several years ago." This is understandable: not everyone has the good fortunate to be able to use the latest version of Java EE. However, it also means that those people are less qualified to talk about the current state of the same technology.

I have seen this before in conjunction with Java. In the beginning, Java was slow. Unfortunately, even after years of significant investment by JVM suppliers in making their JVM implementations very efficient, I still ran into intelligent, well-meaning individuals who simply were basing statements on out-of-date personal experiences or opinions heard/read from others that were out of date. For some of these individuals, it took a while for them to come to grips with the idea that things had changed. I always learn best when I do something myself or try it out myself. Reading gets me so far, but then I need to work directly with it to really start to understand. I think many people are this way. Additionally, none of us can read and use every available alternative out there and so must trust what we read and hear from others to a certain degree. The software development blogosphere has never been truly representative of reality, but it is easy to forget that.

"Java is dead" posts are almost as old as Java itself. For a dead language, Java seems to continue to do pretty well. If languages had emotions or feelings, I bet many of the "still living" languages would love to be as dead.

By the way, the post Explained: Java is A Dead-End for Enterprise Application Development, Mike Gualtieri provides an "expansion of my arguments" from the original post Java Is A Dead-End For Enterprise App Development. From the comments, it sounds like Gualtieri's headline may be overly dramatic and more sensationalist than what the real content seems to be: use the right tool for the job. I would have liked to see the original slides themselves, but the "free registration" to download the slides requires a "business email address" (proving once again that nothing is really "free"). I don't usually give out that type of information because I have rarely found such resources to be any better or more informative or more correct than what's publicly available without strings attached.


Conclusion

What is the state of Java? In some ways it's a mess, but in some ways there seems to be lots of potential. It definitely continues to have a future. In The Rise And Fall of Languages in 2010, Andrew Binstock states: "Java, C, C++, PHP, C#, and Python are languages that are widely used and will have plenty of support in the years to come." I agree with him about this set of languages (I have worked all except for PHP, but PHP's prevalence is obvious) and Java definitely fits into the category. Like numerous others, I have stated before that the alternative JVM languages are particular exciting, but Java SE and Java EE continue to be the work horses of the platform.

Wednesday, February 9, 2011

Posts on the Rise and Fall of JVM Dynamic Languages

In this post, I briefly reference two interesting posts that fall into the camp of The Rise and Fall of Dynamic Languages. The first referenced post focuses on dynamic languages on the JVM and the second referenced post focuses specifically on one Groovy developer's perception of Groovy's eventual demise.


Dynamic Languages on the JVM ... Growth or Demise

I first saw the post Dynamic Languages on the JVM ... Growth or Demise when it was referenced on Java.net on 6 February 2011 (Java.net editor Kevin Farnham has since posted more personal analysis on the post and provided this week's poll question based on that post). In Dynamic Languages on the JVM ... Growth or Demise, post author John Yeary references the Dr. Dobb's article The Rise And Fall of Languages in 2010, which itself is based on analysis of the Tiobe Programming Community Index statistics for 2010.

Yeary observes that dynamic languages are said to be in a decline and that JVM-based dynamic languages are said to be in the same decline with fellow dynamic languages. Yeary does not agree and asserts (emphasis is his): "I believe that the decline of dynamic languages is real EXCEPT on the JVM." Yeary speaks highly of Jython and has even more praise for JRuby because "it combines the ease of use in Ruby with the power and multitude of frameworks available in Java."


The Rise and Fall of the Groovy Language

Another really interesting post I ran across this week was Gavin Grover's "The Rise and Fall of the Groovy Language" (no direct link to it currently?). It is obvious from Grover's blogs and other postings that he has seriously invested time and energy into learning, using, and trying to improve Groovy. Despite that, there is obvious frustration in the post "The Rise and Fall of the Groovy Language."

Anyone who has read my blog probably knows that I really like Groovy for scripting. Colleagues also know of my interest in Groovy. Although I am growing increasingly comfortable with the language, I did learn several things about the history (he links to many earlier interesting forum threads related to Groovy development) and possible future of Groovy from Grover's post. Among other things Grover points out the early history of Groovy, the falling out with the project founder, and looks at the name change he believes is coming to the Groovy language.

Grover also outlines four major reasons he believes "[the Groovy] language has been failing." He articulates his reasons in much greater detail, but they can be summarized as follows:
  1. Developer focus on profit over capital development
  2. Too closely tied and dependent on Grails
  3. Groovy language community is really not a community at all
  4. Combination of first and third reason: Groovy "community" is not really such

I recommend this post to anyone interested in the future of Groovy. I don't know Gavin "Groovy" Grover or the other principals involved enough to formulate an opinion on the correctness of these observations and following conclusions. However, there is no doubt that I did learn several things about the earlier days of Groovy from this post and the post is a reminder that politics are in everything, even open source software development. It's also a reminder that there is often a tension between the legitimate desire to profit from previous work and the desire of other community members to continue focusing on the improvement of the product.

Tuesday, February 8, 2011

Groovy Uses JAVA_OPTS

Developers who have used Tomcat in any significant way are likely already familiar with using the environment variable JAVA_OPTS to specify how much memory should be allocated for an instance of Tomcat. The author of CATALINA_OPTS v JAVA_OPTS - What is the difference? points out that JAVA_OPTS may be used by "other applications" and this should be a consideration when deciding whether to use CATALINA_OPTS or JAVA_OPTS. It turns out that Groovy is an example of one of those "other" applications that uses JAVA_OPTS. In this post, I look at some common uses in Groovy for JAVA_OPTS.

Perhaps the most well-known and common use of JAVA_OPTS within Groovy development is for specifying initial and maximum JVM heap sizes used by Groovy scripts and the JVM in which they run. This is specifically mentioned in the Running section of the Getting Started Guide's Quick Start under the heading "Increasing Groovy's JVM Heap Size". There's not much to say here and it's succinctly stated:
To increase the amount of memory allocated to your groovy scripts, set your JAVA_OPTS environment variable. JAVA_OPTS="-Xmx..."

The Groovy Native Launcher page also demonstrates using JAVA_OPTS to specify heap size for a JVM running Groovy under the heading "JAVA_OPTS" and mentions "achieving the same effect" with environmental variable JAVA_TOOL_OPTIONS.

The use of JAVA_OPTS with Groovy is not limited to specifying heap sizes. Indeed, the Native Launcher JAVA_OPTS section states: "The environment variable JAVA_OPTS can be used to set JVM options you want to be in effect every time you run groovy."

Use of JAVA_OPTS in Groovy is not limited to the groovy launcher or to runtime. In the blog post Using groovyc To Compile Groovy Scripts, I discussed several advantages of explicitly using groovyc and one of the advantages I mentioned is the ability to better understand Groovy's inner workings through use of groovyc. JAVA_OPTS can be used in conjunction with groovyc to further this advantage. Specifically, Groovy in Action points out that groovyc "is sensitive to" three properties that can be specified via JAVA_OPTS: antlr.ast=groovy, antlr.ast=html, and antlr.ast=mindmap. I briefly demonstrate using these with groovyc and JAVA_OPTS.

For the examples of using groovyc, JAVA_OPTS, and the "antlr.ast" settings, I will run groovyc against the script findClassInJar.groovy that was introduced in my blog post Searching JAR Files with Groovy. For convenience, I have included that code listing here.

findClassInJar.groovy
#!/usr/bin/env groovy

/**
 * findClassInJar.groovy
 *
 * findClassInJar <<root_directory>> <<string_to_search_for>>
 *
 * Script that looks for provided String in JAR files (assumed to have .jar
 * extensions) in the provided directory and all of its subdirectories.
 */

import java.util.zip.ZipFile
import java.util.zip.ZipException

rootDir = args ? args[0] : "."
fileToFind = args && args.length > 1 ? args[1] : "class"
numMatchingItems = 0
def dir = new File(rootDir)
dir.eachFileRecurse
{ file->
   if (file.isFile() && file.name.endsWith("jar"))
   {
      try
      {
         zip = new ZipFile(file)
         entries = zip.entries()
         entries.each
         { entry->
            if (entry.name.contains(fileToFind))
            {
               println file
               println "\t${entry.name}"
               numMatchingItems++
            }
         }
      }
      catch (ZipException zipEx)
      {
         println "Unable to open file ${file.name}"
      }
   }
}
println "${numMatchingItems} matches found!"

The above script can be run directly without explicitly using groovyc and this is typically how I'd use it. However, I am going to explicitly compile it here to demonstrate using JAVA_OPTS with groovyc.

The first demonstration involves setting JAVA_OPTS to -Dantlr.ast=groovy which Groovy in Action tells us is for "pretty printing." Once the environmental variable is properly set, it is simply a matter of running groovyc. This is shown off in the next screen snapshot which shows just the Groovy script source at first by itself, the setting of JAVA_OPTS, the executing of groovyc, and the generated output files (.class files and the findClassInJar.groovy.pretty.groovy file generated because of the flag passed via JAVA_OPTS (-Dantlr.ast=groovy)).


This can similarly be done with JAVA_OPTS set with -Dantlr.ast=html (generates HTML output) and -Dantlr.ast=mindmap (format used by FreeMind). Doing this for the other two properties is shown in the next screen snapshot.


Besides the normal .class files generated by groovyc, we now have three additional generated artifacts based on the three different antlr.ast settings: findClassInJar.groovy.pretty.groovy (pretty print), findClassInJar.groovy.html (HTML output), and findClassInJar.groovy.mm (Mindmap output). Each of these output formats are focused on next.

The pretty print output attempts to indent and beautify the code to enable a good representation of code's nesting structure. The contents of findClassInJar.groovy.pretty.groovy are shown next:

import java.util.zip.ZipFile
import java.util.zip.ZipException

rootDir = args?args[0]:"."
fileToFind = args && args.length > 1?args[1]:"class"
numMatchingItems = 0
def dir = new File(rootDir)
dir.eachFileRecurse 
{file -> 
if (file.isFile() && file.name.endsWith("jar")) {
    try {
        zip = new ZipFile(file)
        entries = zip.entries()
        entries.each 
        {entry -> 
        if (entry.name.contains(fileToFind)) {
            println file
                println " ${entry.name}"
                    numMatchingItems++
}
}
}












         catch (ZipException zipEx) {
            println "Unable to open file ${file.name}"
}
}
}

The HTML output might be more interesting in some cases. I show findClassInJar.groovy.html as rendered in the Chrome web browser in the next screen image.


This output is not too surprising, but the color syntax is nice and it might be helpful to make Groovy source code available via this mechanism.

The output generated in the form of findClassInJar.groovy.mm is not very useful when viewed directly (it's just some difficult-to-read XML), but is graphically more pleasing when that .mm file is rendered in FreeMind. This is shown in the next screen snapshot.


I still find it difficult to read, but it's darn pretty and likely will impress someone.

As I stated in my post Groovy Scripts Master Their Own Classpath with RootLoader, I often use shell scripts to kick off my Groovy scripts. These shell scripts can do certain things to set up my Groovy environment just how I like it, including specifying the classpath information for the Groovy script and setting JAVA_OPTS appropriately before running the Groovy script and unsetting it (cleaning it out) before terminating.


Conclusion

The JAVA_OPTS environment variable is a useful approach for specifying various JVM options that one wants Groovy scripts to have access to during runtime and for specifying various JVM options that one wants the Groovy compiler to use during compilation. This post has demonstrated use of JAVA_OPTS to specify heap size for a JVM executing Groovy code and to specify to groovyc to generate additional artifacts from Groovy source code.

Java and Oracle, One Year Later

It's been just over a year since Oracle closed the deal to purchase Sun. With that in mind, the forthcoming Oracle Technology Network (OTN) TechCast "Java and Oracle, One Year Later," is aptly named. It is scheduled for 10 am (Pacific Time) on Tuesday, February 15, 2011. Ajay Patel, VP of Product Development for Application Grid Products, presents a "special live conversation" regarding "changes that have come to Java and Oracle since the Sun acquisition."

Additional information on this TechCast can be found online, but I also received an e-mail message with additional details on this TechCast. The e-mail message adds more details on what will be discussed:
  • "Highlights, challenges and what we learned over the past year"
  • "The Future of Java and its importance to Oracle and the community"
  • "Oracle’s Application Grid product portfolio today"
The e-mail message states that Justin Kestelyn (Director of OTN) will also be involved and that "attendees" will be able to ask questions. There is encouragement to register even if the currently scheduled time does not work "so we can send you the replay information."