2010-01-22 66 views
5

我們遇到異常高的內存使用問題。我觀察到,在我們的代碼中的很多地方,我們正在從數據庫中取出100條記錄,將其包裝在自定義數據對象中,將其添加到數組列表並存儲在會話中。我想知道會話中建議的上限存儲數據是什麼。只是一個不錯的練習類的事情。多少會話數據太多?

我正在使用JRockit 1.5和1.6GB的RAM。我使用Jprobe進行了分析,發現應用程序的某些部分內存佔用量非常大。大部分數據正在進入會話以供稍後使用。

+0

我在Weblogic上運行一個J2EE struts應用程序10 – 2010-01-22 10:44:01

+0

這真的是一個平臺不可知的問題。 – 2010-01-22 10:44:40

回答

6

這完全取決於有多少會話通常存在(這又取決於你有多少用戶,多久他們留在網站上,並在會話超時)和多少RAM你的服務器。

但首先:你有沒有實際使用的內存分析器來告訴你,你的「內存佔用率過高」是由會話數據引起的,或者你只是猜測?

如果你遇到的唯一問題是生產機器上的「高內存使用率」(即它可以處理生產負載,但性能不如你想要的),最簡單的解決方案是獲得更多的RAM服務器 - 比重新設計應用程序更快,更便宜。

但在會議上緩存整個結果集出於不同的原因是糟糕的,以及如果只能在數據庫中的數據變化和用戶期望看到這種變化?如果您要緩存,請使用one of the existing systems,它們在數據庫請求級別執行此操作 - 它們將允許您在用戶之間緩存結果,並且它們具有用於緩存失效的功能。

+0

在問題中增加了更多細節。 – 2010-01-22 10:59:22

6

如果你在會話中存儲數據,以提高性能,可以考慮使用真正的緩存,因爲緩存的應用範圍,而會議是每個用戶,這會導致其他類似物體的不必要的重複。

但是,如果您正在存儲它們供用戶編輯此對象(我懷疑,因爲數百個對象太多了),請儘量減少存儲的數據量或研究樂觀併發控制。

1

我想說這很大程度上取決於您期望的活動會話的數量。如果您正在用戶編寫一個內部網應用程序,那麼在會話中放置幾個​​MB肯定沒有問題。但是,如果您希望實例5000實時會話,則每個會話存儲的每MB數據佔用5GB的RAM。

但是,我通常建議不要在會話中存儲來自數據庫的任何數據。只需從數據庫中獲取每個請求。如果性能問題,請使用應用程序範圍內的緩存(例如Hibernate的第二級緩存)。

1

什麼類型的數據是什麼呢?每個會話真的需要它嗎,還是可以在應用程序級別緩存?你真的需要所有的列還是隻有一個子集?它多久訪問一次?需要提供哪些頁面?等等。

當你真的需要時從數據庫中檢索記錄可能更有意義。在會話中存儲數百條記錄絕不是一個好策略。

+0

每次會話都需要它,我無法緩存它的應用程序級別。如果我每次都從數據庫中檢索,即使我在內存中獲得一些信息,它會不會是性能損失 – 2010-01-22 10:48:02

+1

並且您需要*所有*列數據?所有這些行?在每一頁上?你必須能夠優化一下。是的,無論負載如何,通常在會話中存儲數百個完整的記錄並不是一個好策略。 – 2010-01-22 10:53:33

1

我會說盡量存儲最小數量的數據,足以在隨後的請求中重新創建必要的環境。如果您在內存中存儲以避免數據庫往返,那麼真正的緩存解決方案(如Memcache)可能會有所幫助。

如果您將這些會話存儲在內存中而不是數據庫中,則會保存往返行程,並且只要內存負載較低並且沒有分頁,請求的服務速度就會更快。一旦客戶端數量增加並且分頁開始,大多數客戶端的響應時間就會出現巨大的下降。這兩個變量和負相關。

它更好地衡量您的數據庫服務器的延遲,這通常足夠低,在大多數情況下被認爲是一種可行的存儲手段而不是內存。

1

嘗試將當前存儲在會話中的數據拆分爲用戶特定數據和靜態數據。然後爲所有靜態部分實施緩存。這將爲您在整個應用程序範圍內提供大量重用,並允許您緩存用戶正在處理的特定數據。

1

你也可以製作每個用戶的迷你sqlite數據庫並連接到它,並存儲用戶訪問的數據,然後在用戶請求它時檢索記錄,並在用戶斷開連接後只需刪除sqlite數據庫。