Skip to content

Making persistence layer (Starting with facelets part 2)

March 24, 2010

This is the second part of Starting with Facelets tutorial. To make  Blog app working we have to deal with persistence. I’ll use Hibernate for persistence mechanism (it’s integrated with JBoss platform so you don’t need to download additional jars and add them to project).  In the first part I have created JSF project in Eclipse and now I am going to create Enterprise app and EJB Project (for ejb beans and entities) in Eclipse and place existing web application in it. When create Enterprice application you have  to add DemoFacelets project (web app from the first part) and ejb project which is created in this part of tutorial.  The reason why I’m doing this, cause I’m gonna use EJB and all functionality of JBoss AS for deploying Java enterprise apps.

First, we have to make entity classes. This is a simple blog app and there are only 3 entities. It’s User, Article and Comment. Logic is very simple. User (Author) writes blog articles and others comment on it.  Go to New–New EJB Project  to create EJB project in Eclipse. After this create Enterprice application.  Create package demo.model and place following code for Article Java class.

package demo.model;

import static javax.persistence.GenerationType.IDENTITY;
import java.io.Serializable;
import java.util.Date;
import java.util.List;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.OneToMany;

@Entity
public class Article  implements Serializable{

	private static final long serialVersionUID = 4902391506140773812L;
	@Id
	@GeneratedValue(strategy = IDENTITY)
	@Column(name = "_id", unique = true, nullable = false)
	private Long id;
	private String title;
	@ManyToOne(fetch = FetchType.LAZY)
	@JoinColumn(name = "author_id", nullable = false)
	private User author;
	private Date dateOfPublishing;
	@OneToMany(fetch = FetchType.LAZY, mappedBy = "article")
	private List<Comment> comments;
	private int rating;

	public void setId(Long id) {
		this.id = id;
	}
	public Long getId() {
		return id;
	}
	public void setTitle(String title) {
		this.title = title;
	}
	public String getTitle() {
		return title;
	}
	public void setAuthor(User author) {
		this.author = author;
	}
	public User getAuthor() {
		return author;
	}
	public void setDateOfPublishing(Date dateOfPublishing) {
		this.dateOfPublishing = dateOfPublishing;
	}
	public Date getDateOfPublishing() {
		return dateOfPublishing;
	}
	public void setRating(int rating) {
		this.rating = rating;
	}
	public int getRating() {
		return rating;
	}
	public void setComments(List<Comment> comments) {
		this.comments = comments;
	}
	public List<Comment> getComments() {
		return comments;
	}

}

For managing relations between entities I’ve used Java persistence annotations. The relation between Article and Comment is parent/children relationship. To implement this kind of relation I’ve used bidirectional mapping. Relationship with Article class in Comment class is mapped with ManyToOne annotation.

@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "author_id", nullable = false)
private User author;

There are also User and Comment classes which are also annotated but it is trivial. You can download all 3 classes.

Generic DAO pattern

There are several patterns how to implement persistence layer. For me the most elegant solution is to use Generic DAO pattern which makes following benefits:

  1. Reusing non-CRUD operation. With generic DAO pattern you provide higher level of abstraction for data access operations instead basic CRUD operations
  2. Persistence layer have generic interface without exposing implementation. You can implement it in Hibernate or JPA. One interface (facade) is always exposed.

Generic DAO pattern

There are 2 hierarchies. On one side is interfaces and on the other is its implementations. The highest interface defines basic operations(Create,Read,Update,Delete). The sub interfaces is defined for each entity in application that requires operations with database. The same logic is with implementation classes.

GenericDao interface have basic CRUD operations. All interfaces are in demo.persistence package. Also I have used Java generics. T parameter is the entity for which I’m implementing DAO.

package demo.persistence;

import java.util.List;

public interface GenericDAO<T> {
	void save(T object);
	T get(Long id);
	void update(T object);
	void delete(T object);
	List<T> listAll();
}

