开发者

Stale object in memory (mysql, spring 3, hibernate)

I'm using Spring 3, Hibernate 3.3.1 and MySQL 5.1.x (on red hat 5, also see same behavior when on windows however). I'm noticing that a row in the database is getting updated, but the one of the object references in memory is not being refreshed. I'll try to describe the class structure in a simplified form..

class A {
  @OneToMany(cascade = CascadeType.ALL)
  List<Widget> widgets;

  @OneToMany(cascade = CascadeType.ALL)
  @Cascade(value = org.hibernate.annotations.CascadeType.DELETE_ORPHAN)
  List<B> bObjects;

  @Transactional
  public void turnOnWidgets() { ... }
}

class B {
  @ManyToOne(cascade = { CascadeType.PERSIST, CascadeType.MERGE, CascadeType.REFRESH })
  @Cascade(value = { org.hibernate.annotations.CascadeType.LOCK, org.hibernate.annotations.CascadeType.EVICT})
  private A aObj;

  @Transactional(propagation=Propagation.REQUIRES_NEW)
  public void turnOnWidgets() { 
    for (Widget w : aObj.getWidgets()) {
      w.setOn(true);
    }
  }
}

class Widget {
  Boolean on;
}

Here's the sequence of actions. When A.turnOnWidgets gets invoked it iterates through its collection of "bObjects" and invokes "turnOnWidgets" on each B object. The B object modifies the "on" property for each widget referenced by the A object (as shown in above in B.turnOnWidgets).

When this happens I can look at the database and see that the "on" value has changed for the widgets. However, when I step into the code using a debugger I notice that the B object references a different instance of A (e.g. the same A from the database but in memory its a diff开发者_C百科erent Java object instance) than the A that I invoked "turnOnWidgets" on.

Effectively what I see is that when I navigate the object graph by looking at the Widgets contained by the A instance, the Widgets "on" property is false. However, if I look at the Widgets by navigating from B.aObj.getWidgets() their "on" property is true.

When my application was running against an Oracle database this all worked fine, once I switched to MySQL I began seeing this problem.

Anyone know if there is something particular about MySQL (perhaps in conjunction with Hibernate and/or Spring)?

UPDATE So I think I've narrowed it down to a section in the code where a JPA "refresh" is performed on the "B" object. When running against oracle this causes the objects to refresh properly in memory, however, when running against MySQL the objects are not being updated properly. Still need to figure out why.


Not sure about your problem, but I guess you need mappedBy since it's required for bidirectional relationships:

@OneToMany(cascade = CascadeType.ALL, mappedBy = "aObj")
@Cascade(value = org.hibernate.annotations.CascadeType.DELETE_ORPHAN)
List<B> bObjects;


turns out the db isolation level was the issue, here's the question i started on that which resolved the problem i was having here.

Outer transaction in a nested transaction use case isn't seeing updates persisted in database (JPA, MySQL, Spring Framework, and Hibernate)

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