KakimotOnline

March 28, 2009

Visitor Pattern and the Open-Closed Principle

Filed under: programming, software design — Tags: , , — nandokakimoto @ 3:55 pm

A few weeks ago, I described here the Open-Closed Principle, which says that software entities should be open for extension, but closed for modification. Now, imagine you are facing with the following design problem:

You need to add a new functionality to a hierarchy of classes, but the act of adding it will be painful or damaging to your design.

I’ll use here the example of Robert C. Martin’s book: suppose you have a hierarchy of Modem objects. The base class has the generic methods common to all modems, and the derivatives represent the drivers for many different modem manufactures and types. Suppose also that you have a requirement to add a new method, named configureForUnix, to the hierarchy. This method will configure the modem to work with the UNIX operating system, corresponding to a different implementation in each modem derivative.

The real problem is not adding the new configureForUnix method, but what about the others operating systems? Must we really add a new method to the Modem hierarchy for every new operating system? Adding methods to the hierarchy of classes obviously violates the OCP because we’ll never be able to close the Modem interface.

The VISITOR pattern helps solving this kind of problems. As it definition says: VISITOR lets you define a new operation without changing the classes of the elements on which it operates. To do that, VISITOR use a technique called dual dispatch, which evolves two polymorphic dispatches.

The figure below shows the UML diagram create by VS2008.

uml

Now, let’s create the code necessary to implement the VISITOR pattern in the Modem problem.

Modem.cs

modem

ModemVisitor.cs

modemvisitor1

HayesModem.cs

hayes

ZoomModem.cs

zoom

ErnieModem.cs

earnie

UnixModemConfigurator.cs

unixmodem1

And here is the test code.

TestModemVisitor.cs

testemodem1

Having built this structure, new operation system configuration can be added just by creating new derivatives of ModemVisitor without changing the Modem hierarchy. Another pattern that accomplishes this is the DECORATOR pattern, but this is a talk for other post.

See you,


Fernando

March 15, 2009

Creating a J2ME Web Service Client

Filed under: j2me, java, mobile, programming, web service — Tags: , , — nandokakimoto @ 6:13 pm

This last week I was concentrated in developing a J2ME application that communicates with a Web Service to gather some information about route planning. Basically, the mobile app ask for a route, given an origin and a destination waypoints. Although this kind of work looks very easy, I got some problems to accomplish it. Due to that, I will share here my experiences to save you some time and if you have a different solution for creating J2ME web service clients, please let me know.

First of all, you will need the following softwares:

  • NetBeans IDE: instead of my fanatism for Eclipse IDE, I used NetBeans due to its facilities in creating web services.
  • Sun Java Wireless Toolkit: java toolkit for creating mobile applications.
  • Apache Tomcat: my target Web Server. Remember to download the .zip version.

The first step is creating the Web Service. So, inside NetBeans IDE, I will configure my tomcat installation under Tools->Servers menu option. (I’m using the pt_BR version of netbeans, so the menus may be a little different). Next, I choose Add Server and type the tomcat’s path location in my local machine. (Neatbeans comes with a native Web Server called GlassFish. If you are not aware with web server now, use this configuration as default).

Later, I have to create my web application project. So, under File->New Project menu, I choose Java Web category and Web Application project type. Click on “next” until your configuration has finished. Now, it’s time to create you source. I will show here a similar implementation of my route server.

Here I show the Waypoint class.


package entities;

public class Waypoint {

    private double lat;

    private double lng;

    public Waypoint(double lat, double lng) {
        this.lat = lat;
        this.lng = lng;
    }

    public Waypoint() {
    }

    public double getLat() {
        return lat;
    }

    public void setLat(double lat) {
        this.lat = lat;
    }

    public double getLng() {
        return lng;
    }

    public void setLng(double lng) {
        this.lng = lng;
    }

}

Here I show the Route class.


package entities;

public class Route {

    private Waypoint[]  waypoints;

    public Route(Waypoint[] waypoints) {
        this.waypoints = waypoints;
    }

    public Route() {
    }

    public Waypoint[] getWaypoints() {
        return waypoints;
    }

    public void setWaypoints(Waypoint[] waypoints) {
        this.waypoints = waypoints;
    }

}

Notice that I’m using complex object and arrays, which are in the most cases the reason of a lot of problems in deploying Web Services.

Next, I create my Web Service. To do that, right-click on the package folder and choose New->WebService. Here I show the implementation of my Web Service, which just return a route created by the given latitudes and longitudes.


