lundi 4 avril 2016

Using Atomikos, -journal File Created on Save to Sqlite Database Table, But Does Not Save to Sqlite .db File - Hibernate / JTA / Atomikos

I'm having an issue with doing a simple save of data to a Sqlite DB using Hibernate/JTA/Atomikos. When I execute session.save(), it creates a -journal file in the same folder as the sqlite .db file. However, a commit is done, the journal file is deleted, but the sqlite .db does not get updated. Previously, I was just using JDBC (without JTA or Atomikos) and data was being saved persistently to the DB. But as I've tried to move to using JTA, and using Atomikos, it no longer saves to the Database table.

My files and configuration are based on the following links: http://ift.tt/1ZYKaU5;

http://ift.tt/1qpCi1K

; http://ift.tt/1ZYKcv2 (all atomikos links).

Here are the atomikos libraries I am using (through Maven):

<dependency>
    <groupId>com.atomikos</groupId>
    <artifactId>transactions-jta</artifactId>
    <version>4.0.2</version>
</dependency>


<dependency>
    <groupId>com.atomikos</groupId>
    <artifactId>transactions</artifactId>
    <version>4.0.2</version>
</dependency>


<dependency>
    <groupId>com.atomikos</groupId>
    <artifactId>transactions-jdbc</artifactId>
    <version>4.0.2</version>
</dependency>


<dependency>
    <groupId>com.atomikos</groupId>
    <artifactId>transactions-api</artifactId>
    <version>4.0.2</version>
</dependency>


<dependency>
    <groupId>com.atomikos</groupId>
    <artifactId>transactions-hibernate4</artifactId>
    <version>4.0.2</version>
</dependency>

My hibernate.cfg.xml is as follows:

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE hibernate-configuration PUBLIC "-//Hibernate/Hibernate Configuration DTD 3.0//EN"
                                         "http://ift.tt/1fnOghG">
<hibernate-configuration>
 <session-factory>
  <property name="hibernate.connection.driver_class">org.sqlite.JDBC</property>
  <property name="hibernate.connection.url">jdbc:sqlite:C:\Users\SB\Desktop\rclinicSqlite.db</property>
  <property name="hibernate.connection.username"/>
  <property name="hibernate.connection.password"/>

  <property name="hibernate.connection.datasource">jdbc/rclinicSqlite.db</property>
  <property name="hibernate.jndi.class">javax.naming.InitialContext</property>
  <property name="hibernate.jndi.url">javax.naming.Context.PROVIDER_URL</property>

  <property name="hibernate.c3p0.min_size">1</property>
  <property name="hibernate.c3p0.max_size">1</property>  
  <property name="hibernate.connection.provider_class">org.hibernate.c3p0.internal.C3P0ConnectionProvider</property>
  <property name="hibernate.c3p0.min_size">5</property>
  <property name="hibernate.c3p0.max_size">20</property>
  <property name="hibernate.c3p0.timeout">3000</property>
  <property name="hibernate.c3p0.max_statements">50</property>
  <property name="hibernate.c3p0.idle_test_period">300</property>
  <property name="hibernate.c3p0.dataSourceName">jdbc/rclinicSqlite.db</property>

  <property name="dialect">org.hibernate.dialect.SQLiteDialect</property>
  <property name="hibernate.dialect">org.hibernate.dialect.SQLiteDialect</property>
  <property name="show_sql">true</property>
  <property name="format_sql">true</property>
  <property name="hibernate.current_session_context_class">jta</property>
  <property name="hibernate.transaction.jta.platform">com.atomikos.icatch.jta.hibernate4.AtomikosPlatform</property>
  <property name="hibernate.transaction.flush_before_completion">true</property>
  <property name="hibernate.transaction.coordinator_class">jta</property>

  <mapping resource="User.hbm.xml"/> 

 </session-factory>
</hibernate-configuration>

Here's the User.hbm.xml ((exactly the same as http://ift.tt/1ZYKaU5):

   <class name="User" table="`USERS`"> 
      <id name="id"> 
         <generator class="identity"/> 
      </id> 

      <property name="name" not-null="true" column="`NAME`"/> 
   </class> 

Here's User.java (exactly the same as http://ift.tt/1ZYKaU5):

public class User { 

    private Long id; 
    private String name; 

    public Long getId() { 
       return id; 
    } 
    public void setId(Long id) { 
       this.id = id; 
    } 
    public String getName() { 
       return name; 
    } 
    public void setName(String name) { 
       this.name = name; 
    } 

    public String toString() { 
       return "a User(id=" + id + ", name=" + name + ")"; 
    } 

 }

The relevant java code that then writes to the database table is:

public void doSomeWork() 
{

    try
    {
        initDataSources();
    }
    catch (Exception ex)
    {
        ex.printStackTrace();
    }


    Connection c = null;
    Session session = null;
    UserTransaction userTransaction = null;
    SessionFactory sessionFactoryInst = null;

    try
    {


        Configuration cfg = new Configuration().configure("hibernate.cfg.xml");
        cfg.addAnnotatedClass(User.class);
        sessionFactoryInst = cfg.buildSessionFactory();

        session = sessionFactoryInst.openSession();
        //session = sessionFactoryInst.getCurrentSession();

        userTransaction = new com.atomikos.icatch.jta.UserTransactionImp();
        userTransaction.setTransactionTimeout(60);
        userTransaction.begin();

        c = dataSource1.getConnection();

        Statement statement = c.createStatement();
        statement.setQueryTimeout(30);  // set timeout to 30 sec

        //statement.executeUpdate("CREATE TABLE users (id INTEGER, name STRING)");
        //userTransaction.commit();
        //session.getTransaction().begin();


        User u = new User();
        u.setName("testName");
        session.save(u);
    }
    catch (Exception e) {
        e.printStackTrace();
    }
    finally {
        try
        {
            session.flush();
            userTransaction.commit();
            session.close();
            c.close();
        }
        catch (Exception ex)
        {
            ex.printStackTrace();
        }
    }


    sessionFactoryInst.close();
    dataSource1.close();

}



    private void initDataSources() throws NamingException { 
        Context ctx = new InitialContext(); 
        dataSource1 = getDataSource_db1(); 
        ctx.rebind("testDS1", dataSource1); 
        ctx.close(); 
     } 

    private AtomikosNonXADataSourceBean getDataSource_db1() { 

        AtomikosNonXADataSourceBean ds = new AtomikosNonXADataSourceBean(); 
        ds.setUniqueResourceName("SQLITE - RCLINIC"); 
        ds.setDriverClassName("org.sqlite.JDBC"); 
        String sqliteDBPathAndNameStr = "C:\Users\SB\Desktop\rclinicSqlite.db";
        ds.setUrl("jdbc:sqlite:" + sqliteDBPathAndNameStr);
        ds.setPoolSize ( 3 );
        return ds;
     } 


***NOTE: dataSource1 is a class variable: AtomikosNonXADataSourceBean dataSource1;***

This is partially working, because the users table in the rclinicSqlite.db was created. I opened up the rclinicSqlite.db using SqliteBrowser and here is the result before any insert (before session.save()):

SqliteBrowser - rClinicSqlite.db

Then, when I execute the session.save line below:

   User u = new User();
   u.setName("testName");
   session.save(u);

When the session.save line executes, it creates a rclinicSqlite.db-journal file in the same folder as the rclinicSqlite.db. However, then flush, commit, and close are executed, the journal file is deleted, but the rclinicSqlite.db does not get updated. I have removed the flush, and tried different orderings, but there is no change. Can anyone help with saving the data to the database when using Atomicos?

Aucun commentaire:

Enregistrer un commentaire