2013-07-30 27 views
4

我有一個Windows服務,使用定時器定期調用類庫(在工作線程上)。這個類庫具有所有必需的應用程序功能,Windows服務僅僅是一個簡單的託管環境。該庫作爲其執行的一部分需要調用數據庫並獲取一堆記錄。這些記錄不會經常改變(想想幾周),我想將它們緩存在內存中。我應該在類庫還是Windows服務中實現緩存結構?在哪裏實現緩存 - 類庫或Windows服務

本質上我有點不確定的是,一旦Windows服務加載,然後定期調用此類庫,庫運行的應用程序域對於庫的所有執行都保持不變(通過工作者線程每隔幾分鐘)。因爲如果不是這樣,在庫中實現緩存的目的似乎毫無意義。

有人能幫我理解嗎?

回答

0

這是一個有效的設計問題,但我認爲你從一個錯誤的角度來看待它:而不是思考應用程序域和其他可能使你難以實現功能的東西,邏輯設計的觀點。

這裏有可能影響你的思維的一些注意事項:

  • 你的類庫呈現一定的接口,它的用戶。所有調用你的類庫的用戶都坐在內存緩存的後面是否有意義?如果這個問題的答案是「是」,那麼緩存功能屬於類庫。
  • 由於類庫是一個獨立的實體,可能你想隱藏庫的客戶的一些實現細節,比如窗口的服務。如果服務要將數據緩存一段時間,那麼該服務將擁有數據不經常變化的知識。如果這是不可取的,請將緩存功能放入類庫中。
  • 如果數據的性質可能比您正在編寫的特定Windows服務更頻繁地更改,那麼緩存屬於Windows服務。
  • 如果您打算在未來實現控制緩存狀態的其他功能,例如強制緩存失效的方法,那麼該功能屬於Windows服務(儘管您也可以將其放入類中庫,併爲其用戶顯式控制其狀態)。
+0

非常感謝您的回覆。我不能指望任何更簡潔的東西! – Cranialsurge

0

在類似的情況下,我在庫中實現了緩存(因爲它是你的主代碼庫),但是它使得它與主呼叫服務獨立。

像這樣的事情

class ServiceRun 
{ 
    private MyLibrary.LibraryContext _context; 
    private Timer _timer; 

    public ServiceRun() 
    { 
     _context = MyLibrary.Core.InitializeBaseData(); 
     _timer = new Timer(10000); 
     _timer.OnTick+=()=> MyLibrary.Core.DoAction(_context); 
    } 
} 

應該LibraryContext關心它自己的完整性或服務需要調用類似_context.Refresh()與另一個定時器完全是你的選擇,因爲幾乎不取決於存儲在它的數據。

0

您的緩存方法將基於您的實現。從你上面描述的你的服務是一個簡單的包裝。這個包裝器調用了一個(我通過線程假設)類庫來完成實際的過程。

有了這個設計,我會建議在類庫中實現你的「緩存服務」。儘管庫中的類正在被執行並被處置掉,但在庫的其他類完成之後,您的類庫無法保持對緩存的引用。

就個人而言,因爲類庫需要緩存的對象,我沒有看到任何理由爲什麼服務需要訪問這些對象。另外通過維護你的類庫中的緩存可以讓你「隱藏」你的緩存對象。最後,另一個重大的積極因素是調試和修復bug會容易得多。由於您可以在任何其他應用程序中運行類庫,因此您不必在Windows服務中進行調試,這本身可能頗具挑戰性。

我認爲真正的問題是你應該使用什麼類型的緩存,這對正在使用的內存總量有很大的影響。現在這是一個不同的問題。

對於緩存,您有許多實施選項。最常見的內存緩存是使用.Net框架的一部分MemoryCache功能完成的。這支持expreration策略,以及類似於ASP.Net web實現的完整緩存包裝器。

MSDN的內存緩存:http://msdn.microsoft.com/en-us/library/system.runtime.caching.memorycache.aspx

在我看來,最終我可能會換你的緩存系統進入使用singleton或通過DependencyInjection保持高速緩存的對象的類。

希望這會有所幫助。

Nico

+0

非常感謝您的回覆,希望我可以在這裏標記兩個答案。我一定會在接近這個時候保持你和dasblinkelight所說的。此外,MemoryCache對我來說是新的,欣賞那裏的指針! – Cranialsurge