Posts Tagged ‘Object Oriented Programming’

Object Oriented Persistence & Repositories

Tuesday, June 8th, 2010

In this post, I will share my own understanding of Object Oriented Persistence and relate it to the Repository pattern, suggested by Eric Evans in Domain Driven Design.

In object oriented perspective, persistence can actually be considered as the extension of the life-cycle of an object. This view of persistence allows us to think that it is actually a minor part of the software, compared to the whole domain. Thus, a programmer’s main focus shouldn’t be the persistence. Although this ideal description of “what should happen” (or what should not happen) sounds neat, this is not what happens most of the time. The reason for that is Database Management Systems are complex entities; they have their own constraints, rules and protocols. If you would like to use a database management system, then you need to follow these rules and constraints.

This clearly is a problem, but there is another, even bigger problem as well. The bigger problem is, in order to follow these constraints, rules, protocols; it is tempting to put the main focus on the database technology & persistence and start doing data processing. Although it sounds bizarre if it is stated like this, this is a contemporary issue and one of the biggest problems in Software Engineering. And more interestingly, even people who claim to be Object Oriented Programmers do that. And I’m not talking about the inexperienced ones, there are people who have been doing this for a long time without knowing it.

In order to avoid this, one needs to know that Object Oriented Programming is not a data processing scheme and persistence is just a minor part of the domain. The word “Domain” is the key here and the solution of this problem lies within the principles of “Domain Driven Design”. (Eric Evans, 2004)

Repositories

Repositories are actually abstract entities that contain a collection of objects. As the programmer, you can put some objects into a repository and then retrieve them back, when they are needed. With this very simple definition of the repositories, they can easily be considered as a part of the domain.

Hence, the client needs to know if he asks for an object in the proper way, the repository will give it to him. Furthermore, the client can also send an object to the repository for further usage. In essence, this is all a client needs to know about a repository.

Looking through the repository’s perspective, the repository both needs to provide a good interface to the client and know how to communicate with the persistence layer.

Persistence Layer / Technology

The implementation details for the persistence layer should not be scattered into the domain layer. In other words, ideally, the client shouldn’t know whether you are using traditional SQL to communicate a relational database, an object database, an ORM Tool or just keeping the objects in a simple array. Independent of those details, the client should be able to communicate with the repository. All those details should be encapsulated within the Persistence Layer. The concrete repositories may need to know which technology you are using. In this sense, repository can be considered both part of the domain and persistence layers.

At this point, it would be better to stop talking about the concepts and do some practice with an example. Suppose that we have a Book class and it has the following class diagram :

Figure 1 : Book Class

Figure 1 : Book Class

Now, suppose we want this entity to become persistent. Then we can create an associated repository, BookRepository class. We need to determine the interface for this class wisely so that we can easily store, retrieve and update books.

BookRepository Interface

Figure 2 : BookRepository Interface

As you see, regardless of the technology behind it, BookRepository interface enables us to store books and retrieve them by various settings.

Although it seems neat, this strategy becomes problematic at some point. In fact, you might have already noticed it easily. We have a simple Book class and we needed 4 retrieval methods. What if Book class was much more complex? This strategy will clearly become problematic because BookRepository might get too crowded.

One solution to this problem is using some “façades” to simplify the BookRepository interface. (please refer to Design Patterns by Gamma et al) However, a more advanced solution would be to use the Specification design pattern. (DDD, Evans) This is not going to be described in this article; it is subject to another article. Hopefully, I will publish an article about specification pattern, soon.

Concrete Repositories

In the example above, we have just given a simple interface for the BookRepository. However, we didn’t describe how a concrete repository looks like. First of all, we need to decide which technology to use. For the sake of simplicity, I choose to use a simple list implementation. In fact, this will not make sense at all because the objects will not be kept in disk. A more advanced and sensible choice would be to use Hibernate. Anyways, the class diagram for BookRepositoryListImpl looks like this :

Figure 3: BookRepositoryListImpl class

Figure 3: BookRepositoryListImpl class

