2012-09-06 9 views
7

मैंने ईमेल बनाने और भेजने के लिए एक विंडोज सेवा बनाई है। मैं ईमेल टेम्पलेट्स को पार्स करने के लिए Razor Engine का उपयोग कर रहा हूं। मैं मॉडल बनाने के लिए एक गतिशील ExpandoObject का उपयोग कर रहा हूँ।रेजोरइंजिन मेमोरी उपयोग

मेरी समस्या तब होती है जब प्रत्येक ईमेल बनाया जाता है और स्मृति भेजता है लेकिन इसे कभी जारी नहीं किया जाता है। मैं चींटियों मेमोरी प्रोफाइलर साथ सेवा प्रोफाइल है (मैं इस से पहले इस्तेमाल नहीं किया है), लेकिन यह निम्न परिणाम दिखा रहा है:

उस्तरा इंजन

Razor.Parse (पाठ, मॉडल के साथ 200 ईमेल पार्सिंग के साथ)

जनरेशन 1: 12.9kb

जनरेशन 2: 15.88mb

बड़े वस्तु ढेर: 290.9kb

अप्रयुक्त स्मृति नेट के लिए आवंटित: 3.375mb

अप्रबंधित: 69.51mb

स्मृति टुकड़े की कुल संख्या: 197

कोई उस्तरा इंजन

200 ईमेल अनपेक्षित पाठ लौट रहा है।

जनरेशन 1: 13.87kb

जनरेशन 2: 3.798mb

बड़े वस्तु ढेर: 95.58kb

अप्रयुक्त स्मृति नेट के लिए आवंटित: 4.583mb

अप्रबंधित: 44.58 एमबी

स्मृति टुकड़ों की कुल संख्या: 7

रेजर के साथ

सबसे बड़ी पीढ़ी 2 उदाहरण हैं:

System.Reflection.Emit __FixUpData [] - 2,447,640 लाइव बाइट्स, 3,138 उदाहरणों

किसी को भी किसी भी विचार क्यों वस्तुओं जारी नहीं किया जा रहा है है और जनरेशन 2 बढ़ रहा है? प्रत्येक बार जब मैं टेम्पलेट को पार्स करना चाहता हूं और जब इसे समाप्त किया जाता है तो इसे रेजरइंजिन का एक नया उदाहरण प्राप्त करने का कोई तरीका है, इसे संदर्भित नहीं किया जाएगा और जीसी में जाएगा।

Ive हर बार मैं एक टेम्पलेट पार्स खाका सेवा का एक नया उदाहरण बनाने की कोशिश की लेकिन यह नहीं चढ़े, जिस एक फर्क

using (ITemplateService templateService = new TemplateService()) 
{ 
    result = templateService.Parse<ExpandoObject>(text, model); 
} 
+0

यह एक पुराना सवाल है, लेकिन मुझे नहीं लगता कि 'पार्स()' कॉलम को कैश करता है। मैंने जो किया है वह 'Razor.GetTemplate()' का उपयोग कर रहा है और लौटाए गए 'ITemplate' उदाहरण पर' रन() 'को कॉल कर रहा है। अभी भी यह देखने के लिए कि असेंबली कितनी मेमोरी लेती है, लेकिन अगर इसे ठीक से कैश किया जाता है तो प्रति टेम्पलेट केवल एक असेंबली होना चाहिए। – mao47

+0

क्या आपने सफलतापूर्वक टेम्पलेट्स को कैश किया है? मेरी सेवा में स्मृति अभी भी बढ़ जाती है और कचरा इकट्ठा नहीं होता है। क्या आपने स्मृति उपयोग में कमी देखी है? – ministrymason

+0

वर्तमान में ITEMplate टेम्पलेट = Razor.Resolve (टेम्पलेटफाइलनाम, मॉडल) कर रहा हूँ; स्ट्रिंग परिणाम = टेम्पलेट। रुन(); लेकिन स्मृति अभी भी हास्यास्पद बढ़ने के लिए contunes। – ministrymason

