Java 8: Don’t mistake concision for readability

O’Reilly has a quick little eBook called Introducing Java 8 that, in exchange for your name and email, you can download now on Java 8 right now. If you haven’t spent much time looking at Java 8’s new features, it’s surely worth a download because it’s a quick and easy read.

If you do however, I hope you’ll come back and consider my comments.

My immediate and most prominent reaction to the book is that it appears to pile on to the idea that more code always makes code less readable. Here’s the compare/contrast he offers. This is old school:

According to the author, the following Java 8 syntax is both more concise and more readable:

I obviously can’t disagree that it’s more concise because there were five lines in the first example; one the second. Therefore, concision.

Squishier is the author’s conclusion that it’s therefore more readable. My first reaction was quite contrary. In the first example, I knew exactly what was going on (maybe because I’m old school and understand the APIs well). In the second, I didn’t think it was readable for lots of reasons:

  1. What is the comparingDouble function? It’s oddly named and I don’t know what kind of comparison it does. And where did it come from? Static import? If so, that adds an off balance sheet line of code.
  2. Why is there only one “Invoice” amount getting passed into the function? What invoices?? Comparing what to what?? What comes first and what comes last???
  3. What does “reverse” do?

I totally understand what the author was trying to do with the example because I’ve tried to put these kinds of juxtapositions together too. But I think he’s just going too far to drop a single line of code and conclude that it’s both more concise and more readable without explaining why.

And if you’ll allow me to go further, it’s an issue I have with the fashion industry mentality that too many developers have. Think critically. Just because it’s concise doesn’t make it readable. If you think it is, explain why. Am I just irrational? Look no further than some of the grep statements that “those grep people” put together to know that concision does not automatically result in readability.

Does Docker = The End of Java Containers?

I’ve said this to almost every software person I know, including a guy who lives here in Pasadena and works for Docker as an evangelist: I’ve never seen anything hit so broad, fast, and high-profile as Docker has in the enterprise. Lots of people who are lots smarter than me said also said it months before me, locked it in as a critical opportunity, and aligned to it. My company, Red Hat, is a great example. In a lot of ways, we’re leading the charge — not just with Docker but with ancillary technologies like Kubernetes, and I’ve heard we’re in the top three upstream contributors to those projects.

