2011-11-01 25 views
6

Tôi viết dự án và sử dụng NHibernate 3.1Tại sao NHibernate ném "StaleObjectStateException"?

SimpleTest:

Forum forum = Session.CreateCriteria<Forum>().Add(Restrictions.Eq("UrlName", "reportabug")).UniqueResult<Forum>(); 
forum.TopicsCount++; 
IForumRepository forumRepository = new ForumRepository(SessionFactory); 
forumRepository.Update(forum); 

public virtual void Update(TEntity entity) 
{ 
    if (!session.Transaction.IsActive) 
    { 
     TResult result; 
     using (var tx = session.BeginTransaction()) 
     { 
      session.SaveOrUpdate(entity) 
      tx.Commit(); 
     } 
     return result; 
    } 
    session.SaveOrUpdate(entity) 
} 

Bản cập nhật cuối cùng ném ngoại lệ: truy vấn

StaleObjectStateException was unhandled by user code: 
    Row was updated or deleted by another transaction (or unsaved-value mapping was incorrect) 

SQL:

UPDATE Forums 
SET Name = 'Forums Issues (not product support)' /* @p0 */, 
     UrlName = 'reportabug' /* @p1 */, 
     Description = 'Use this forum to report issues with the online forums application. When reporting an issue please include relevant details such as repro steps, error messages and browser version.' /* @p2 */, 
     CategoryId = 'b2cc232c-0d5c-4f35-bb6f-29c67d7d40c2' /* @p3 */, 
     TopicsCount = 1 /* @p4 */ 
WHERE ForumId = '864046b7-ca57-48c4-8a81-082103223527' /* @p5 */ 

ForumId là đúng. Có thể đây là sự tương tranh? Bạn có ý tưởng gì không?

+0

@ManuPK, ngoại lệ được ném trên dòng tx.Commit(); –

Trả lời

5

StaleObjectStateException là một cách để bảo đảm tính nhất quán về dữ liệu đọc API here. Hibernate duy trì các version của các đối tượng mà nó cập nhật và sẽ ném một lỗi nếu phiên bản trong DB và trong bộ nhớ không khớp. Đọc thêm về cơ chế khóa lạc quan here.

Vì vậy, Gỡ lỗi ứng dụng bằng thông tin này. Tôi không quen thuộc với cú pháp C# nhưng tôi nghĩ rằng lần lưu thứ hai phải ở trong điều kiện else.

+0

Thats chính xác, tôi hoàn toàn bị mất rằng: P +1. @Kovpaev - Xóa 'session.SaveOrUpdate (thực thể) cuối cùng', không cần thiết cho nó. –

+0

@Ash Burlaczenko, gọi ở cuối phương thức là cần thiết nếu phương thức Update() được gọi trong ngữ cảnh giao dịch bên ngoài. Nếu không, nó được tạo ra trong khối "if". –

Các vấn đề liên quan