openjpa-users mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Rick Curtis <>
Subject Re: Simple object synchronization
Date Tue, 23 Nov 2010 14:01:21 GMT
Cefn -

I did look at this quickly yesterday and I'd say this is a bug with OpenJPA.
I believe them problem is that when you merge and existing Entity (which
didn't come from us) we aren't sure where this is a insert or an update...
it looks like we make an incorrect assumption based off the version field.
If you were to set the version field to mirror the value in the DB, this
would work correctly.

Please go ahead and open a JIRA.


On Mon, Nov 22, 2010 at 7:02 AM, <> wrote:

> In my test app, I'm dealing with objects which didn't arise in a
> Persistence Context, but may need to be 'synchronized' with the
> corresponding stored data record. Can anyone point me to the right strategy
> for this very simple operation? My problem: I don't see a simple signature
> within the JPA APIs which takes account of this situation, and attempts to
> use promising ones are triggering errors.
> Ideally I want to be able to say 'write this object's fields into the
> database, using its identity to determine which record to create or update.
> If it already exists then overwrite values, cascading changes to referenced
> objects as overwrites too. I must be missing something about the way these
> operations should be used given the error I'm seeing.
> In the app, filesystem traversals (which generate  filesystem, folder and
> file objects using constructors) are repeated periodically, new items should
> be stored in new records, and existing items should have their records
> overwritten to incorporate any changes in the filesystem (reflected by the
> objects and their fields).
> From looking at the OpenJPA DAO lifecycle, all the EntityManager operations
> seem to assume your object originated with an EntityManager at some point in
> the past, even if perhaps it has been detached since. Something which has
> been independently originated using a constructor, but for which a
> corresponding identity already exists doesn't seem to be anticipated, at
> least in the descriptions provided.
> The App class in this github folder contains the problem merge(...) call...
> Currently the engine sees duplicate identities as a clash when using
> merge(), rather than an opportunity to synchronise the new object into the
> corresponding data record. I'd expect identity clashes to arise using
> persist() but not merge(). Calling either merge() or persist() on a FileImpl
> created using a constructor in a Filesystem traversal triggers the same
> error...
> org.apache.openjpa.lib.jdbc.ReportingSQLException: ERROR: duplicate key
> value violates unique constraint "file_pkey" {prepstmnt 32879825 INSERT INTO
> file (locationString, location, version, folder) VALUES (?, ?, ?, ?)
> [params=?, ?, ?, ?]} [code=0, state=23505]
> Of course it's possible for me to hard code a 'does this object already
> exist yet' sort of behaviour, using find(...), then delete, then persist, or
> alternatively comparing all the fields and changing them, but this obviously
> takes away from the advantage of annotation-oriented data objects.
> Assumptions about Data Object identity and fields will end up bleeding out
> into my application code where it should be handled by JPA conventions in
> the data objects.
> If I was to manually verify whether an object already exists, I'd want to
> say find(object) not find(identity). Otherwise I have to re-represent all
> the object->identity relationships which JPA has baked in. Once I've
> retrieved the record I'd presumably have to delete it (possibly causing a
> cascade of removes), and reinsert possibly the same data, which just seems
> wrong, but let me know if this is my only option.
> Given JPA is supposed to understand what identity and fields my object has,
> why can't I ask it to commit the new data into the database? I'd really
> benefit from suggestions how this should properly be approached.
> Cefn

  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message