2010-01-06 23 views
41

Tôi mới sử dụng NHibernate và đã gặp một số vấn đề khi đóng phiên sớm. Tôi đã giải quyết điều này tạm thời bằng cách sử dụng lại các phiên thay vì mở một phiên cho mỗi giao dịch. Tuy nhiên, tôi đã ấn tượng rằng các buổi mở đầu mỗi khi bạn cần chúng là phương pháp được khuyến nghị cho quản lý suốt đời của phiên. Không?Điều gì sẽ là cuộc đời của một phiên NHibernate?

Vì vậy; cách xử lý được khuyến nghị là gì? Cuộc sống của họ sẽ là gì? Một phiên giao dịch pr? Một phiên đơn để xử lý mọi thứ? Hay cái gì?

Edit:

Lưu ý rằng kiến ​​trúc ứng dụng của tôi là một ứng dụng máy tính để bàn giao tiếp với một dịch vụ phía máy chủ, đó là những gì làm tất cả việc xử lý cơ sở dữ liệu, sử dụng NHibernate + thạo. (Nếu điều này tạo ra bất kỳ sự khác biệt nào ...)

+2

Trong câu hỏi của bạn http://stackoverflow.com/questions/2011950/nhibernate-mappings-issue-when-referencing-class-lazy-load-issue bạn đã yêu cầu tôi xem xét câu hỏi mới này, nhưng tôi thấy bạn ' đã nhận được bảo hiểm phong phú rồi. Tôi thứ hai một số ý kiến ​​ở đây, nhưng lưu ý rằng có vẻ như các phiên và giao dịch được xen kẽ trong cuộc thảo luận, trong khi đó là những thứ khác nhau. Ngoài ra, một phiên nhóm hoặc phiên khởi động được kích hoạt có thể mang lại lợi ích về mặt hiệu suất, nhưng khó thiết lập và có quyền. Cũng lưu ý rằng tính năng tổng hợp kết nối được sử dụng không phụ thuộc vào mẫu bạn đã chọn. – Abel

+0

Cảm ơn bạn đã bình luận Abel. Trong ví dụ, tôi đã thấy các phiên và giao dịch thường chia sẻ cùng một thời gian, nhưng như đã thấy trong câu hỏi được tham chiếu, điều này đôi khi có thể là vấn đề .. Tôi hy vọng mọi người đã trả lời "phiên đời" - không phải "giao dịch trọn đời", ấn tượng rằng đây là trường hợp. – stiank81

Trả lời

26

Bạn muốn chiến lược quản lý phiên cho phép ứng dụng của bạn hoạt động hiệu quả và tận dụng những thứ NHibernate cung cấp cho bạn - đáng chú ý nhất là bộ nhớ đệm và tải chậm. Tạo các phiên là một quá trình không tốn kém và đòi hỏi ít RAM hoặc CPU trước, vì vậy bạn không nên lo lắng về việc bảo tồn hoặc sử dụng lại phiên (thực tế, việc sử dụng lại chúng có thể dẫn đến một số mặt khó chịu và không được dự đoán trước). - hiệu ứng). Nhà máy phiên là thứ đắt tiền và nên được xây dựng một lần và chỉ một lần khi khởi động ứng dụng.

Quy tắc chung là: thời lượng phiên cần đủ dài để bạn không có đối tượng liên tục bị treo trong phạm vi sau khi phiên kết thúc. Sau khi phiên kết thúc, tất cả thay đổi theo dõi đối tượng bạn nhận được từ phiên đó sẽ dừng lại, vì vậy những thay đổi đó sẽ không được lưu trừ khi bạn cố tình đính kèm lại đối tượng đó vào phiên mới. Do đó, phiên nên có khoảng chừng nào các đối tượng bạn tìm nạp từ nó sẽ tồn tại. Trong một ứng dụng Web, điều đó thường có nghĩa là một phiên cho mỗi yêu cầu; trong WinForms, một phiên cho mỗi biểu mẫu.

Trong trường hợp của bạn, với dịch vụ (Tôi cho rằng nó đang chạy dịch vụ Windows) làm công việc NHibernate, bạn có thể xem xét việc tạo phiên cho mỗi yêu cầu mới từ ứng dụng dành cho máy tính để bàn tiêu thụ và xử lý nó khi yêu cầu đó được phục vụ. Không biết chính xác dịch vụ của bạn chạy như thế nào và ứng dụng máy tính để bàn nào sử dụng để nói chuyện với nó (từ xa? WCF? SOAP cũ?) Tôi thực sự không thể cụ thể hơn.

