Wednesday, December 14, 2011

JPA

This is a a step by step instruction on how to create an ejb project and call it from a stand alone java class and from a web page. Basically what the application will do is connect Authors and Books and display it in a GUI.

The work order is.

One ejb (Steteless session bean)

Two entity classes
One pom.xml file per project (all in all 2 pom files)
Everything will be built with maven


Step 1 -Create maven project structure

Top directory is called book and beneath it we create two projects, bookejb and bookwar


Step 2 - Add two pom files, first the top pom.




4.0.0

Parent
org.aja.book
parent
1.0.0

pom



ejb






org.apache.maven.plugins
maven-compiler-plugin
2.0.2

1.5
1.5








Step 3 - Add pom file in ejb project



org.aja.book
parent
1.0.0

org.aja.book
4.0.0
ejb
1.0.0
ejb
Aja EJB




java
java-ee
5.0
provided





Step 4 - Now we must create an ejb-jar.xml file in the directory structur, otherwise maven will not build.

In the ejb project create this. src/main/resources/META-INF/ejb-jar.xml

This file must contain this;



aja-book-ejb


Step 5 - build

execute mvn clean install


Create data source

First step is to add the actual database handling. Since we are using ejbs we must use an EJB container to run it, in our
case the Sun Server. Let's add a data connection.

How to do it can be found elsewhere but in short, in the App Server, go to

Resources->JDBC->Connection Pools;

Choose DataSource class name.

If you work with say mysql or toplink, you must put the jar file in the App Servers lib directory. I doesn't matter in
which lib (the AppServers top lib directory, or the domain lib directory) . As you probably understand, in the top lib all
applications can share it, in the domain only those classes find it.


Make sure the connection type is

javax.sql.ConnectionPoolDataSource.
Make sure to ping the database when you are done.

Ok, add
Resources->JDBC->JDBC Resources

Add a jndi name to your connection pool. I will call my pool

jdbc/BookPool


Now, add a persistence.xml, in the src/main/resources/ folder. My file looks like this;





jdbc/__default






Bascially the file contain the name of the Pool which
we deined in the App Server. If everything is ok, they will connect
with each other and live happily ever after. At the moment we leave all
transaction handling and stuff like that to
the wise care of the application server and all default vales. These
values are often sensible and in 99% of the cases you can let them stay
as they are.


Create java classes

The business objects contain all getter/setters we need and we will create it in org.book.business. We build a really small application so we will use the same objects within the whole application, from the database to the exposed services. We are now only working in the ejb project.


Step 6- Add Author entity

Add the Author.

package org.aja.book.business;

import java.io.Serializable;
import java.util.Collection;

import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.OneToMany;
import javax.persistence.Table;

import static javax.persistence.CascadeType.ALL;

@Entity
@NamedQueries( {
@NamedQuery(name = "getAllBooksByAuthor", query = "SELECT A FROM Author A WHERE A.firstName = :firstName AND A.lastName = :lastName")})

@Table(name = "AUTHOR")
public class Author implements Serializable {

/**
*
*/
private static final long serialVersionUID = 5172793849216643729L;

protected Collection books;

@OneToMany(cascade = ALL, mappedBy = "author")
public Collection getBooks() {
return books;
}

public void setBooks(Collection books) {
this.books = books;
}

private String firstName;

private String lastName;

private String id;

@Id
public String getId() {
return id;
}

public void setId(String id) {
this.id = id;
}

public String getFirstName() {
return firstName;
}

public void setFirstName(String firstName) {
this.firstName = firstName;
}

public String getLastName() {
return lastName;
}

public void setLastName(String lastName) {
this.lastName = lastName;
}

}


Step 7 - Add the book entity.

package org.aja.book.business;
import java.io.Serializable;

import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.persistence.NamedQueries;
import javax.persistence.NamedQuery;
import javax.persistence.Table;

@Entity
@NamedQueries( {
@NamedQuery(name = "getAllBooks", query = "SELECT B FROM Book B")})
@Table(name = "BOOK")
public class Book implements Serializable {

/**
*
*/
private static final long serialVersionUID = -5901348294266358004L;

private Author author;

private String title;

private int pages;

private String id;

@Id
public String getId() {
return id;
}

public void setId(String id) {
this.id = id;
}

public String getTitle() {
return title;
}

public void setTitle(String title) {
this.title = title;
}

public int getPages() {
return pages;
}

public void setPages(int pages) {
this.pages = pages;
}

@ManyToOne
public Author getAuthor() {
return author;
}

public void setAuthor(Author author) {
this.author = author;
}


}


Step 8 - Add remote interface

package org.aja.book.service;

import javax.ejb.Remote;

@Remote
public interface BookServiceRemote extends BookService {

}


Step 9 - Add local interface

package org.aja.book.service;

import javax.ejb.Local;
@Local
public interface BookServiceLocal extends BookService {

}


Step 10 - Add service interface

package org.aja.book.service;

import java.util.List;

import org.aja.book.business.Author;
import org.aja.book.business.Book;

public interface BookService {

public void addBook(Book book);

public List getAllBooksByAuthor(Author author);

public List getAllBooks();
}


Step 11 - Add concrete class implementing the service interface

package org.aja.book.service.impl;

import java.util.List;

import javax.ejb.Local;
import javax.ejb.Remote;
import javax.ejb.Stateless;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.Query;

import org.aja.book.business.Author;
import org.aja.book.business.Book;
import org.aja.book.service.BookService;
import org.aja.book.service.BookServiceLocal;
import org.aja.book.service.BookServiceRemote;

@Stateless(mappedName = "aja/BookService")
@Local(BookServiceLocal.class)
@Remote(BookServiceRemote.class)
public class BookServiceImpl implements BookService {


@PersistenceContext
EntityManager em;

public void addBook(Book book) {
em.persist(book);
}

@SuppressWarnings("unchecked")
public List getAllBooksByAuthor(Author author) {

Query q = em.createNamedQuery("getAllBooksByAuthor");
q.setParameter("firstName", author.getFirstName());
q.setParameter("lastName", author.getLastName());
return q.getResultList();

}

@SuppressWarnings("unchecked")
public List getAllBooks() {
Query q = em.createNamedQuery("getAllBooks");
return q.getResultList();

}

}

0 comments:

Post a Comment