package webservice;

import entities.Route;
import entities.Waypoint;
import javax.jws.WebMethod;
import javax.jws.WebParam;
import javax.jws.WebService;

/**
 *
 * @author Fernando Kakimoto
 */
@WebService()
public class RouteService {

    /**
     * Operação de serviço web
     */
    @WebMethod(operationName = "getRoute")
    public Route getRoute(@WebParam(name = "oLat", partName="oLatPart") double oLat,
            @WebParam(name = "oLng", partName="oLngPart") double oLng,
            @WebParam(name = "dLat", partName="dLatPart") double dLat,
            @WebParam(name = "dLng", partName="dLngPart") double dLng) {

        Waypoint w1 = new Waypoint(oLat, oLng);
        Waypoint w2 = new Waypoint(dLat, dLng);
        Waypoint[] waypoints = new Waypoint[]{w1, w2};

        return new Route(waypoints);
    }
}

After project compilation, the project tree will be similar than the picture below:

project

The Web Service is done. It’s time to create our J2ME client. For that, there are some options. One option is using the netbeans native support for that. After created a J2ME project, inside the New->J2ME Client for Web Applications menu, you are able to select a WSDL file as source and the IDE creates the J2ME client code for you. However, I tried this approach and the generated code came with errors. So, I used the second option: Sun Java Wireless Toolkit.

The WTK offers some utilites under File->Utilities menu. One of them is the Stub Generator, which generates J2ME client code for your WSDL service. So, run your service inside NetBeans or create its respective WSDL file. Next, in the stub generator, type the file path or URL, the code destination and the CLDC version. Here is how my Stub Generator looks like.

stubgenerator

After the code generation, here is the result of my WebClient J2ME project.

projectj2me

To finish, all you have to do is instantiate RouteService_Stub class and invoke getRoute() method. To make things simple, I used just one class which corresponds to the midlet. Here is the midlet code.


package main;

import client.Route;
import client.RouteService;
import client.RouteService_Stub;
import client.Waypoint;
import java.rmi.RemoteException;
import javax.microedition.lcdui.Command;
import javax.microedition.lcdui.CommandListener;
import javax.microedition.lcdui.Display;
import javax.microedition.lcdui.Displayable;
import javax.microedition.lcdui.Form;
import javax.microedition.midlet.*;

/**
 * @author Fernando Kakimoto
 */
public class MainMidlet extends MIDlet implements CommandListener {
    private Command exitCommand = new Command("Exit", Command.EXIT, 1);
    private Form form = new Form("J2ME Web Client");

    public void startApp() {
        try {
            RouteService service = new RouteService_Stub();
            Route r = service.getRoute(1.5, 2.5, 1.8, 2.8);

            Waypoint origin = r.getWaypoints()[0];
            Waypoint detination = r.getWaypoints()[1];

            form.append("origin:" + origin.getLat() + "," + origin.getLng());
            form.append("\n");
            form.append("destination:" + detination.getLat() + "," + detination.getLng());

            form.addCommand(exitCommand);
            form.setCommandListener(this);
            Display.getDisplay(this).setCurrent(form);

        } catch (RemoteException ex) {
            ex.printStackTrace();
        }
    }

    public void pauseApp() {
    }

    public void destroyApp(boolean unconditional) {
    }

    public void commandAction(Command c, Displayable d) {
        if(c == exitCommand){
            destroyApp(false);
        }
    }
}

That’s it. Simple and working.
The result you can see running the midlet sample.

phone

See you,


Fernando

March 8, 2009

The Principles of Object-Oriented Design

Filed under: programming, software design — Tags: , , — nandokakimoto @ 3:33 pm

At this moment, a lot of source code are been writing by thousands and thousands of programmers all around the world. Most of them uses an object-oriented language, but probably just a few have knowledge of the ODD, which I consider crucial for a reusable and extensible project.

What are The Principles of Object-Oriented Design

In March of 1995 UncleBob wrote an article that was the first glimmer of a set of principles for OOD. These principles expose the dependency management aspects of OOD. When dependencies are well managed, the code remains flexible, robust, and reusable. So dependency management, and therefore these principles, are at the foudation of the -ilities that software developers desire.

