OpenJPA's batching update constraint manager currently does not retrieve non 
primary key identity fields on an insert/update
----------------------------------------------------------------------------------------------------------------------------

                 Key: OPENJPA-1930
                 URL: https://issues.apache.org/jira/browse/OPENJPA-1930
             Project: OpenJPA
          Issue Type: Bug
    Affects Versions: 2.2.0
         Environment: DB2 (from Control Center Help About)
Product Identifier SQL09072
Level Identifier 08030107
Level DB2 v9.7.200.358
Build Level s100514
PTF IP23084

JCC Driver is db2jcc4-9.7.100.177.jar, db2jcc_license_cu-9.7.100.177.jar 

The Database version is DB2 Express C v 9.7.200.358 on a windows 7 box.
I am using jdk version jdk1.6.0_07 inside of RAD 8.0.1 to run my junit tests. 
            Reporter: Rob Sinner


Please see full thread here:

http://openjpa.208410.n2.nabble.com/How-to-get-generated-keys-without-requerying-the-database-td5957346.html

Thank you Jeremy for providing a workaround and for your timely response here. 
It is much appreciated.

Jeremy Bauer's Comments
Thanks for the DB and JCC info.  I remembered there being some issue with
getGeneratedKeys on a JCC driver level, but that was quite a while ago.
Your driver and DB level are current, so I quickly set aside that
possibility.

Using a trimmed down version of your code, I found that there is a bug in
OpenJPA's batching update constraint manager (the piece of code that drives
batched updates through the JDBC driver).  The batching manager currently
does not retrieve non-key identity fields on an insert/update operation.
Until a fix is available, you can get around the problem by adding this
property to your persistence.xml:

      <property name="openjpa.jdbc.UpdateManager" value="constraint"/>

This property enables the non-batching constraint update manager, which has
the proper code to retrieve the generated field. 

- My Beginning Comments
I have an Entity with a non primary key identity column.

This entity  
Part.java
has the following fields among others

        @EmbeddedId
        private PartPK pk;


        @GeneratedValue(strategy=GenerationType.IDENTITY)
        @Column(name="REC_ID")
        private Integer recId;

Note the EmbeddedId does not contain the  Generated Value , the PartPk is made 
up of two strings, one for company and one for part number.

So the Entity has a primary key which is  a business composite key. This table 
also has a column in DB2 which is a IDENTITY column which is not part of the 
primary key. This identity column which is not part of the primary key is 
called REC_ID.

After insert I would like the recId to be populated onto the entity however it 
is not. In JDBC this is usually accomplished via statement.getGeneratedKeys 
after the insert statements has been run.

For example in a straight JDBC Data Access Object this would be accomplished 
after the insert statement by
                        // retrieve values from auto-increment columns
                        rs = stmt.getGeneratedKeys();
                        if (rs != null && rs.next()) {
                                dto.setRecId( new Integer( rs.getInt(1) ) );
                        }

However when I run a junit test using a simple JPA data access object the recId 
column is null after insert.

        public void testInsert()
        {
                        log.info("insert");
                        log.info("part="+part);

                        manager = getManager();
                       
                        pk.setIncomp(comp);
                        pk.setInpart(part);

                        dto.setPk(pk);

                        log.info(dto);
                        manager.insert(dto);
                                               
                        log.info("recId="+dto.getRecId());
                        assertFalse("recId is null after insert should not be", 
dto.getRecId() == null); //fails here
      }


The manager class is wrapping this data access object code

        public PK insert(DTO dto) throws Exception {
                EntityManager em = getEntityManager();
                em.persist(dto);
                return dto.getPk();
        }
 
How do I specify the mapping in the entity with a non primary key identity 
column such that after an insert the non primary key identity column is 
populated onto the entity.

Among other things I am using Db2 with spring and openjpa 2.2.0.

I believe this has something to do with getGeneratedKeys and how I'm doing the 
mapping in the entity and possibly DB2 with openjpa.

The table are legacy and are not easily modifiable to accomplish this. Im 
trying to avoid having to relook up the non primary key with a seperate query 
by the primary key after the insert.

Thank you in advance for your assistance. I searched in the nabble users list 
and could not find anything related. If you need more detailed information I 
can post more. I believe this is a simple configuration done incorrectly at the 
entity level.

Thank you in advance for any assistance you provide. 

-- 
This message is automatically generated by JIRA.
-
You can reply to this email to add a comment to the issue online.

Reply via email to