While I get to see the from the inside the great stuff Red Hat does (and it’s indeed cool, I’m just writing personally and as a consultant who only really cares about results for my clients. And in that context — out in the field — I’ve noticed the impact Docker’s having on the developer ecosystem, especially the Java enterprise ecosystem. While we recently celebrated the twentieth anniversary of Java, as an industry we spent the majority of those twenty years trying to figure out how to build big, monolithic, mutlti-threaded, container-based enterprise systems. That is, we thought we needed Java EE containers or OSGi containers or whatever because we couldn’t possible run mainline Java code.

Or that’s what our industry and our bosses said, right?

Frankly, even though I admit I followed my marching orders without really challenging them, hasn’t it been a colossal hassle? As a developer, all I really want is some kind of framework that works, like Hibernate. I like it even better if it’s a standards-based framework like JPA because I could theoretically move to some better framework someday… maybe.  It’s great for speeding up development and saving me keystrokes.

But at runtime, I don’t want to have to code around specs and requirements and impositions just because of some mythical (or, worse, historical) scalability issues. When I was younger and when I challenged less, I just assumed that the big runtime containers, like the JavaEE containers, were solving a problem I didn’t really understand, so I slavishly followed the specs and debugged the seemingly endless issues and just believed that my life was the better for it.

But… now… in a Docker-like, microservices world, all that has turned on its head. An executive-level client at one of my recent clients, who’s tracking these same issues closely, asked me not so long ago, “Do I really need a container anymore?” I didn’t have an articulate, crisp answer for him. Since then, I’ve had people I’ve heard other people with vested interested in container-based architectures answer with a resounding, “YES!”

The developers in the room looked skeptical. I am too. I don’t think containers are dead. But I think their primacy is.

The simplest JMS request/reply I could come up with for ActiveMQ and JBoss A-MQ

In case you find yourself needing to set up some JMS request/reply code, I hope this helps (the whole example, including writing this post took less than one hour for me). It’s the simplest example I could come up with for ActiveMQ (and JBoss A-MQ, of course). By simple  I mean it focuses as much on the simple task as possible without adding any other frameworks, magic tricks, or whatever — just pure JMS API.

First, create the request message

Here’s the code:

You’ll notice that, compared to a simple send method, the request/reply is a little more complicated in the following ways: you need to create a temporary reply queue (goes in the JMSReplyTo header), a correlation ID (JMSCorrelationID), and then start listening for a reply message.

When you run this, you should see the following if you log into JBoss A-MQ and browse the messages (ActiveMQ lets you do something similar through its web interface too):

jms-request-reply-example

Notice the JMSCorrelationID and the JMSReplyTo headers are set.

Next, subscribe and reply

The code to respond to the message mirrors the sender’s code:

Assuming that the sender code is running, if you run the code above, you should then see this in your IDE or console:

jms-request-reply-example-2

The full code is available on Github. Good luck out there, and let me know how this demo goes for you.

The simplest OSGi / Karaf hello, world demo I could come up with

I don’t know about you, but I almost gave up looking for quick and lightweight examples on how to get started creating and deploying an OSGi bundle. Everything I found used out of date or opaque Maven plugins, proprietary techniques specific to a platform, magic tooling called “bnd,” and all kinds of other chaos. I repeatedly hear that precisely this chaos slows down OSGi adoption and related technologies like Camel. I hope this post speeds you up a little.

First, let’s write some Hello, World code

This is the easiest part. I just wanted a simple example that prints hello, world to the console when the bundle starts. Here’s the code I came up with:

You probably noticed you’re going to need the OSGi framework on your classpath. Here are the dependencies I used (but I haven’t researched whether both are strictly necessary or not):

Hand craft a MANIFEST.mf file – You. Can. Do. It.

This was the big hurdle for me. It seems that most of the authors of the examples I found had some kind of allergy to hand writing the file, so they rely on various tooling to write it and bundle it. I suppose in real life I might get used to the tooling, but it just gets in the way of me learning. So here’s my hand crafted file:

Bundle-SymbolicName and Bundle-Version lets you describe what the bundle will look like to a user in Karaf (or whatever OSGi container, I suppose). For example:

simple-osgi-example-1

Import-Package is critical. In fact, it’s a core part of the OSGi concept that you must explicitly declare the services you’re depending on. Remember how we imported the OSGi dependencies in the hello, world Java code? You might have thought that installing a bundle would implicitly include the framework, but you’d be wrong. You have to explicitly declare it.

Export-Package is a similar concept. You need to expose your services to other bundles. Finally, Bundle-Activator is the class you want to fire up on start (the hello, world code above).

Structuring your project

I put my manifest file under src/main/resources/META-INF:

osgi-example-2

The wrinkle here is that Maven will overwrite your META-INF file unless you override the default behavior with this:

Finally. Now let’s install and start the bundle

I ran this in Karaf, so here’s what I did. First, run mvn install to get the artifact into your local repository. Next, start up Karaf and run this command:

osgi-example-3

Take note of the bundle ID. Mine was 95 in this example, but it varies each time. Now let’s start it with this command:

And you should see something like this:

osgi-example-4

The full example is here: https://github.com/mrice/osgi-demo Good luck out there.

How to get the Apache Camel tooling features into your JBoss Developer Studio

This feature — as of this writing — isn’t immediately obvious, so in case you’re trying to figure out how to visually design, test, and run Apache Camel routes in your JBoss Developer Suite, here’s what I’ve got:

When JBDS starts, you get the JBoss Central welcome screen by default, right? There’s a tab at the bottom called “Software/Update.” Click it. Near the bottom right, you’ll see an option to “Enable Early Access.” Click that too.

I’m don’t know when it will get out of early access. If you’re from the future and you’re reading this, things may be different. For now, you should see this:

enable_jboss_fuse_tooling

Select the JBoss Fuse Development, like I did in the example above. Click that too. Now you’ll see this:

jboss_fuse_tooling_2

The most important to you is probably the Apache Camel Editor, so check it, click Next, and you should be on your way.

Did I join the ActiveMQ Developers list at a great time, or what

I joined the ActiveMQ Developers list to watch the sausage getting made. Maybe I just joined at a good time, or maybe it’s just always this entertaining…?

The background and the vote: Red Hat is donating HornetQ to the Apache Foundation. The ActiveMQ project management committee (“PMC”) needs to report to the board what they should name it and where they should house it. The community narrowly voted to rename it ActiveMQ Artemis instead of ActiveMQ Reactive (I thought reactive was a little confusing too).

The fight: a few of the developers suggested that HornetQ — I mean Artemis — should go to an incubation process first, but that turned out to not be the real issue. No, the real issue appears to be fears or paranoia concerns that the Fuse and Red Hat committers are controlling the code, the process, and effectively masterminding the ASF.

The way it looks is that Fuse/RH/(the Damarillo group), anyway you want to describe that faction is dead set on replacing the existing ActiveMQ with HornetQ (or whatever code name) in version 6 or 10. By keeping HornetQ under the ActiveMQ PMC influence its future will be heavily influenced by the already biased PMC and at the same time hide the lack of diversity in HornetQ. In the incubator, HornetQ will have the opportunity and freedom to grow in any direction and build a diverse community.

Then a response:

We’ve had lots folks from different companies agree with the direction that code contribution is going in. The fact that pin it on ‘Fuse/RH/(the Damarillo group)’ is very disingenuous and I think a poisonous position to take.

Then someone dropped words like evil, conspiracy, and even junta:

Which committer, specifically, could be brought into the PMC to try to counterbalance the alleged RH junta? I’m really discouraged by the insistence from a couple people that the only possible explanation of where we are now is an evil Winston/Fuse/RedHat conspiracy. I think it’s also just barely possible that after working all day people get tired. After providing unpaid all-waking-hours support for first jboss and then geronimo for many many years I sure did. This is not to say that there isn’t a strong need for more community involvement, but expecting the same people to do everything all the time is getting implausible.

Then getting HornetQ into the incubater became a matter of sacrificing oneself to protect Apache values:

Why not be open about it, advocate for it, work for it and build consensus and acceptance instead of putting everybody in front of a ‘take it or leave it’ choice. That’s what rubbed me the wrong way. That’s really not like the ASF I know. That’s why I made a conscious decision to be vocal about it and, in my mind, do my best to protect this community. This may cost me some personal relations, with people like you who are really extremely intelligent and
still do respect

Remember the Junta / Fuse / conspiracy stuff? Here’s one response from one of the alleged but as yet unindicted co-conspirators:

You are the second person to allege that I am acting with secret instructions and communications on this. I demand a pubic apology, immediately. I have done no such thing, all my communications with anyone about this issue have been on this list, and in reply to others raising similar issue on the pmc list. This is disgusting.

Who knew enterprise software could be so… dramatic.

UPDATE: the next morning, my IRC lit up with more conversation from some of the core ActiveMQ folks about yesterday’s discussions. Generally, they seem to think they discussions are good because they indicate people care passionately about ActiveMQ. And then this article appeared:

Ultimately, open source isn’t about code. It’s about community, and as Bert Hubert suggests, “community is the best predictor of the future of a project.” That community isn’t fostered by jerk project leads or corporate overlords pretending to be friendly foundations. It’s the heart of today’s biggest challenges in open source — as it was in the last decade.

Demo: JBoss A-MQ, Websockets/HTML5, and Gordon Gecko

Back in early 2013, Eric Schabell, a Red Hat JBoss evangelist, created a cool JBoss A-MQ demo based on HTML5 websockets. You can see the YouTube demo here and access the JBoss Github repo for the demo here.

I wanted to work through it myself; only, it didn’t work for me out of the box. I fixed it and submitted a pull request, but while we’re waiting for the JBoss folks to accept the PR (’cause you know they should!), you can use the changes on my fork. Plus, I’ll help you out if you hit issues (I’m a consultant, you know…). But let’s walk through the demo for fun and clarification.

Running the demo

The README in the demo repo has all the nitty gritty details you need, but you might want an overview first since it’s a little more involved than just firing up a web application.

  1. Download a recent copy of JBoss A-MQ 6.1 from the JBoss Developer site and copy it to the “installs” directory — even if you already have A-MQ installed.
  2. Run the init.sh script to build all the artifacts you need and to provision the A-MQ installation correctly.
  3. Start the “feeder” standalone client, which will start putting stock price (and news) messages on JMS topics.
  4. Install the Websocket OSGI features as well as the demonstration web app.

What it looks like when you stay on the demonstration’s happy path

You’ll start the Karaf command-line client (from target/{amq_version}/bin).

a-mq-karaf

After installing the websocket application, you’ll see installed near the end of the osgi:list:

a-mq-demo-webapp-installed

Next, you’ll start your feeder application from the support directory (support/start_feeder.sh). You should start seeing messages flowing into the A-MQ topic such as the following:

feeder-updates

Finally, you’ll load up a web browser and start seeing messages flowing through websockets to update web stock prices dynamically:

a-mq-demo-client

What the demonstration does under the hood

The demonstration shows really well, but you’re probably interested in what’s happening under the hood and how it may (or may not) apply to the work you actually do.

How the demonstration initialization script provisions the A-MQ server

First of all, you might bristle a little at the init script. Let’s talk about what it does because it’s not as black box or magical as it might appear.

  1. It unpacks the JBoss A-MQ installation you downloaded and puts it in the target directory.
  2. It copies over some configuration files. These files mostly just add security accounts so the feeder and client UI can interact.
  3. It runs Maven builds on the feeder and web UI clients so you can (a) run the feeder script and (b) install the web application and websocket features.

The Java code for the message producer and consumers

There are two Java applications that ship with the demo. The “feeder” application puts fake stock and news updates on two JMS topics: stockQueueTopic and newsTopic. The following is just a snippet from FeedThread on how the feeder applcation accesses A-MQ and the topics I just mentioned:

The Websocket-based client code uses the STOMP protocol through Jeff Mesnil’s stomp.js client code. One you login, it starts sending websocket frames to populate the screen I showed you above.

a-mq-demo-websocket-frames

Cool, huh? You might bump into issues out there, so let me know what we can do to improve it.

A simple message driven bean (MDB) in JBoss AS/EAP with Maven

I had a really hard time finding a really simple example to show, so hopefully this will help you.

How to Set Up Your Maven Project

Sometimes I swear that getting a Maven project is sometimes the hardest part of getting a Java EE project going. Once you’ve got it, it all snaps into place. Here’s a simple pom:

Create a Message Driven Bean (MDB)

Here’s a simple example:

Now Create a Client to Send Messages Into the Queue

This too is pretty straightforward. In my example, I just run it with a servlet.

Now Configure JBoss AS 7 / EAP 6

You’ll need to start AS/EAP in at least standalone-full mode because the simple standalone configuration — out of the box — does not start the HornetQ queueing system:

Finally add the queue to AS/EAP. You can use the JBoss CLI (jboss-cli.sh), with this command:

How to develop a custom module for JBoss EAP 6x / AS 7

Sometimes you want to be able to share a custom JBoss EAP module across a number of different WARs or EARs on your application server. I cam across this recently when a client had a big module that retrieved a lot of data from a legacy system. Since the data set was so big, it didn’t make sense to deploy the library with every application.

There are really just two steps to the process: build the custom module and then wire up your application to use it.

Step one: create a custom JBoss module

Developing the custom module

If you’re using JBoss AS7 or EAP 6x, you’re probably using Maven. So here’s a pretty minimal pom to get you started. The only real dependency you might want to exclude (but do you really?!?) is Google’s Guava.

Now, let’s do the test driven development thing and start with a test class in the src/test/java Maven directory. If you haven’t worked with this approach with Intellij IDEA, you’re missing out. The ergonomics really are nice.

And here’s the actual implementation class:

Now, let’s assemble the module. Remember how I included the Guava package? Well, to make this demo simple, let’s go ahead and rely on the maven-assembly-plugin that we included in the pom above like this.

First, run mvn clean package, and you’ll see two different artifacts created:

two-artifacts

Installing the custom JBoss module

Now let’s get the module installed. First, create a directory named {jboss_home}/modules/com/redhat/demo/main. The “main” is significant because it lets you configure multiple “slots” if you have different versions of the same module installed on the server. Then copy the JAR file with the dependencies over to that main directory.

Next, we’ll create a descriptor in that “main” directory called module.xml. Mine is ultra simple with the following:

Finally, let’s set up the module as a “global” module so it’s easily available to all the application on AS7/EAP 6 by adding the following to standalone.xml (or the equivalent in domain.xml):

Now start your JBoss AS7/EAP instance.

Step two: start using the module

I created a simple “hello, world” type servlet just to demo the module. Here’s the pom:

And here’s the simple servlet:

That’s it, now deploy it on your instance and you should see it running.