For DAO implementations I have used EJB 3.0. All DAO objects are implemented as stateless EJB beans. GenericDAOImpl is abstract class and it isn’t EJB bean. It has references to hibernate session and implemented basic and common operations (CRUD). All DAO implementation classes are subclass of GenericDAOImpl abstract class and EJB stateless beans.

package demo.persistence.implementation;

import java.util.List;
import org.hibernate.Criteria;
import org.hibernate.Session;
import org.hibernate.criterion.Restrictions;
import javax.persistence.PersistenceContext;
import demo.persistence.GenericDAO;

public abstract class GenericDAOImpl<T> implements GenericDAO<T> {
	@PersistenceContext(unitName="BlogPU")
	private Session session;
	private Class<T> persistentClass;
    
    
	@SuppressWarnings("unchecked")
	public T get(Long id) {
		Criteria criteria = session.createCriteria(getPersistentClass()).
		add(Restrictions.like("id", id));
		T uniqueResult = (T) criteria.uniqueResult();
		return uniqueResult;
	}

	@SuppressWarnings("unchecked")
	public List<T> listAll() {
		Criteria criteria = session.createCriteria(getPersistentClass());
		return criteria.list();
	}

	public void save(T object) {
        session.saveOrUpdate(object);	
	}

	public void update(T object) {
        session.update(object);		
	}
	public void delete(T object) {
	    session.delete(object);
	}
	
	public void setSession(Session session) {
		this.session = session;
	}

	public Session getSession() {
		return session;
	}

	public void setPersistentClass(Class<T> persistentClass) {
		this.persistentClass = persistentClass;
	}

	public Class<T> getPersistentClass() {
		return persistentClass;
	}

}

With anotaion @PersistenceContext(unitName=”BlogPU”) hiberante session is injected with persistence unit BlogPU which is defined in persistence.xml file (I’ll explain content of this file later)

Adding configuration files

We have persistence layer implemented using DAO pattern but I did not configure data source. The moste easiest way to configure data source on JBosss AS is to make it as default data source. Make new file mysql-ds.xml and add following xml:

<?xml version="1.0" encoding="UTF-8"?>
<datasources>
  <local-tx-datasource>
  <jndi-name>BlogAppDS</jndi-name>
  <connection-url>jdbc:mysql://localhost:3306/BlogAppDS</connection-url>
  <driver-class>com.mysql.jdbc.Driver</driver-class>
<!-- enter your username and password for MySQL server -->
  <user-name>YOURUSERNAME</user-name>
  <password>YOURPASSWORD</password>
  <valid-connection-checker-class-name>org.jboss.resource.adapter.jdbc.vendor.MySQLValidConnectionChecker</valid-connection-checker-class-name>
  <metadata>
  <type-mapping>mySQL</type-mapping>
  </metadata>
  </local-tx-datasource>
</datasources>

You have to add url of database (<connection-url> tag),jndi name, mysql jdbc driver (<com.mysql,jdbc.Driver> tag), username  and password. Place file in /%jboss-5.1.0.GA install. dir. %/server/default/deploy To make all work  download mysql driver jar and place it in %jboss-5.1.0.GA install. dir. %/server/default/lib folder.

Maybe this post isn’t straitforward. Maybe it is confusing. Dear reader, all these technologies aren’t straitforward and it is take time to learn and use it on right way. Good luck!!

Advertisements

From → Hibernate, Java

2 Comments
  1. I’ve been exploring for a bit for any high quality articles or blog posts on this sort of area .
    Exploring in Yahoo I at last stumbled upon this site.
    Reading this info So i am happy to convey that I have a very good uncanny feeling I discovered just what I needed.
    I most certainly will make certain to don’t forget this site and give it a glance regularly.

Trackbacks & Pingbacks

  1. Testing persistence layer (starting with facelets part 3) « Ivan Doskovic's blog

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: