2016-08-26 9 views
7

के लिए किया जा सकता है। मैं ईएफ 6.1.3 और .NET Framework 4.6.1 का उपयोग कर मॉडल लागू कर रहा हूं। इस मॉडल का उपयोग एएसपीएनईटी ऐप द्वारा और एएसपीएनईटी कोर ऐप द्वारा किया जाता है, इसी कारण से यह System.Data.Entity का उपयोग करता है और यह एक अलग असेंबली mymodel.dll में स्थित है।केवल स्रोत जो IAsyncEnumerable को लागू करते हैं, का उपयोग एंटिटी फ्रेमवर्क एसिंक्रोनस ऑपरेशंस

यह मॉडल

using System.Data.Entity; 
public partial class MyDbContext : DbContext 
{  
     public virtual DbSet<Athlete> Athletes{ get; set; } 
} 
public partial class Athlete 
{ 
    public Athlete() 
    { 
    } 
    //... 
    public string Country { get; set; } 
} 

मुझे लगता है कि aspnet कोर में .NET फ्रेमवर्क 4.6 के साथ लागू किया गया है MVC अनुप्रयोग विकसित कर रहा हूँ है। यह ईएफ 6.1.3 का संदर्भ देता है ताकि मॉडल का उपयोग किया जा सके।

public class MyViewModel 
{ 
    public IList<Athlete> ItalianAthletes{ get; set; } 
} 

using Microsoft.EntityFrameworkCore; 
//solution: comment the previous line and use instead System.Data.Entity; 
public class MyController : Controller 
{ 
    private readonly MyDbContext _context; 
    //... 
    public IActionResult Index() 
    { 
     MyViewModel myvm = new MyViewModel(); 
     var result = _context.Athletes.Where(a=>a.Country=="Italy").ToList(); 
     myvm.ItalianAthletes = result ; 
     return View(myvm); 
    } 
} 

... और यह अपेक्षा के अनुसार काम करता है।

अब बदल रहा async के सूचकांक विधि

public async Task<IActionResult> Index() 
{ 
    MyViewModel myvm = new MyViewModel(); 
    var result = _context.Athletes.Where(a=>a.Country=="Italy").ToListAsync(); 
    await result; //at this point an exception is thrown 
    //... 
} 

InvalidOperationException: स्रोत IQueryable IAsyncEnumerable को लागू नहीं करता है। केवल स्रोत जो IAsyncEnumerable को लागू करते हैं, का उपयोग एंटिटी फ्रेमवर्क एसिंक्रोनस ऑपरेशंस के लिए किया जा सकता है।

कहां() खंड को हटा रहा है समस्या को जारी रखता है, इसलिए समस्या ToListAsync() से संबंधित प्रतीत होती है;

var result = _context.Users.ToListAsync(); 

मेरी बात ध्यान से अपवाद मैं समझता हूँ कि "IQueryable ToList (द्वारा उत्पन्न) does not को IAsyncEnumerable लागू" लेकिन यह does not कर भावना का पाठ पढ़ने क्योंकि वह सब व्यवहार ToListAsync करने के लिए आंतरिक है();

कोई मुझे हुड के नीचे क्या हो रहा है यह बेहतर ढंग से समझने में मदद कर सकता है? और मैं क्या कर सकता हूं ताकि ToListAsync() अपेक्षा के अनुसार काम करता हो?

किसी भी टिप्पणी के लिए अग्रिम धन्यवाद

+1

आप में मदद की जा सकती है: https://msdn.microsoft.com/en-us/data/dn313107 – Sampath

+0

समाधान –

उत्तर

10

आप इन 2 चीजों में से एक करना चाहते हैं।

दोनों विधानसभाओं में ईएफ न्यूज पैकेज का संदर्भ लें। ऐसा इसलिए है क्योंकि यह ToListAsync() ऑपरेशन वास्तव में आपके ईएफ डीबीकॉन्टेक्स्ट के माध्यम से बुलाया जा रहा है और यह किसी ऐसे प्रोजेक्ट से नहीं किया जा सकता है जिसमें ईएफ NugetPackage का कोई संदर्भ नहीं है। यदि यह पहले से ही है मामला वाकई कोड के शीर्ष पर बयान का उपयोग करने में नाम स्थान System.Data.Entity संदर्भित कर रहे हैं बनाने:

using System.Data.Entity; 

इस रूप में विस्तार विधि ToListAsync आप कॉल करना चाहते का स्थान है।


लपेटें कोड है कि अपनी परियोजना में एक सेवा एफई का उपयोग करता है में एफई से प्राप्त करता है, कॉल async बनाने के लिए, और फोन है कि अपने asp.net MVC के परियोजना से। यह मेरी पसंदीदा पसंद होगी क्योंकि यह अमूर्तता की एक अच्छी परत जोड़ता है और आपके कोड को परीक्षण/बनाए रखने में आसान बनाता है।2 विकल्प

public interface IAthleteService { 
    Task<List<Athlete>> GetAthletesByCountryAsync(string country, CancellationToken token); 
} 

public class AthleteService : IAthleteService { 
    private MyDbContext _context; 
    public async Task<List<Athlete>> GetAthletesByCountryAsync(string country, CancellationToken token) 
    { 
     return await _context.Athletes.Where(athlete => athlete.Country == country).ToListAsync(token).ConfigureAwait(false); 
    } 
} 

public class MyController : Controller 
{ 
    private readonly IAthleteService _service; 
    //... 
    public async Task<IActionResult> Index(CancellationToken token) 
    { 
     MyViewModel myvm = new MyViewModel(); 
     myvm.ItalianAthletes = await _service.GetAthletesByCountryAsync("Italy", token).ConfigureAwait(true); 
     // rest of code 
    } 
} 

नोट्स के लिए

कोड उदाहरण:

  • मैं एक CancellationToken इस्तेमाल किया, यह एक async आपरेशन को रद्द करने के लिए अनुमति देता है। यह पूरी तरह से वैकल्पिक है।
  • मैंने कॉन्फ़िगरएवाइट का उपयोग किया, यह आपको ऑपरेशन फिर से शुरू होने पर वही थ्रेड संदर्भ को पुनः प्राप्त करने की अनुमति देता है। यह संसाधनों को सहेजने के लिए बचाता है (झूठा पास) लेकिन जब आप इसे संभव हो तो केवल ऐसा कर सकते हैं। उपर्युक्त उदाहरण में यह पुस्तकालय में किया गया है। इसके अलावा उपर्युक्त उदाहरण में यह नियंत्रक से नहीं किया गया है क्योंकि आपको थ्रेड से जुड़े एचटीपी संदर्भ की आवश्यकता है (सत्य पास करें)।
  • मैंने संसाधनों की सफाई को ध्यान में नहीं रखा (जैसे डीबीकॉन्टेक्स्ट को साफ करने के लिए एथलीट सेवा डिस्पोजेबल बनाना) या निर्भरताओं के किसी भी इंजेक्शन।
+0

दोनों विधानसभाओं पहले से ही एफई संदर्भित कर रहे हैं के साथ कोड का संपादन किया। 6.1.3 (मेरे प्रश्न को संपादित किया गया) –

+1

@ रॉबर्टो वानोली - क्या आपने यह सुनिश्चित किया है कि 'System.Data.Entity का उपयोग करना;' शीर्ष पर आपके कंट्रोलर कोड फ़ाइल में शामिल है? इस नेमस्पेस में वह एक्सटेंशन विधि है जिसे आप कॉल करना चाहते हैं। – Igor

+0

आप अनुमान लगा रहे थे कि मैं गलत ईएफ का संदर्भ दे रहा था। प्रभावी रूप से मैं अपने नियंत्रक में माइक्रोसॉफ्ट.इन्टिटीफ्रेमवर्ककोर का उपयोग कर रहा था, इसके बजाए System.Data.Entity सही ToListAsync() विधि अब कहा जाता है (अस्पष्ट क्यों ToList() संस्करण पहले काम कर रहा था)। पीएस: मैं आपके अतिरिक्त सुझावों के लिए +1 जोड़ूंगा लेकिन मेरी प्रतिष्ठा मुझे इस समय मतदान करने की अनुमति नहीं देती है :-( वैसे भी धन्यवाद और –

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