Now, BookRepositoryListImpl can be used as a concrete instance of BookRepository.

List Implementation and Unit Testing

In the above example, I chose list implementation for the sake of simplicity. However, there are also some other places in which the list implementation may come handy, interestingly. For instance, list implementation might become useful if you would like to test a component that uses a repository. Now, assume that we have a class, called BookReservationManager, that has the following definition:

 Figure 4 : BookReservationManager class

Figure 4 : BookReservationManager class

In order to make it more concrete, the implementation of the reserve method is given below:

public Book reserve(String ISBN)
{
   Book b = bookRepository.getByISBN(ISBN);
   if(b.reserve())
      return b;
   return null;
}

If reserve() needs to be unit-tested (and it must be done in isolation, of course) then a mock object of type BookRepository should be used. In fact, the list implementation of the BookRepository can act as a mock object, here. Although BookRepositoryListImpl has nothing to do with the actual implementation, it can be used for unit testing, here. This is beautiful; and the reason for that is if you test reserve() with an actual BookRepository (which uses an actual DBMS) rather than using the list or mock implementation, the failure of one of the database transactions may cause your test to fail.

Summary

To conclude, Repositories are good object oriented and domain-driven ways of implementing persistence. They are part of the domain and this enables us to concentrate on the domain rather than the technology. For each object that needs to be persistent and accessed globally, a corresponding Repository interface should be created. List implementation of a repository allows us to perform unit tests easily on complex components that make use of repositories.

Java Implementation

In this section you will find actual implementation of the example that has been focused on.

Book.java

package com.alicevik.blog.repositories.domain;
  public class Book
  {
 
	private String ISBN;
	private String title;
	private String author;
	private int year;
	private boolean isReserved;
 
	public Book(String ISBN, String title,
        String author, int year)
	{
		this.ISBN = ISBN;
		this.title = title;
		this.author = author;
		this.year = year;
		this.isReserved = false;
	}
 
	public String getISBN() {
		return ISBN;
	}
 
	public String getTitle() {
		return title;
	}
 
	public String getAuthor() {
		return author;
	}
 
	public int getYear() {
		return year;
	}
 
	public boolean reserve()
	{
		if(!isReserved)
		{
			isReserved = true;
			return true;
		}
 
		return false;
	}
 
	public void read()
	{
		// left blank intentionally.
                // irrelevant for this example.
	}
  }

BookRepository.java

package com.alicevik.blog.repositories.domain;
 
public interface BookRepository {
 
	void store(Book b);
	Book getByISBN(String ISBN);
	Book[] getByTitle(String title);
	Book[] getByAuthor(String author);
	Book[] getBooksBetwYears(int year1, int year2);
}

BookRepositoryListImpl.java

package com.alicevik.blog.repositories.domain;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
 
/* List implementation of the BookRepository interface.
 * Author : Ali Çevik
 * Only the methods of interest are implemented.
 * 08.06.2010
 */
 
public class BookRepositoryListImpl implements BookRepository
{
 
	private List list;
 
	public BookRepositoryListImpl()
	{
		list = new ArrayList();
	}
 
	@Override
	public Book[] getBooksBetwYears(int year1, int year2)
	{
		return null;
	}
 
	@Override
	public Book[] getByAuthor(String author)
	{
		return null;
	}
 
	// iterates through the list to find the match
	@Override
	public Book getByISBN(String ISBN)
	{
		Book book = null;
		Iterator it = list.iterator();
		while(it.hasNext())
		{
			Book b = it.next();
			if(b.getISBN() == ISBN)
				book = b;
		}
		return book;
	}
 
	@Override
	public Book[] getByTitle(String title)
	{
		return null;
	}
 
	@Override
	public void store(Book b)
	{
		list.add(b);
	}
 
}

BookReservationManager.java

package com.alicevik.blog.repositories.domain;
 
public class BookReservationManager
{
	private BookRepository bookRepository;
 
	public BookReservationManager(BookRepository repository)
	{
		bookRepository = repository;
	}
 
