You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@openjpa.apache.org by "Fay Wang (JIRA)" <ji...@apache.org> on 2009/10/31 00:36:59 UTC

[jira] Commented: (OPENJPA-1371) Insert is called instead of Update when merge() with derived Identity

    [ https://issues.apache.org/jira/browse/OPENJPA-1371?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=12772179#action_12772179 ] 

Fay Wang commented on OPENJPA-1371:
-----------------------------------

The following test scenario is provided by Constantine Kulak <co...@mail.by>:

There are three entities where PrognosisEntry has derived identity:

***** Source for Prognosis.java:

 @Entity(name = "Prognosis")
 @Table(name = "PROGNOSIS")
 @IdClass(Prognosis.PrognosisId.class)
 @Inheritance(strategy = InheritanceType.JOINED)
 public class Prognosis {

     protected List<PrognosisEntry> entries;
    protected String station;
    protected String type;

    @OneToMany(targetEntity = PrognosisEntry.class, cascade = {CascadeType.MERGE}, mappedBy="prognosis", fetch=FetchType.EAGER)
    public List<PrognosisEntry> getEntries() {
        if (entries == null) {
            entries = new ArrayList<PrognosisEntry>();
        }
        return this.entries;
    }

    public void setEntries(List<PrognosisEntry> entries) {
        this.entries = entries;
    }

    @Id
    @Column(name = "STATION")
    public String getStation() {
        return station;
    }

    public void setStation(String value) {
        this.station = value;
    }

    @Id
    @Column(name = "TYPE_")
    public String getType() {
        return type;
    }

    public void setType(String value) {
        this.type = value;
    }

    public boolean equals(Object object) { ... }
    public int hashCode() { ... }

    public static class PrognosisId {
        protected String station;
        protected String type;

        public String getStation() {
            return station;
        }

        public void setStation(String value) {
            this.station = value;
        }

        public String getType() {
            return type;
        }

        public void setType(String value) {
            this.type = value;
        }

          public boolean equals(Object object) { ... }
        public int hashCode() { ... }
    }
 }


 ***** Source for PrognosisEntry.java:

 @Entity(name = "PrognosisEntry")
 @Table(name = "PROGNOSISENTRY")
 @Inheritance(strategy = InheritanceType.JOINED)
 @IdClass(PrognosisEntry.PrognosisEntryId.class)
 public class PrognosisEntry {

    protected String timestamp;
    protected String localState;
    protected Prognosis prognosis;

    protected Stock stock;

    @Id
    @ManyToOne(targetEntity = Stock.class, cascade = { CascadeType.MERGE }, fetch = FetchType.EAGER)
    public Stock getStock() {
        return stock;
    }

    public void setStock(Stock stock) {
        this.stock = stock;
    }

    @Id
    @ManyToOne(targetEntity = Prognosis.class, cascade = { CascadeType.MERGE }, fetch = FetchType.EAGER)
    public Prognosis getPrognosis() {
        return prognosis;
    }

    public void setPrognosis(Prognosis prognosis) {
        this.prognosis = prognosis;
    }

    @Column(name = "TIMESTAMP_", length = 255)
    public String getTimestamp() {
        return timestamp;
    }

    public void setTimestamp(String value) {
        this.timestamp = value;
    }

    @Basic
    @Column(name = "LOCALSTATE", length = 255)
    public String getLocalState() {
        return localState;
    }

    public void setLocalState(String value) {
        this.localState = value;
    }

    public boolean equals(Object object) { ... }
    public int hashCode() { ... }

    public static class PrognosisEntryId {

        protected Prognosis.PrognosisId prognosis;
        protected String stock;

        public String getStock() {
            return stock;
        }

        public void setStock(String stock) {
            this.stock = stock;
        }

        public Prognosis.PrognosisId getPrognosis() {
            return prognosis;
        }

        public void setPrognosis(Prognosis.PrognosisId prognosis) {
            this.prognosis = prognosis;
        }

        public boolean equals(Object object) { ... }
        public int hashCode() { ... }
    }
 }


 ***** Source for Stock.java:

 @Entity(name = "Stock")
 @Table(name = "STOCK")
 @Inheritance(strategy = InheritanceType.JOINED)
 public class Stock {
    protected String index;
    protected String length;

    @Id
    @Column(name = "INDEX_")
    public String getIndex() {
        return index;
    }

    public void setIndex(String value) {
        this.index = value;
    }
      @Basic
    @Column(name = "LENGTH_", length = 255)
    public String getLength() {
        return length;
    }

    public void setLength(String value) {
        this.length = value;
    }

    public boolean equals(Object object) { ... }
    public int hashCode() { ... }
}

The test scenario: 
(1) create a Prognosis entity with a list of PrognosisEntry.
(2) call em.merge(newEntity) and commit
(3) call em.clear()
(4) call em.merge(newEntity)

Step (4) generate insert statement to insert PrognosisEntry again, resulting in unique constraint violation from the database.

It appears that the ApplicationIds.create(pc, meta) where pc is PrognosisEntry, the oid does not have complete id values.











> Insert is called instead of Update when merge() with derived Identity
> ---------------------------------------------------------------------
>
>                 Key: OPENJPA-1371
>                 URL: https://issues.apache.org/jira/browse/OPENJPA-1371
>             Project: OpenJPA
>          Issue Type: Bug
>          Components: kernel
>    Affects Versions: 2.0.0-M3
>            Reporter: Fay Wang
>             Fix For: 2.0.0-M3
>
>
> Insert is called instead of Update when merge() with derived Identity:

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