The first principles are about class design, which are:

  • The Single Responsability Principle (SRP): a class should have one, and only one, reason to change.
  • The Open-Closed Principle (OCP): software entities should be open for extension, but closed for modification.
  • The Liskov Substitution Principle (LSP): subtypes must be substitutable for their base types.
  • The Dependency-Inversion Principle (DIP): depend on abstractions, not on concretions.
  • The Interface-Segregation Principle (ISP): make fine grained interfaces that are client specific.

The Single Responsability Principle

In the context of the SRP, responsability is defined as a reason to change. Therefore, when the requirements change, that change will reflect in all classes that assume that responsability. If a class assumes more than one responsability,  then there will be more than one reason for it to change. In addition, this responsabilities becomes coupled and software is all about low coupling and high cohesion.

A good design is to separate two responsabilities in two completely different classes.

The Open-Closed Principle

This principle is about Rigidity, which is the tendency for a software to be difficult to change, even in simple ways. A design is rigid if a single change causes a cascade of subsequent changes in dependent modules. The more modules that must be changed, the more rigid the design.

The OCP advises us to refactor the system so that further changes will not cause more modifications. If OCP is well applied, then changes are achieved by adding new code, not by changing old code that already exists.

Modules that conform to the Open-Closed Principle have two primary attributes:

  • Open for extension: this means that the behavior of the module can be extended. As the requirements of the application change, we are able to extend the module with new behaviors that satisfy those changes.
  • Closed for modifications: extending the behavior of a module does not result in changes to the source or binary code of the module. The binary exacutable version of the module remais untouched.

How to be conform with this principle? Abstraction. This topic is covered by ICP.

The Liskov Substitution Principle

The LSP is one of the prime enablers of the OCP. It is the substitutability of subtypes that allows a module, expressed in terms of a base type, to be extensible without modification.

This principle is about inherintance and polymorphism. It exposes that base and concrete classes must be substitutable in all aspects and behaviors. Let’s take the Square and Rectangle example. In math, a Square is a Rectangle and this is the reason why many programmer design a Square as a derivate of a Rectangle. However, this is a really poor design. Look at the code below, assuming that a Square class extends a Rectangle class.


void f (Rectangle r) {
     r.setWidth(5);
     r.setHeight(4);
     assert(r.getArea() == 20);
}

The f functions is able to accept Rectangles and Squares object. With that in mind, the first problem is a Square does not have, in its concept, the attributes width and height. But, this should be acceptable. The second problem is  the need of overriding the setWidth and setHeight methods of Square object to maintains the object integrity. The final, and the real problem is that this function works just for Rectangle and not for Square. Since, for these function, Square is not substitutable for Rectangle, which violates the LSP.

The LSP makes it clear that in ODD, the IS-A relationship pertains to behavior that can be reasonably assumed and that clients depend on.

The Dependency-Inversion Principle

  1. High-level modules should not depend on low-level modules. Both should depend on abstractions.
  2. Abstractions should not depend on details. Details should depend on abstractions.

More traditional software developers methods, such as Structured Analysis and Design, tend to create software structures in which high-level modules depend on low-level modules, and in which policy depends on detail. The dependency structure of a well-designed, object-oriented program is inverted with respect to the dependency structure that normally result from traditional procedural methods.

However, considering the implications of a high-level module that depend on a low-level module you will see that changes to the lower level modules can have direct effects on the higher level modules and can force them to change in turn. This is not a good idea at all.

The modules that contain high-level business rules should take precedence over, and be independent of, the modules that contain the implementation details. High-level modules simply should not depend on low-level modules in any way. In contrast, they should depend on abstractions. In that way, you are able to change concrete implementations with no changes to its clients.

The Interface-Segregation Principle

This principle deals with the disavantages of fat interfaces. Classes that have fat interfaces are classes whose interface are not cohesive. In other words, the interfaces of the class can be broken up into groups of methods, each one serving a different set of clients. So, some clients use one groups of member functions, and others clients use the other groups.

The ISP acknowledges that there are objects that require noncohesive interfaces. however, it suggests that clients should not know about them as a single class. Instead, client should know about abstract base classes that have cohesive interfaces.

Conclusion and References

This is just the beginning of Object-Oriented Design. Remeber to not apply those principles and patterns to a big, up-front design. Rather, they are applied from interation to interation in an attempt to keep the code ,and the design it embodies clean.

You can read more about OOD principles here or in the book Agile Software Development, Principles, Patterns and Practices, in which this post is based on.

See you


Fernando

Blog at WordPress.com.