	public Book reserve(String ISBN)
	{
		Book b = bookRepository.getByISBN(ISBN);
 
		if(b.reserve())
			return b;
 
		return null;
	}
 
}

BookReservationManagerTest.java

package com.alicevik.blog.repositories.test;
 
import junit.framework.TestCase;
 
import com.alicevik.blog.repositories.domain.Book;
import com.alicevik.blog.repositories.domain.BookRepository;
import com.alicevik.blog.repositories.domain.BookRepositoryListImpl;
import com.alicevik.blog.repositories.domain.BookReservationManager;
 
public class BookReservationManagerTest extends TestCase {
 
	private BookRepository repository;
	public void setUp()
	{
		repository = new BookRepositoryListImpl();
		repository.store(new Book("1111-1111-1111", "Faust", "Goethe", 1832));
	}
 
	public void testReserve()
	{
		BookReservationManager man = new BookReservationManager(repository);
		assertNotNull(man.reserve("1111-1111-1111"));
		assertNull(man.reserve("1111-1111-1111"));
	}
 
}

A good resource for Spring AOP

Monday, April 27th, 2009

A good resource for spring and AOP, “Spring 2.5 Aspect Oriented Programming“; has been published by Packt Publishing. I strongly suggest reading if you are a little bit familiar with Spring and interested in AOP.

Before you start reading my review about it, you can find more information about the book and how to get it, at this page.

Although Spring Framework has been seen as just an IoC container by some of the programmers, most of the programmers nowadays start to realize that this kind of view would be an over simplification of its capabilities. It has many features and one of them is using it for AOP. In book Spring 2.5 Aspect Oriented Programming written by Massilimiano Dessi and published by Packt Publishing, the use of Spring for AOP is well explained.

First of all, the need for AOP is explained in an analytical way, allowing readers to make comparison between a scenario with and without help of AOP. After this persuasive attitude, the introduction of AOP specific concepts (such as “pointcut”, “joinpoint”, “advice”) and introduction to some more Spring-AOP specific concepts (such as advisor) are provided. A language that is going to be used throughout the book is built in the beginning; and this enables readers to gain a better insight about the AOP paradigm while reading the book.

As well as describing how to realize AOP using Spring, chapters 2-4 also explain what is happening behind the scene. In this sense, this part of the book might be used as a “Cookbook”. Despite existence of diverse options while using Spring; some advice has been given about when to use which, depending on the context. While illustrating the use of AOP by giving some simple examples; the book also explains what kind of dilemmas might a programmer get into and make suggestions about which way would be more convenient.

After giving those details, the book comes back to a more conceptual point about AOP. From the beginning, a concept such as “croscutting concerns” has been mentioned as the most fundamental reason why AOP has been evolved. As object oriented programmers, we have experience about a lot of scenarios and we even have design patterns that help us a lot. However, when we decide to use AOP in our applications; the need to have some kind of decision mechanism that regards when to use it confronts us; since it is a new paradigm compared to OOP. At first glance, this may seem like an easy task; but not at all! While programmers are still arguing about the patterns and anti-patterns about AOP, there are some scenarios that is perfectly legal to use AOP. Some of them are concurrency, caching, security / role assignment. Use of AOP in those scenarios is illustrated in the book in a dialectic manner. First, implementation without using AOP and then with the use of AOP is provided; which enables readers to make comparison between them. This chapter illustrates very typical scenarios in which the use of AOP is approved and perfectly legal.

Domain Driven Design is very popular nowadays and the book connects AOP with it in chapters 6 and 7. First of all; without causing reader to get drown details, the relevant concepts are identified. Before applying AOP, a good Object-Oriented design has been given. Domain layer is separated from application and infastructure layers. Some of the croscutting concerns are identified and the reader is informed about how they are going to be handled. Moreover, the domain objects are designed in such a way that they would be able to take advantage of inversion of control (IoC). Simply, “Model” is created on this chapter, which is going to be associated with a “View” and a “Controller” in the subsequent chapter. Spring MVC has been used in chapter 7 in order to associate Model in chapter 6 with an appopriate view and controller. For readers who are not familiar with Spring MVC; a little information is provided, but there are lots of documentation in World Wide Web for Spring MVC; one of those should be read before starting this chapter. In chapter 7, AOP has been used for caching, concurrency, security in a sensible manner.

