11

मेरे पास एक नियंत्रक क्रिया है जो जावास्क्रिप्ट फ़ाइल लौटाती है। मैं इस फ़ाइल को मेरे विचार से संदर्भित कर सकता हूं और यह ठीक काम करता है। मैं इसे एक सिस्टम में रखना चाहता हूं। Web.Optimization.Bundle अन्य जेएस फ़ाइलों के साथ।मैं एक बंडल में एएसपी.नेट एमवीसी नियंत्रक कार्रवाई का परिणाम कैसे जोड़ सकता हूं?

मैं यह करने के कोशिश कर रहा हूँ, अनिवार्य रूप से:

new Bundle().Include("~/DynamicScript/UrlDictionary"); 

अन्य फ़ाइलों मेरी बंडल में ठीक प्रदान की गई हो, लेकिन इसे अनदेखा कर दिया जाता है। इस व्यवहार को देखते हुए, मेरी धारणा यह है कि एप्लिकेशन रूटिंग इंफ्रास्ट्रक्चर के माध्यम से यूआरएल को हल करने में सक्षम होने से पहले बंडलिंग को संभाला जाता है, या हो सकता है कि बंडलिंग घटक फाइलों को ऐसे तरीके से अनुरोध नहीं करता है जो उस संकल्प को होने की अनुमति देगा।

अगर कोई मेरी पुष्टि कर सकता है और/या मुझे एक अच्छी दिशा में इंगित करता है, तो इसकी सराहना की जाएगी।

उत्तर

0

बंडलिंग सिस्टम केवल आवेदन मार्गों की बजाय भौतिक फाइलों का समर्थन करता है।

6

मुझे लगता है कि यह काफी काम करने योग्य है - लेकिन इससे पहले कि मैं अपने समाधान में जाऊं - याद रखें कि बंडल पहली हिट पर बनाया गया है और इसका पुन: उपयोग किया गया है - इसका मतलब है कि किसी भी 'गतिशील' स्क्रिप्ट को अभी भी वैश्विक होना चाहिए (यानी यह नहीं हो सकता है एक विशिष्ट उपयोगकर्ता आदि पर निर्भर हो)। यही कारण है कि आम तौर पर यह केवल स्थिर जेएस फाइलों की अनुमति देता है। यह कहकर ... मैं ऐसी स्थिति की कल्पना कर सकता हूं जहां आप संस्करण संख्या या अपने जेएस में ऐसा कुछ वैरिएबल चिपकाना चाहें (हालांकि उस मामले में मैं व्यक्तिगत रूप से इसे पाने के लिए अजाक्स/जेएसओएन का उपयोग करता हूं)।

मुझे लगता है कि इसके बारे में जाने का तरीका Bundle से व्युत्पन्न प्रकार बनाना है। इसमें आप EnumerateFiles विधि को ओवरराइट करेंगे। शुरुआत में आप आधार पर गणना करेंगे। अनन्य फ़ाइल और फिर अपनी खुद की वर्चुअल फ़ाइल शामिल करें।

कुछ (ध्यान दें: नहीं परीक्षण किया कोड): जैसे

public class VirtualMethodBundle : Bundle 
{ 
    private List<VirtualFile> _virtualContent = new List<VirtualFile>(); 

    public override IEnumerable<VirtualFile> EnumerateFiles(BundleContext context) 
    { 
     foreach(var file in base.EnumerateFiles(context)) 
     { 
      yield return file; 
     } 

     foreach(var virtual in _virtualContent) 
     { 
      yield return virtual; 
     } 
    } 

    public void AddCustomFile(VirtualFile file) 
    { 
     _virtualContent.Add(method); 
    } 
} 

तो फिर तुम एक विशेष VirtualFile परिभाषित प्रकार है कि ओपन/नाम विधि ओवरराइड करता है और आपकी गतिशील सामग्री देता है ... की तरह कुछ होगा।

public class MethodBasedVirtualFile : VirtualFile 
{ 
    private readonly Func<string> _contentFactory; 
    private readonly string _path; 

    public MethodBasedVirtualFile(string path, Func<string> contentFactory) 
    { 
     _path = path; 
     _contentFactory = contentFactory; 
    } 

    public override string Name { get { return _path; } } 

    public override Stream Open() 
    { 
     MemoryStream stream = new MemoryStream(); 
     StreamWriter writer = new StreamWriter(stream); 
     writer.Write(_contentFactory()); 
     writer.Flush(); 
     stream.Position = 0; 
     return stream; 
    } 
} 

तो फिर यह सब आप के लिए होता है उपयोग करने के लिए ...

