Saturday, May 17, 2008

Introducing JugList.net

As part of a homeschool project and a way to try out their budding Groovy & Grails development skills, two of my sons, Zak and Ben, have been working on a website. Their creation is now up and running and you can see it at www.juglist.net

JugList.Net is a searchable directory of Java User Groups around the world.


You can search for a JUG (Java User Group) by name, city, state/province or country. If you still can't find a JUG in your area, there is a link to an article, by yours truly, that gives some tips on starting your own group.

Java User Groups are a valuable resource for honing your craft and building your career. They also provide a great way for experienced programmers to give a little back to the community. If you are not involved in a JUG yet, then check out juglist.net and find one near you.

Friday, May 16, 2008

Another way to use Groovy in the Enterprise

Another great way to incorporate Groovy into your enterprise Java projects is Groovy SQL. GSql makes JDBC access so easy and Groovy's seamless Java integration and dynamic nature provides for some interesting ways to take advantage of it.

In this example we'll build a utility class that will use convention to turn an SQL select statement into a List of data transfer objects.

Our goal here is to take an SQL statement and a Class, execute that statement and use the results to populate instances of the Class. We will assume the convention of camel case for object properties and underscores for database fields, so that a field called LAST_NAME would be mapped to a property called lastName. We will also assume that the select statement will only return fields that have a corresponding property in the Class.

So let's see what this might look like:

static Collection getData(String query, Class clazz, Connection con){
def field = ''
def result = []
def sql = new Sql(con)
sql.rows(query).each {row ->
def dto = clazz.newInstance()
row.keySet().each{
field = toCamelCase(it)
dto."${field}" = row."${it}"
}
result << dto
}
result
}


After defining a few variables, we create our groovy.sql.Sql object using the constructor that takes a Connection. This will allow us to use Connections provided by an application server such as WebLogic or WebSphere. We could easily change this method to take advantage of the other constructors.

