Given a need to work towards more scalable systems, and to increase concurrency, many developers working in Java wonder what’s on the other side of the fence.
Languages such as Erlang and Haskell bring the functional programming style to the fore, as they essentially force you to think and write functionally – they simply don’t support (well, at least not easily) doing things in a non-functional fashion very easily.
The mental grinding of gears, however, can be considerable for developers coming from the Java (or C/C++) worlds in many cases, who have become familiar with the Object-oriented paradigm. An excellent solution might be to consider the best of both worlds: Scala.
I had the opportunity this weekend to renew my acquaintance with Scala, and to work on blending it with the old mainstay, Java. Scala runs on the JVM, so as you might expect, it can be combined pretty readily with Java – more cleanly than before, given some new Maven and IDE plugins.
IDE Support for Scala**
My IDE of choice lately has been Netbeans, and sure enough, there’s a (beta) Scala plugin for Netbeans.
Installing this plugin gives me syntax-aware editing of Scala source, along with basic refactoring support. Here’s the obligatory “Hello, World” in Scala sitting happily in my Netbeans window, color-highlighted syntax and all:
In order to organize my code, tests, and generally make life easier, I’ve used Maven to first generate the project, then created the code above (and some more, as we’ll see in a minute). I started with the regular “mvn archetype:generate” command to build my source directories just as for a Java project, then added a bit of Maven magic to the generated POM to use the Maven Scala plugin. Here’s the full POM:
Lines 21-25 tell Maven where to find the actual Scala plugin
29-33 add the Scala libraries to our list of dependencies
Lines 44 thru 48 add the Scala plugin itself to our build lifecycle
Lines 58 thru 75 specify the lifecycle events we bind to for actually compiling first the Scala production code, then the tests.
When we open this POM with Netbeans, you’ll see we’ve got a folder defined for both our Scala sources and tests, and our regular folders for Java sources and tests:
Calling Scala code from Java code
Now that we’ve got our project defined to contain both Scala and Java, let’s put them to work together. We can call our Scala code directly from Java just as if the objects involved were Java, like so:
The only class we’ve got defined with the name HelloWorld is the Scala version – but it looks like Java as far as our Java classes are concerned. (There are some things to keep in mind when doing more advanced types between the two, but if you keep your interfaces straightforward these edge cases don’t arise very often).
Calling Java code from Scala code
The reverse is also true: we can make use of the entire library of existing Java code out there from Scala, even easier than in the reverse direction, as the more sophisticated type system of Scala handles anything Java can throw at it. Let’s look at a good example: Using JUnit4 (a Java library) to test both Scala and Java code.
Using JUnit4 to test Scala
The simple and expressive JUnit library has implementations in a number of other languages, but in the case of Scala and Java, the connection is so close we don’t really need a Scala version at all – we can use JUnit directly from a test written in Scala, as described below.
With the test written in Scala…
Here we see a Scala test, DogTest, running from within Netbeans (using Maven).
(Yes, the DogTest class is actually defined in a file called AppTest.scala – perfectly valid in Scala)
The results can be seen in the lower window (printing “Hello, World”).
As you can see, we’re using JUnit4, even with it’s Annotations, despite the fact the test is written in Scala.
With the test written in Java…
Now let’s go the other way: This is simply a matter of writing a regular Java Junit4 test, except instead of calling a Java class we’re actually calling our Scala class again.
In this example, you can see we’re using JUnit 4 in the usual way, but on line 20 and 25 we make reference directly to Scala classes, just as if they were regular Java classes. (The IDE shows them underlined due to a classpath issue, but they compile just fine in any case – the Netbeans Scala support is still Beta, after all).
As you can see, these two languages blend very smoothly in many respects, even more so than one of my other favorite combinations, Java and JRuby.
Although it is cool to see Scala and Java in a single project, I probably wouldn’t do it this way for production code. A cleaner approach might be to write a pure Scala module that is then a dependency of the Java project (or vice-versa), using Mavens ability to handle cross-project SNAPSHOT dependencies to break our work up into more manageable chunks.
We can then call Scala functionality from any Java application, even webapps, while still working with all of the exact same tools and procedures we’re used to for pure Java projects. Of course, we can also go the other way: write Scala web applications (perhaps with the excellent Lift framework) and call existing Java functionality, just as easily.
I predict Scala will be used in more and more Java (and other JVM-based language) projects where the advantages of functional programming and high concurency are necessary, while at the same time preserving the massive investment in Java many of us already have.
Long live the happy couple!