var bundle = new VirtualMethodBundle(); 
bundle.Include(... real files ...); 
bundle.AddCustomFile(
    new MethodBasedVirtualFile("~/DynamicScript/UrlDictionary", 
    ... the method that creates the content of that script...) 
); 

यदि आप चतुर तुम सिर्फ एक UrlVirtualFile कि url पथ लेता है और का उपयोग करता MVC जब स्वचालित रूप से सामग्री प्राप्त करने के कर सकते थे की आवश्यकता है।

+0

आप EnumerateFiles अधिभावी कर रहे हैं() वापसी प्रकार, यह IEnumerable IEnumerable नहीं है:

public ActionResult ReturnFooBundle() { return new BundleResult("foo", TimeSpan.FromDays(7)); } 

यहाँ BundleResult कार्यान्वयन है। कोड संकलित नहीं होगा। –

3

यहां मैंने इस परिदृश्य के लिए क्या किया है। मैंने एक "बंडल परिणाम" परिभाषित किया और फिर मेरे नियंत्रक विधि में, बस नाम से एक बंडल लौटा दिया। मैं क्लाइंट कैशिंग के अनुकूलन के रूप में ईटैग (अगर-नो-मैच हैडर) का उपयोग कर रहा हूं।

जैसे:

public class BundleResult 
    : ActionResult 
{ 
    private class BundleInfo 
    { 
     public string BundleETag; 
     public DateTime LastModified; 
     public Bundle TheBundle; 
     public BundleResponse Response; 
    } 

    private static Dictionary<string, BundleInfo> _bundleCache = new Dictionary<string, BundleInfo>(); 

    public string BundleName { get; private set; } 
    public TimeSpan CacheExpiry { get; private set; } 

    public BundleResult(string bundleName, TimeSpan cacheExpiry) 
    { 
     BundleName = bundleName; 
     CacheExpiry = cacheExpiry; 
    } 
    public override void ExecuteResult(ControllerContext context) 
    { 
     context.HttpContext.Response.Clear(); 
     BundleInfo bundleInfo = GetBundle(context.HttpContext); 

     string requestETag = context.HttpContext.Request.Headers["If-None-Match"]; 
     if (!string.IsNullOrEmpty(requestETag) && (requestETag == bundleInfo.BundleETag)) 
     { 
      context.HttpContext.Response.StatusCode = (int)HttpStatusCode.NotModified; 
      context.HttpContext.Response.StatusDescription = "Not Modified"; 
      return; 
     } 
     else 
     { 
      BundleResponse bundleResponse = bundleInfo.Response; 
      HttpResponseBase response = context.HttpContext.Response; 
      response.Write(bundleResponse.Content); 
      response.ContentType = bundleResponse.ContentType; 

      HttpCachePolicyBase cache = response.Cache; 
      cache.SetCacheability(HttpCacheability.ServerAndPrivate); 
      cache.SetLastModified(bundleInfo.LastModified); 
      cache.SetETag(bundleInfo.BundleETag); 
     } 
    } 

    private BundleInfo GetBundle(HttpContextBase context) 
    { 
     // lookup the BundleResponse 
     BundleInfo retVal; 
     lock (_bundleCache) 
     { 
      _bundleCache.TryGetValue(BundleName, out retVal); 
     } 
     if(retVal != null) 
     { 
#if DEBUG 
      // see if the contents have been modified. 
      BundleContext bundleContext = new BundleContext(context, BundleTable.Bundles, BundleName); 
      DateTime lastModified = retVal.TheBundle.EnumerateFiles(bundleContext).Select(fi => fi.LastWriteTimeUtc).Max(); 
      if (lastModified > retVal.LastModified) 
      { 
       // regenerate the bundleInfo 
       retVal = null; 
      } 
#endif 
     } 
     if (retVal == null) 
     { 
      string rawBundleName = BundleTable.Bundles.ResolveBundleUrl(BundleName); 
      string hash = rawBundleName.Substring(rawBundleName.IndexOf("?v=") + 3); 
      Bundle bundle = BundleTable.Bundles.GetBundleFor(BundleName); 
      BundleContext bundleContext = new BundleContext(context, BundleTable.Bundles, BundleName); 
      BundleResponse bundleResponse = bundle.GenerateBundleResponse(bundleContext); 
      DateTime lastModified = bundle.EnumerateFiles(bundleContext).Select(fi => fi.LastWriteTimeUtc).Max(); 
      retVal = new BundleInfo 
      { 
       BundleETag = hash, 
       Response = bundleResponse, 
       TheBundle = bundle, 
       LastModified = lastModified, 
      }; 
      lock (_bundleCache) 
      { 
       _bundleCache[BundleName] = retVal; 
      } 
     } 
     return retVal; 
    } 
} 
संबंधित मुद्दे

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