To conclude, the book Spring 2.5: Aspect Oriented Programming is an excellent source for programmers who are familiar with OOP, Spring Framework and interested in applying AOP on a real project.

Refactoring: Sync. to Async. (An Object Oriented Approach)

Sunday, January 4th, 2009

Let’s get back to the refactoring : sync to async problem. If you don’t know the scenario, then you will probably want to read this article first.

The purpose of this article is to prove that classical object oriented techniques would also be sufficient for solving this particular problem.

In fact, some people have been talking about AOP as if it is a total revolution and it provides radical solutions for the problems that have never been resolved before!

I am personally against those kind of ideas and believe that the main idea behind AOP is not to derive solutions to problems we haven’t been able to solve so far. I believe the idea is to improve the solutions to the problems we have dealed with.

Let’s step back to the example in previous article and solve the problem using object oriented techniques.

To do that, we are going to use the “Decorator” design pattern. However, for this approach to become a valid one, the class we are going to decorate should have been created in such a way that it is based on some carefully designed abstractions and coded on to an interface, not an implementation!

If you look through the code, you may notice that the class Foo is coded on top of an implementation rather than an interface.

In fact, it is this way; because my intention was just to introduce the problem and indicate how AOP could become a solution for that. Most of the time, a good programmer would depend on abstractions and program on top of interfaces, rather than implementations!

Hence, please assume that Foo implements IFoo and IFoo simply consists of the same methods as we have in Foo. Moreover, assume that all the other types depend on IFoo instead of Foo.

Caution: Notice that we are making the design in “the other way around”, this is not a good design practice! We should have identified the interface before and implementation later, however, I am trying to fit one problem that is subject for one particular article to another article, this was not my intention, hence there should be no problem at all, for this specific case.

By using Decorator pattern, we will decorate instances of Foo in such a way that they will represent an “asynchronous” behaviour rather than a “synchronous” one. AsynchronousFoo class will decorate Foo and simply delegate calls to an instance of Foo, but in an asynchronous way.

package ali.test;

public interface IFoo {

public void performFirstTask() throws InterruptedException;

public void performSecondTask() throws InterruptedException;

}

package ali.test;

public class Foo implements IFoo {

public Foo()

{

}

public void performFirstTask() throws InterruptedException

{

Thread.sleep(3000);

System.out.println(“Foo : the first complex task has been completed…”);

}

public void performSecondTask() throws InterruptedException

{

Thread.sleep(3000);

System.out.println(“Foo : the second complex task has been completed…”);

}

}

package ali.test;

public class AsynchronizedFoo implements IFoo {

private Foo foo;

public AsynchronizedFoo(Foo f)

{

this.foo = f;

}

@Override

public void performFirstTask() throws InterruptedException {

// TODO Auto-generated method stub

Thread t = new Thread()

{

public void run()

{

try {

foo.performFirstTask();

} catch (InterruptedException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

}

};

t.start();

}

@Override

public void performSecondTask() throws InterruptedException {

// TODO Auto-generated method stub

Thread t = new Thread()

{

public void run()

{

try {

foo.performSecondTask();

} catch (InterruptedException e) {

// TODO Auto-generated catch block

e.printStackTrace();

}

}

};

t.start();

}

}

import ali.test.AsynchronizedFoo;

import ali.test.Foo;

import ali.test.IFoo;

public class Program {

public static void main(String[] args) throws InterruptedException

{

System.out.println(“Foo obj. will complete a complex task.”);

IFoo f = new AsynchronizedFoo(new Foo());

f.performFirstTask();

f.performSecondTask();

System.out.println(“end of sequence”);

}

}

Now that we have resolved this issue in two different ways; using an object oriented approach and an aspect oriented approach, you can select and use one of them, depending on the conditions.