Next we'll call the rows method of the Sql class, which will execute the SQL statement and return an ArrayList of GroovyRowResults. Now we'll iterate through this ArrayList and create a new instance of our DTO class for each row. GroovyRowResult implements the Map interface so we can loop through its keys with row.keySet().each. This will give us each of the fields in that row and we will turn them into property names with a call to the toCamelCase() method (which we'll look at shortly). Notice how we take advantage of GStrings to dynamically access properties of our DTO as well as keys of the row map. After we assign each of the fields in the row to properties of the DTO instance we add it to the result List. When the loop is done we just return the List. Obviously, more can be done to make this more robust and more flexible, but it's pretty amazing how easy it was to build a Groovy class that can replace tons of repetitive Java code.

Let's take a look at how we could use this class from a Java project:

...
Connection con = getConnectionFromPool();
String query = "SELECT FIRST_NAME, LAST_NAME, EMAIL FROM MEMBER";
Collection members = GroovyData.getData(query, MemberDTO.class, con);
...

That's all there is to it.

Now let's take a quick look at the toCamelCase() method we mentioned above. This doesn't directly have anything to do with the purpose of this post, but I am hoping that someone might see this and offer a groovier way to do the same thing. Basically the goal is to take a database field name such as LAST_NAME and turn it into a camelCase string like lastName. Here's how I did it:

static String toCamelCase(String val){
def sb = new StringBuffer()
Boolean newWord = false
val.toLowerCase().each{
if (it == '_')
newWord = true
else{
if (newWord){
newWord = false
sb << it.toUpperCase()
}
else
sb << it
}
}
sb.toString()
}

I was sure there was a groovier way to do this and, sure enough, Andres Almiray came up with this awesome improvement:

static String toCamelCase(String val){
def result = val.split("_").collect { word ->
word[0].toUpperCase() + word[1..-1].toLowerCase()
}.join("")
result[0].toLowerCase() + result[1..-1]
}

Thanks Andres! And if that wasn't groovy enough, Ted Naleid came up with this cool mix of regular expressions and meta-programming. Good stuff Ted!

def camelCaseConverter(orig) {
orig.toLowerCase().replaceAll(/_(\w)?/) { wholeMatch, firstLetter ->
firstLetter?.toUpperCase() ?: ""
}
}

String.metaClass.toCamelCase = {->
camelCaseConverter(delegate)
}

Thursday, May 1, 2008

Groovy and Grails at JavaOne

It's less than a week until JavaOne 2008! It is going to be an exciting week packed full of brain stretching content. There will be technical sessions, birds of a feather sessions, panels, keynotes, etc. on just about everything having anything to do with Java. But most importantly, there will be a bunch of Groovy and Grails related sessions. Starting with Jeff Brown's Grails presentation at Community One on Monday, followed by the G2One / NoFluffJustStuff gala Monday evening at the W Hotel.

Then for the rest of the week a groovy search in the Content Catalog turned up the following list:

ID

Session Title

Speaker(s)

Date / Time

Room

TS-5771

The Duke and the Elephant: PHP Meets Java™ Technology--the Best of Both Worlds

Rob Nicholson, IBM

Tuesday
05/06/2008
10:50 AM -11:50 AM

Esplanade 301

TS-5764

Grails in Depth

Guillaume Laforge, G2One, Inc., Graeme Rocher, G2One Inc

Tuesday
05/06/2008
6:00 PM -7:00 PM

Esplanade 307-310

BOF-5613

Jersey: RESTful Web Services Made Easy

Jakub Podlesak, Sun Microsystems
Paul Sandoz, Sun Microsystems, Inc.


Tuesday
05/06/2008
8:30 PM -9:20 PM

Esplanade 307-310

PAN-5435

The Script Bowl: A Rapid-Fire Comparison of Scripting Languages

Guillaume Laforge, G2One, Inc., Charles Nutter, Sun Microsystems, Inc., Jorge Ortiz, Stanford, Raghavan Srinivas, Sun Microsystems, Inc.,
Frank Wierzbicki, Sun Microsystems


Wednesday
05/07/2008
9:30 AM -10:30 AM

Gateway 104

TS-5572


Groovy, the Red Pill: Metaprogramming--How to Blow the Mind of Developers on the Java™ Platform

Scott Davis, Davisworld Consulting, Inc.

Wednesday
05/07/2008
9:30 AM -10:30 AM

North Mtg-121/122/124/125

TS-5815

Going Mobile with JavaFX™ Script Technology, Groovy, and Google Android

Mike Mannion, Canoo Engineering AG

Wednesday
05/07/2008
10:50 AM -11:50 AM

Esplanade 301

TS-6050

Comparing JRuby and Groovy

Neal Ford, ThoughtWorks Inc.

Wednesday
05/07/2008
1:30 PM -2:30 PM

North Mtg-121/122/124/125

TS-5274

Groovy on a Cloud: Testing Java™ Platform, Enterprise Edition (Java EE Platform) Applications on Amazon EC2

Chris Richardson, Chris Richardson Consulting, Inc.

Wednesday
05/07/2008
4:10 PM -5:10 PM

Gateway 104

TS-6213

Boldly Go Where the Java™ Programming Language Has Never Gone Before

Geert Bevin, Terracotta

Wednesday
05/07/2008
4:10 PM -5:10 PM

North Mtg-121/122/124/125

BOF-5102

Cooking Your Own Groovy Builder: A Step Forward into Domain-Specific Languages

Andres Almiray, Oracle, Ixchel Ruiz, Clemente Camara y Asociados

Wednesday
05/07/2008
8:30 PM -9:20 PM

Gateway 104

BOF-5110

Extending Groovy’s Swing User Interface in Builder to Build Richer Applications

Danno Ferrin, Intelligent Software Solutions, Inc., James Williams, Spatial Networks

Wednesday
05/07/2008
8:30 PM -9:20 PM

Hall E 133

TS-5793

Groovy and Grails: Changing the Landscape of Java™ Platform, Enterprise Edition (Java EE Platform) Patterns

Guillaume Laforge, G2One, Inc., Graeme Rocher, G2One Inc

Thursday
05/08/2008
9:30 AM -10:30 AM

North Mtg-121/122/124/125

TS-5693

Writing Your Own JSR-Compliant, Domain-Specific Scripting Language

John Colosi, VeriSign, Inc.; David Smith, VeriSign Inc.

Thursday
05/08/2008
1:30 PM -2:30 PM

Esplanade 301

TS-6457


Choosing Your Java™ Technology-Based Web Framework: A Comparison

Richard Pack, Hyperic; Stacey Schneider, Hyperic

Thursday
05/08/2008
2:50 PM -3:50 PM

Esplanade 307-310

TS-6606

Patterns for Integrating Java™ and JavaScript™ Technology: Tales from the Front Lines

David Caldwell, David P. Caldwell, Inc.

Thursday
05/08/2008
2:50 PM -3:50 PM

North Mtg-121/122/124/125

BOF-5101

Boosting Your Testing Productivity with Groovy

Andres Almiray, Oracle;, James Williams, Spatial Networks

Thursday
05/08/2008
7:30 PM -8:20 PM

Gateway 102/103

TS-5098

Building Rich Applications with Groovy's SwingBuilder

Andres Almiray, Oracle;, Danno Ferrin, Intelligent Software Solutions, Inc.

Friday
05/09/2008
12:10 PM -1:10 PM

Esplanade 305

TS-6050

Comparing JRuby and Groovy

Neal Ford, ThoughtWorks Inc.

Friday
05/09/2008
1:30 PM -2:30 PM

Esplanade 303

TS-6039

Jython - Implementing Dynamic Language Features for the Java™ Platform Ecosystem

Jim Baker, Zyasoft, Tobias Ivarsson, Neo Technology

Friday
05/09/2008
2:50 PM -3:50 PM

Esplanade 305



Well, if you read this far and if you happen to be wandering around the Pavillion on Tuesday afternoon at 3:30, I will be giving a mini-talk on Java User Groups at the java.net Community Corner. (That way I can say that I gave a presentation at JavaOne).