Showing posts with label java. Show all posts
Showing posts with label java. Show all posts

Thursday, April 5, 2012

Back to the roots

I've been going over some of my old stuff that I wrote back in the day in 1998 when I started to work professionally as a developer. Among other things (like using polish names for variables, classes and what have you and seeing absolutely no automated tests whatsoever) I've also spotted some nice stuff that I wanted to share with the class.

DDD was normal

Back in the day having a TTeacher (Delphi) class that knew about the schedule and could tell you which one is going on at a particular point in time was no big deal. Classes were not PODO, they actually knew how to do stuff. Just to give you another example here's something that struck me fairly recently:

Given a Company company and a Candidate candidate if the company decides to hire candidate then the output is an Employee employee. This could be written down more/less like this:
Employee employee = company.hire(candidate)
Now take a look at this and tell me how would you call this now a days? IT IS DDD at its purest! We have domain classes that can be retrieved from some source and operated upon.

Short methods were normal

Actually this isn't entirely true but it was pretty much the standard that a method contained calls to other methods that contained calls to other methods. I kind of felt the necessity too express things clearly or else the code would then be unreadable. So the whole "one-screen method" or "CCC < 5" was kind of natural even though nobody told me to do so. It just felt right.

Coding standard

This has surprised me most: All (and I mean it when I say "all") of the code has one and the same coding convention. There's no deviation whatsoever when there is no special case that needed separate consideration of formatting rules. And above all: it was based on VCL's code. Maybe not 100% equal but very, very close. Now that is some code you read like an open book just a after minutes of getting used to the coding style.

I, J and K were iteration variables - and nothing else!

Back then there was a number of variable names that were reserved for a certain task. "I, J, K" were always and without exception the iteration variables. There was no itinerary "i" or class "K". Similarly "S" was always a temporary string variable. The code was so damn short even though there were no closures to express things better!

What has changed?

Well, what has really changed after the year 2000? There were 3 major factors that influenced me to write worse code:

  • I stopped writing code for myself
  • The schedule became a lot tighter
  • The complexity sky-rocketed when I started writing calculation-intensive apps

With that in the picture when I look at the code I wrote after 2001 I feel like the IQ of the author just dropped 30-40 points!

The Corporate times

