openjpa-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "Phani Madgula" <phanibalaji.madg...@gmail.com>
Subject Entities not flushing into oracle database.
Date Tue, 30 Dec 2008 07:26:33 GMT
Hi,

I am using Apache Geronimo for my JPA applications. I am using oracle
10G database for my entities.

I have an EAR application with an EJB and a WEB module. EJB module has
an SLSB that uses Container Managed Transactions and uses Container
Managed Persistence Manager (EntityManager injected by container). The
code is as follows.

************
package sample.jpa;


import javax.ejb.EJBException;
import javax.ejb.Remote;
import javax.ejb.Stateless;
import javax.ejb.TransactionAttribute;
import javax.ejb.TransactionAttributeType;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.persistence.PersistenceContextType;


@Stateless
@Remote(AccountInterface.class)
public class AccountBean implements AccountInterface {


    @PersistenceContext(type=PersistenceContextType.TRANSACTION)
    private EntityManager manager;


    @TransactionAttribute(TransactionAttributeType.REQUIRED)
    public Account open(int accountNumber) {
        Account account = manager.find(Account.class, accountNumber);
        if(account == null){
        	account = new Account();
        	account.ownerName = "anonymous";
            account.accountNumber = accountNumber;
            manager.persist(account);
            manager.flush();
            return account;
        }else{
        	throw new EJBException("Account already exists..!!. Account
Number = "+accountNumber);
        }

    }

    @TransactionAttribute(TransactionAttributeType.REQUIRED)
	public double getBalance(int accountNumber) {
    	 Account account = manager.find(Account.class, accountNumber);
        if(account==null)
            throw new EJBException("Account not found..!!. Account
Number = "+accountNumber);
        return account.balance;
    }

    @TransactionAttribute(TransactionAttributeType.REQUIRED)
    public void deposit(int accountNumber, double amount) {
    	Account account = manager.find(Account.class, accountNumber);
        if(account==null)
        	throw new EJBException("Account not found..!!. Account Number
= "+accountNumber);
        double new_balance = account.getBalance() + amount;
        account.setBalance(new_balance);
        manager.flush();
    }

    @TransactionAttribute(TransactionAttributeType.REQUIRED)
    public double withdraw(int accountNumber, double  amount) {
    	
    	Account account = manager.find(Account.class, accountNumber);
    	
        if(account==null)
        	throw new EJBException("Account not found..!!. Account Number
= "+accountNumber);

        if (amount > account.getBalance()) {
            return 0;
        } else {
        	double new_balance = account.getBalance() - amount;
            account.setBalance(new_balance);
            manager.flush();
            return amount;
        }
    }



}
**************

The Account.java is an entity.

The WEB module has a servlet that looks up EJB to perform amount
transfer from one account to another.

The code is as follows.

******************
package sample.jpa;

import java.io.IOException;
import java.io.PrintWriter;

import javax.ejb.EJB;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.persistence.EntityManager;
import javax.persistence.PersistenceContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.transaction.UserTransaction;

/**
 * Servlet implementation class for Servlet: Test
 *
 */
 public class Test extends javax.servlet.http.HttpServlet implements
javax.servlet.Servlet {
   static final long serialVersionUID = 1L;


   @PersistenceContext(unitName="AccountUnit")
   private EntityManager em;

   @EJB AccountInterface accountBean;

    /* (non-Java-doc)
	 * @see javax.servlet.http.HttpServlet#HttpServlet()
	 */
	public Test() {
		super();
	}   	
	
	/* (non-Java-doc)
	 * @see javax.servlet.http.HttpServlet#doGet(HttpServletRequest
request, HttpServletResponse response)
	 */
	protected void doGet(HttpServletRequest request, HttpServletResponse
response) throws ServletException, IOException {
		// TODO Auto-generated method stub
		PrintWriter out = response.getWriter();
		
		int accNo1 = Integer.parseInt(request.getParameter("account1"));
		int  accNo2 = Integer.parseInt(request.getParameter("account2"));
		double amount = Double.parseDouble(request.getParameter("amount"));
		
		try{
			Context ctx = new InitialContext();
			UserTransaction ut =
(UserTransaction)ctx.lookup("java:comp/UserTransaction");
			ut.begin();
			Account account = em.find(Account.class, accNo1);
			if(account.getBalance() < amount){
				throw new Exception("Account "+accNo1+" does not have enough
balance "+amount);
			}else{
				out.println("Account ="+accNo1+" : Current balance "+account.getBalance());
				accountBean.withdraw(accNo1, amount);
				out.println("Account ="+accNo1+" : Withdrawn "+amount);
				double balance = account.getBalance();
				out.println("Account ="+accNo1+" : After withdrawing the balance
is "+balance);
				Account account2 = em.find(Account.class, accNo2);
				out.println("Account ="+accNo2+" : Current balance "+account2.getBalance());
				accountBean.deposit(accNo2, amount);
				out.println("Account ="+accNo2+" : After depositing the balance is
"+account2.getBalance());
			}
			em.flush();
			ut.commit();
		}catch(Exception e){
			throw new ServletException(e);
		}
	}  	
	
	/* (non-Java-doc)
	 * @see javax.servlet.http.HttpServlet#doPost(HttpServletRequest
request, HttpServletResponse response)
	 */
	protected void doPost(HttpServletRequest request, HttpServletResponse
response) throws ServletException, IOException {
		// TODO Auto-generated method stub
	}   	  	
}
****************

The persistence.xml file is as follows.

******************
  <?xml version="1.0" encoding="UTF-8" ?>
<persistence xmlns="http://java.sun.com/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" version="1.0"
xsi:schemaLocation="http://java.sun.com/xml/ns/persistence
http://java.sun.com/xml/ns/persistence/persistence_1_0.xsd">

<persistence-unit name="AccountUnit" transaction-type="JTA">
  <description>ContainerManagedJPA</description>
  <provider>org.apache.openjpa.persistence.PersistenceProviderImpl</provider>
  <jta-data-source>PhaniOraclePool</jta-data-source>
  <class>sample.jpa.Account</class>
  </persistence-unit>
</persistence>
***************

The "PhaniOraclePool" is the datasource deployed on the Geronimo
server over Oracle database.

Problems :
**********
1. When the servlet is executed, the committed values are not flushing
to Oracle database. After a transaction, when I query the database on
SQLPLUS prompt, I still get the old values. I have used all possible
methods like enititymanager.flush etc. It did not work.

2. Only when I shutdown the geronimo server, I am able to see the data
being flushed to the database.

3. I have even redeployed the app to see if the EntityManager is
flushing the data to the base. But no luck.

The question is, how can we flush the data to the database in a
controlled fashion from OpenJPA cache as sometimes we need the
committed values to be available in the database. ??

Thanks in advance.
Phani

Mime
View raw message