title: Deadlocked transactions with Hibernate on Oracle
body: <p>I have the following (simplified) Hibernate entities:</p>
  
  <pre><code>@Entity(name = "Foo")
  public class Foo {
  
      @Id
      @GeneratedValue
      public int id;
  
      @OneToOne
      public Bar bar;
  }
  </code></pre>
  
  <p>and,</p>
  
  <pre><code>@Entity(name = "Bar")
  public class Bar {
  
      @Id
      @GeneratedValue
      public int id;
  
      @Column
      public String field;
  
      @Version
      public int version;
  
  }
  </code></pre>
  
  <p>I update these entities in a transaction that looks roughly like this:</p>
  
  <pre><code>Bar bar = findBar(em);
  Foo foo = findFoo(em);
  
  bar.field = "updated value";
  
  if (&lt;condition&gt;) {
      em.remove(foo);
  }
  
  em.detach(bar);
  em.merge(bar);
  </code></pre>
  
  <p>Note that <code>em.remove(foo)</code> is only called sometimes, while bar is always updated.</p>
  
  <p>I'm noticing occasional <code>ORA-00060: Deadlock detected</code> errors when running the application. The dump seems to suggest that the two deadlocked sessions are locked on <code>em.merge(bar)</code> and <code>em.remove(foo)</code>, but I don't understand why that would be the case.</p>
  
  <p>How can this code deadlock? Is there a way to restructure it avoid deadlocking?</p>
  
  <p>Here's some extra information from the trace:</p>
  
  <pre><code>Deadlock graph:
                         ---------Blocker(s)--------  ---------Waiter(s)---------
  Resource Name          process session holds waits  process session holds waits
  TX-00040005-000010dd        73    6557     X             81    6498           X
  TX-00010018-000010bd        81    6498     X             73    6557           X
  
  session 6557: DID 0001-0049-000002F5    session 6498: DID 0001-0051-0000030E 
  session 6498: DID 0001-0051-0000030E    session 6557: DID 0001-0049-000002F5 
  
  Rows waited on:
    Session 6557: obj - rowid = 00004797 - AAAEeXAB4AAADH0BBP
    (dictionary objn - 18331, file - 120, block - 12788, slot - 15)
    Session 6498: obj - rowid = 00007191 - AAAHGRAB4AAAACBBBo
    (dictionary objn - 29041, file - 120, block - 129, slot - 40)
  
  ----- Information for the OTHER waiting sessions -----
  Session 6498:
  program: JDBC Thin Client
      application name: JDBC Thin Client, hash value=2546894660
    current SQL:
  
  delete from Foo where id=:1 
  
  ----- Current SQL Statement for this session (sql_id=sfasdgasdgaf) -----
  update Bar set field=:1, version=:2 where id=:3 and version=:4 
  </code></pre>