2013-02-24 62 views
5

我想将新的异步等待功能应用于导入到我的实体模型中的存储过程/函数导入,但尚未与EF6 alpha一起使用。EF6 alpha异步等待实体存储过程/函数导入?

在EF6 alpha2(或20211的夜间版本)中,是否可以调用返回复杂类型集合的Entity Function Import(调用SQL存储过程)上的任何新Async方法?例如

private async Task<IList<Company>> getInfo (string id) 
{ 
    using (CustomEntity context = new CustomEntity()) 
    { 
     var query = await context.customStoredProcedure(id).ToListAsync(); 
     // ".ToListAsync()" method not available on above line 

     // OR ALTERNATIVELY 
     var query = await (from c in context.customStoredProcedure(id) 
          select new Company 
          { 
           Ident = c.id, 
           Name = c.name, 
           Country = c.country, 
           Sector = c.sector, 
           etc. etc.... 
          }).ToListAsync(); 
     // ".ToListAsync()" method or any "...Async" methods also not available this way 

     return query; 
    } 
} 

“ToListAsync”,或任何新的异步改性方法似乎不提供给存储过程/函数导入上述实体;只有标准的“ToList”或“AsNumerable”等方法可用。

我跟着这个(http://entityframework.codeplex.com/wikipage?title=Updating%20Applications%20to%20use%20EF6),以确保代码是引用新的EF6 DLL而不是EF5,以及更新各种使用语句。除了上面以外,所有内容都可以正确构建。 (.NET Framework 4.5)

我唯一可以看到异步方法的是,如果不是只从数据库导入存储过程,我还导入一个表 - 然后当通过上面的实体上下文引用该表时context.SomeTable),一些异步方法出现在intellisense中。

我真的很想在将数据作为JSON返回之前在多个存储过程中开始使用新的异步等待功能,但尚未能使它在目前的工作中发挥作用。

我做错了什么?实体存储过程/函数导入不可能实现异步功能吗?谢谢你的建议。

+0

'context.customStoredProcedure(id)'静态有什么类型? – usr 2013-02-24 14:13:55

+0

系统。Data.Entity.Core.Objects.ObjectResult blueFish 2013-02-24 14:40:40

+0

你有没有得到它的工作?我与Stored Proc有同样的问题需要ASYNC。 – 2013-11-11 20:02:26

回答

4

现在这绝不是最好的解决方案。我添加了一个扩展方法,以便我可以在我的存储过程中调用await。在新版本的EF6.1 +中,我们应该看到这个正式实施。在此之前,一个虚拟扩展方法完成这项工作。

static async Task<List<T>> ToListAsync<T>(this ObjectResult<T> source) 
{ 
    var list = new List<T>(); 
    await Task.Run(() => list.AddRange(source.ToList())); 
    return list; 
} 

如果您反映EF的6版本,你会看到,实际上ObjectResult<T>实现IDbAsyncEnumerable<T>, IDbAsyncEnumerable。而且ToListAsync<T>(this IDbAsyncEnumerable<T> source)的方法应该能够将它与LINQ查询相同。

编辑 当ObjectResult为空时,返回null。如果你想返回一个空的List而不是null,你可以添加if (source == null) return new List<T>();

+4

用'Task.Run'产生一个新线程,这样你就可以“等待”一个方法,完全失败了异步/等待的目的。你通过等待来释放主线程,但是你刚刚产生了一个新线程。如果考虑产生这个新线程的开销,然后在产生的线程完成时最终恢复主线程,则性能会更差。 – TugboatCaptain 2015-10-14 20:09:07

0

这是一个古老的线程,但我觉得我应该分享。您应该使用APM,然后在任务中包装同步呼叫。

例如:当您要执行

// wraps the method in a task and returns the task. 
public Task<MyResult> MySPAsync() 
{ 
    MySPDelegate caller = new MySPDelegate(MySP); 
    return Task.Factory.FromAsync(caller.BeginInvoke, caller.EndInvoke, null); 
} 

调用异步方法:

var MyResult = await MySPAsync(); 

您最多可以使用

//declare the delegate 
private delegate MyResult MySPDelegate(); 

// declare the synchronous method 
private MyResult MySP() 
{ 
    // do work... 
} 

然后包裹在任务中的同步方法到方法中的三(3)个参数。最佳做法是如果您使用三个以上的参数;你应该通过一堂课。