(Có một số ngoại lệ đối với quy tắc chung này - giả sử bạn có một tập hợp các đối tượng liên tục đại diện cho tài nguyên được chia sẻ mà mã khác sẽ tham chiếu nhưng không thay đổi, bạn có thể tải những thứ này ở đầu ứng dụng chúng bị ngắt kết nối từ đó trở đi.)

Nếu bạn thấy hiệu suất chậm chạp trong chiến lược như vậy, có thể bạn chỉ đang nói chuyện với cơ sở dữ liệu quá nhiều và đồ thị đối tượng của bạn phức tạp; xem second-level caching trong trường hợp này.

+0

Cảm ơn!Về dịch vụ của tôi tôi đang sử dụng WCF, hiện tại với xà phòng - chạy như một ứng dụng giao diện điều khiển, nhưng tôi không nghĩ rằng điều này sẽ làm cho bất kỳ sự khác biệt, vì vậy bạn đã đủ cụ thể. Âm thanh hợp lý để có một phiên cho mỗi yêu cầu. Hiện tại tôi chỉ đang sử dụng phiên mà giao dịch đang được chạy và dường như có một số dữ liệu được tham chiếu không được tải trong giao dịch không thành công do phiên bị đóng. – stiank81

6

Phiên phải tương ứng với một đơn vị công việc. Phiên sẽ vẫn hoạt động trong khi bạn đang làm việc với các đối tượng được truy xuất hoặc tiếp tục sử dụng phiên đó.

2

Không có câu trả lời nào phù hợp với mọi tình huống. Phiên 13 của Summer of Nhibernate trình bày tổng quan tốt đẹp về vấn đề này.

0

Phần lớn khung công tác NHibernate và Khung thực thể Microsoft ADO.NET giống nhau. Đây là một bài viết rất hay về cách bạn nên điều khiển một đường dẫn của ObjectContext trong ADO.NET EF.

http://blogs.msdn.com/alexj/archive/2009/05/07/tip-18-how-to-decide-on-a-lifetime-for-your-objectcontext.aspx

Nó cũng nên áp dụng cho các phiên NHibernate.

+1

Theo ý kiến ​​của tôi, vì EF 1.0/3.5 không hỗ trợ tải dựa trên proxy tự động, sự khác biệt giữa EF và NHibernate liên quan đến vấn đề này là quá lớn để chia sẻ lời khuyên hiệu quả. Thời gian ObjectContext trong EF đơn giản hơn để quản lý vì EF không phải là tính năng phong phú. –

+0

Bạn chính xác là EF 1.0 không hỗ trợ điều đó, nhưng EF 2.0 thì không. Bài viết này dường như áp dụng cho cả hai. –

11

Trong ứng dụng web, bạn nên có một phiên cho mỗi yêu cầu. Điều này cho phép bạn kiểm soát toàn bộ thời gian của phiên và đơn giản hóa việc xử lý lỗi.

Trong ứng dụng dành cho máy tính để bàn, tôi khuyên bạn nên sử dụng phiên cho mỗi người trình bày (hoặc biểu mẫu nếu bạn thích). Để báo Ayende trong MSDN Magazine article mình:

Việc thực hành được khuyến cáo cho máy tính để bàn ứng dụng là sử dụng một phiên mỗi hình thức, do đó mỗi hình thức trong việc áp dụng có phiên riêng của mình. Mỗi biểu mẫu thường đại diện cho một phần công việc riêng biệt mà người dùng muốn để thực hiện, vì vậy, hãy kết hợp phiên toàn thời gian với thời gian biểu mẫu hoạt động khá tốt trong thực tế. Quyền lợi được thêm vào là bạn không còn gặp sự cố với rò rỉ bộ nhớ, vì khi bạn đóng biểu mẫu trong ứng dụng , bạn cũng hủy phiên . Điều này sẽ làm cho tất cả các đối tượng được tải bởi phiên đủ điều kiện để cải tạo bằng bộ thu gom rác (GC).

Có các lý do khác cho thích một phiên duy nhất cho mỗi biểu mẫu. Bạn có thể tận dụng lợi thế của theo dõi thay đổi của NHibernate, vì vậy nó sẽ tuôn ra tất cả các thay đổi vào cơ sở dữ liệu khi bạn cam kết giao dịch.Nó cũng tạo ra một rào cản cách ly giữa các hình thức khác nhau, vì vậy bạn có thể cam kết thay đổi đối với một thực thể duy nhất mà không cần lo lắng về các thay đổi đối với các đơn vị khác được hiển thị trên các hình thức khác .

+0

"phiên trên mỗi hoạt động" khá mơ hồ. Bạn nên đề cập đến "phiên cho mỗi yêu cầu" –

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