One very much disastrous time for me was the time when I started working for an international corporation. And I mean it in every single way one can possibly imagine. That was the place where I learned that even though the application is mission critical (people's life depends on it!!!) it is not really important that the quality of the code is kept at a reasonable level. It was really enough that the application worked around 60%-70% of the time! AAAAARGH!!! I remember fighting the original team members to the death trying to teach'em about quality of the code. That was the time I worked for the first time with "legacy code".

Java - the ultimate readability killer

As much as I hate Java the language for its verbosity and lack of advanced features like properties I'm inclined to say that the worse thing about Java are Hibernate and POJO-style programming model. Why?

Let's summarize what a POJO is, shall we? A POJO (plain old java object) is just a class. This simple and quite good idea turned into a disaster with Hibernate where most of the objects started to be those gigantic pile of annotation crap but besides that didn't contain anything else. That's how I came to learn POJOs as a programming style: dump, idiotic and trivial classes. So it is not a POJO anymore - you might say. And you'd be right! That'd be a dumb Java Object (DJO) but unfortunately when you see code that has to do with EntityManager, pure Hibernate or some other ORM (which is very likely) this is what you are going to experience..

Back to the roots

Now that I am old enough to look back and see the mistakes I made I've decided to find a way to get back to the programming style where a "Company" has the ability to "hire" a "Candidate" which would spit out an "Employee" but at the same time to keep things as separated as they should be for the sole reason of testability.

Spring sucks - Grails to the rescue

It should come as no surprise that my first attempt to mimic a rich domain object was undertaken in Spring. I admit I'm no spring expert and I still believe it is a vastly bloated library but I do get the idea behind it (unlike myself 3 years ago). But stuff is very much complicated with pure Spring. And one thing in particular - dependency injection in domain classes.

When I say that Spring sucks it really means that "Spring sucks by comparison to Grails". It is really great that spring does all the wrapping and all that but making domain classes automatically injectable borders on the infinity...

The whole point to this exercise is to have an object model that is usable without GUI and still makes a whole lot of sense.

Candidate.groovy:
class Candidate {
    String firstName
    String lastName
}
Company.groovy:
class Company {
    String name

    def hiringService

    Employee hire(Candidate candidate) {
        return hiringService.hire(candidate)
    }
}
Employee.groovy:
class Employee {
    String firstName
    String lastName
}
Now how about this:
Employee employee = company.hire(candidate)
Isn't that nice? And it is so damn readable!

The best part of all this is that in Grails domain classes are by default eligible for dependency injection which means that the hiringService is injected automatically. And I really mean AUTOMATICALLY! This means that when you do "new Company(name: "Test")" the "hiringService is automatically injected!!! This is the best thing ever!!!

I strongly recommend you try to look at your application from within the code and see if you can read it as you'd read plain text. If not there's something wrong with either your eyes or the code before you. If I was a betting man I'd go with the latter one :)

Write clean code!

Sunday, October 16, 2011

Creating standalone applications with Java and Maven

The challenge

In this installment we're going to take a look at what does it take to create a standalone Java application that's a little bit more sophisticated than the famous Hello, World. Let's start with the simplest example:
package org.example;

public class Main {
    public static void main(String[] args) {
        System.out.println("Hello, world!");
    }
}
To compile and run this one we need to invoke the javac compiler, package it to some jar file (say example.jar), create a manifest file (or not..) and start the application passing on the proper classpath and class name that is the entry point to our application. This might look something like this:
java -cp . org.example.Main

The "proper" way

I know for a fact that Maven can be a pain in the ass if used by some inexperienced fellow that wanted it to do everything but didn't know how to ask for it. For example for tasks that Maven is good at like specifying dependencies using Ivy and Ant for it makes no sense, right? Well, you wish! I've seen those kind of nonsense a lot of time with pom.xml reaching out beyond the magic 100k boundary...

Instead of cranking up the heat I'd like to see people develop simple mojos solving one problem at a time and not resorting to ant or anything like it. But above all, for crying out loud, use what's already there to do the job!

Doing Spring in standalone Java application

If you can imagine how hard would it be to prepare a standalone Java application that uses external configuration, external libraries and resembles what users are already used to (the bin folder, the lib folder, maybe some conf or etc for the configuration files) you'll appreciate the fine job application assembler is going to do for you.

<plugin>
    <groupId>org.codehaus.mojo</groupId>
    <artifactId>appassembler-maven-plugin</artifactId>
    <version>1.1.1</version>
    <configuration>
        <copyConfigurationDirectory>true</copyConfigurationDirectory>
        <configurationDirectory>etc</configurationDirectory>
        <repositoryName>lib</repositoryName>
        <repositoryLayout>flat</repositoryLayout>
        <programs>
            <program>
                <mainClass>org.example.Main</mainClass>
                <name>example</name>
            </program>
        </programs>
    </configuration>
</plugin>
That's pretty much it! All you have to do now is to call maven to do your bidding.
mvn clean package appassembler:assemble
Please note I didn't change anything in the application itself. Well that's because it's not a post about how to instantiate Spring in a console application but rather how to package everything so that it works as expected. You can take a look at a fully working example on GitHub.

Have fun!

Friday, September 23, 2011

CORS filter for Java applications

Hi there, in today's installment we're going to allow Ajax calls from other domains to be answered and accepted by browsers.

The what

This thing (completely forgotten by many) is called Cross Origin Resource Sharing and works with standard Ajax requests your browser can send. You can read about it in depth on Wikipedia or on the http://enable-cors.org/ site.

The how

Let's get to the meat - shall we? On the http://enable-cors.org/ site there are many recipes for all kind of servers and they respective configuration but what if you'd like to enable CORS just for a part of your application? If you're lucky enough and you're coding your application in Java then there is a standard mechanism to do just that! It's called filters.
Here's the most simple way of implementing CORS response headers:
import java.io.*;
import javax.servlet.*;
import javax.servlet.http.*;

public class CORSFilter implements Filter {

	public CORSFilter() { }

	public void init(FilterConfig fConfig) throws ServletException { }

	public void destroy() {	}

	public void doFilter(
		ServletRequest request, ServletResponse response, 
		FilterChain chain) throws IOException, ServletException {

		((HttpServletResponse)response).addHeader(
			"Access-Control-Allow-Origin", "*"
		);
		chain.doFilter(request, response);
	}
}
As you can see here all we're doing is adding the Access-Control-Allow-Origin header so that the browser can accept the response sent by server.

You can use this filter as follows in your web.xml:
<web-app>
	<filter>
		<filter-name>CORSFilter</filter-name>
		<filter-class>CORSFilter</filter-class>
	</filter>
	<filter-mapping>
		<filter-name>CORSFilter</filter-name>
		<url-pattern>/api/*</url-pattern>
	</filter-mapping>
</web-app>

Have fun!

Thursday, May 26, 2011

String + String = Problems

This is just a quick note to everyone not knowing it.

If for whatever reason you do have in your code something that concatenates strings using the + (plus) operator and it's going on in any form of loop or other that means executing this part regularly you might want to rethink what you've become over the years.

Man I never thought I'll see this thing again but I did! One of the developers was (again) producing a CVS line using a + b + c + d + shit load of other stuff. I mean come on! There have been books written about it already! :)

So if you're a Java developer choose one of either String.format, StringBuilder or StringBuffer classes to do the concatenation for you. If you're a .NET use either String.Format or StringBuilder to do it efficiently.

If you're a lucky Groovy developer your string concatenation will not be efficient anyway so you're free to use string interpolation - you can't get any worse than that :) At least it's damn good readable!

Sure thing is that depending on which platform you use concatenating might be more efficient if you use (for example in C#) the String.Concat method. But overall if you're concatenating a large number of strings (say in a loop or so) use the builder things at your disposal - they're a safe bet.

Sunday, January 2, 2011

JavaEE 6 + Metro WebServices

Following the post about WebServices with Grails here's a short summary of my attempt to make Java's EE 6 WebServices work with .NET. It's quite a basic example but as history shows even the simplest examples might not work (as it is the case with Axis2).

Setup

So here's a definition of a Hello WebService:
package com.aplaline.integration.webservices;

import javax.jws.*;

@WebService(name="Hello", serviceName="HelloService")
public class HelloService {
@WebMethod
public String sayHello(@WebParam(name="name") String name) {
return "Hello " + name + "!";
}
}

As you can see there's no magic here. Let's see how NetBeans' configuration option look like for this guy:



Surprisingly enough there's mentioning of a .NET version! Let's see how this works. I'll be using VWD 2008 SP1 to test it:



Let's add a web reference to this web site:



Now let's create a blank Default.aspx page and add some code to call that web service:
Default.aspx:
[...]
<form id="form1" runat="server">
<div>
<table>
<tr>
<td><asp:Label ID="Label1" runat="server" Text="Enter name" /></td>
<td><asp:TextBox ID="input" runat="server" /></td>
</tr>
<tr>
<td align="right" colspan="2"><asp:Button ID="Button1" runat="server"
onclick="Button1_Click" Text="Click me" /></td>
</tr>
<tr>
<td colspan="2"><asp:Label ID="output" runat="server" /></td>
</tr>
</table>
</div>
</form>
[...]
Default.aspx.cs:
[...]
protected void Button1_Click(object sender, EventArgs e)
{
output.Text = new localhost.HelloService().sayHello(input.Text);
}
[...]

Results

As it turns out it works out of the box properly.



For the kicks of it let's try and consume the same web service from PHP 5.3:
<?php
$client = new SoapClient("http://localhost:8080/WebServices/HelloService?wsdl");
var_dump($client->sayHello(array("name" => "John")));
>
There's a little inconvenience when calling web services from PHP in that the parameters need to be passed as an array instead of simply specifying their value. In the long run it's kind of healthy because different webservice stacks tend to handle things differently and putting the proper context into the whole thing.



This is the first pleasant surprise since I've started to work on the web-service interoperability between .NET and Java. It looks like things are definitely going in the right direction :)

Here's the Java project for reference.
Here's the .NET website for reference.

Have fun!

Saturday, January 16, 2010

JavaEE 6 - first impression

Hi

I've had some delay checking out the latest stuff on JavaEE 6 but finally I've done some looking around and I must honestly say that it is really impressed!

Using maven I've created 4 projects: parent, EJB, WAR and an EAR to house the others. It was relatively easy so I'd say in a scale from 1 to 10 I'd give it an 6 (the same thing using NetBeans scores a complete 10). I've implemented a EJB bean (just a class with one annotation - @Stateless - so the score is 9 because Java is just too damn verbose) and a servlet that uses that bean (that has scored a 6 because of the web.xml part, but maybe there's something new I didn't read about yet to raise the score).

Overall it was very pleasing to see the EJB part without XML configuration whatsoever :)

If you want you can check it out here.


Have fun!

Monday, December 7, 2009

Code coverage and Enum types

Hi,

I've been trying really hard to achieve 100% code coverage on one of the projects I'm working on right now. Pretty much all my business code showed the desired code coverage right up to the point where I introduced enumeration.

First let me explain why I wanted to get to the 100% in the first place.

Whenever I'm writing code that should be covered by unit tests (which is pretty much always nowadays) I'd like to be reminded (by either the code coverage results in CI or by the IDE) that some of the edge cases have not been tested yet. I know this might sound bad in the first place because I should only write as much code as required to satisfy the test I wrote but still - there are cases where the business code I produced does a little bit more than what's in the test. So it's a good idea to keep the 100% test coverage at all times so that once it drops below this magic number I'll notice immediately that something has been skipped.

Back to enumerations.

Those guys contain synthetic methods generated by the compiler (like valueOf and values) that do exist in the byte code but have no corresponding lines in the code itself. This means that there's more that meets the eye from the code's perspective but the code coverage tools I use (Cobertura and EclEmma) know only about byte code and they couldn't care less if the method they are testing came from the code itself or if it was dynamically generated by the compiler.

To that end, whenever I use an Enum the overall coverage drops like stone which simply looks awful.



But there's hope! One line of stupid test and all is green again.

MyEnum.valueOf(MyEnum.VALUE.toString());








I admit that the actual value of this test is minimum but the real reason to do that is to allow yourself the luxury to always react on the drop of coverage below 100% instead of manually checking every time if what's missing is really something we don't care about.

I hope this helps.

Wednesday, November 18, 2009

Java and Closures - own goal

Today in the morning there was an announcement made that closures (a feature long awaited in Java) will make it to version 7. Here you'll find some examples of how it will actually look like.

But...

To have an understanding of what closures really are useful for one must follow an example. Here's something written in C# for sorting a list of strings:

var list = new List<string>() {...content go here...};
list.Sort({ (s1, s2) => s1.Length - s2.Length });

And here's the equivalent in Java:

List list = ...
Collections.sort(list, #(String str1, String str2) {
return str1.length() - str2.length();
});

One can clearly see the intent of what the closure (a function being passed as parameters) looks like in both languages with the clear winner in succinctness being C# (or pretty much any other modern language out there). I know that java tends to be verbose on all possible counts but having a different approach for commonly understandable constructs is a bad thing all along.

One other thing that you can clearly see in the example above is the lack of type inference feature which makes the syntax even more verbose.

So when I said "own goal" in the title what I really meant is that the primary function, which is succinctness and clarity has been lost in transition.

Unfortunately we're facing yet another messed up implementation of a perfectly good idea (like generics with type erasure) in one of the most popular languages in the industry.
With this kind of mind set the end is near!

C ya!

Monday, September 28, 2009

Java 7 - a dissapointment

I've just been looking into the "features" available in J7 and I must say I'm mostly disappointed. Closures are out, properties are not yet implemented... I guess the code base must be to big to do any relevant changes to the language. Maybe it's time someone will admit that the language is going down and that there's time for Java++?