उत्तर

2

हर बार जब आप एक टेम्पलेट को पार्स किया, RazorEngine एक में स्मृति विधानसभा संकलित करता है।
महंगा हो सकता है।

आपको जितना संभव हो सके अपने टेम्पलेट का पुन: उपयोग करना चाहिए।

+1

क्यों नहीं है यह वस्तुओं को जारी कर रहा है? उनके लिए एक संदर्भ क्या है? – ministrymason

+0

शायद इसकी ओवरकिल? अल मैं एक गतिशील मॉडल के साथ एक स्ट्रिंग पार्स करना चाहता हूँ। मैंने माना कि प्रत्येक टेम्पलेट को पार्स करने के बाद, रेजर के भीतर सब कुछ जारी किया जाएगा क्योंकि इसकी आवश्यकता नहीं है? – ministrymason

+0

@ministrymason: गतिशील असेंबली उतारना मुश्किल है। – SLaks

0

जब आप एक टेम्पलेट संकलित करते हैं, तो बनाई गई गतिशील असेंबली वर्तमान एपडोमेन में लोड की जाती है। उन्हें अनलोड करने की कोई सुविधा नहीं है, क्योंकि आप अधिक टेम्पलेट संकलित करते हैं, स्मृति बढ़ती रहती है।

आप इस बारे में जानने के लिए RazorEngine 3.x में IsolatedTemplateService का उपयोग कर सकते हैं। यह एक नए एपडोमेन में संकलित टेम्पलेट लोड करता है। जब वह एपडोमेन कचरा इकट्ठा होता है, तब उस ऐपडोमेन में लोड किए गए टेम्पलेट असेंबली भी एकत्र किए जाते हैं। यद्यपि कुछ सीमाएं हैं - जैसे गतिशील मॉडल (एक्सपांडो ऑब्जेक्ट्स) या अज्ञात मॉडल का उपयोग करने में असमर्थता। मॉडल को क्रमबद्ध करने की भी आवश्यकता है।

RazorEngine के लेखक की ओर से इस की जाँच करें: http://www.fidelitydesign.net/?p=473

+0

मैं एक गतिशील मॉडल का उपयोग कर रहा हूं इसलिए मैं IsolatedTemplateService का उपयोग नहीं कर सकता। क्या स्मृति को निरंतर बढ़ने से रोकने का कोई और तरीका नहीं है? अगर मैं टेम्पलेट्स को कैश करता हूं तो बेहतर होगा? फिलहाल मैं टेम्पलेट को पुनर्प्राप्त करता हूं और टेम्पलेट नाम के बजाए इसे स्ट्रिंग के रूप में रेजरइंजिन में पास करता हूं। – ministrymason

+0

RazorEngine का उपयोग करने का सबसे अच्छा तरीका क्या है? आवेदन ive लिखा गया स्मृति 2 जीबी तक बढ़ गया है। मुझे विश्वास नहीं है कि अन्य लोगों को समस्याएं नहीं लग रही हैं। – ministrymason

1

पुराना सवाल है, लेकिन टेम्पलेट कैश आप पार्स विधि के लिए "कैश" तर्क (जो/अपने टेम्पलेट के लिए पथ होना चाहिए कर सकते हैं प्रदान करना होगा सक्रिय करने के लिए):

return RazorViewService.Parse(File.ReadAllText(path), model, null, cache); 
0

आप एक ही टेम्पलेट का उपयोग कर रहे हैं तो बार-बार RazorEngine.Compile एक बार फिर Razor.Run वहाँ के बाद फोन सुनिश्चित करना है कि टेम्पलेट केवल एक बार संकलित किया गया है।

मुझे यह भी विश्वास है कि निर्माण में DEBUG सक्षम होने पर RazorEngine स्मृति को रिसाव लग रहा है। सुनिश्चित करें कि आपका उत्पादन कोड रिलीज प्रोफ़ाइल के साथ बनाया गया है यानी DEBUG कंपाइलर निरंतर के बिना।

संबंधित मुद्दे